1
1

Initial dump from Zyxel

This commit is contained in:
2026-04-17 17:00:52 +02:00
commit 81fec250f4
23116 changed files with 5231237 additions and 0 deletions
@@ -0,0 +1,42 @@
#
# (C) Copyright 2000-2006
# Wolfgang Denk, DENX Software Engineering, wd@denx.de.
#
# See file CREDITS for list of people who contributed to this
# project.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License as
# published by the Free Software Foundation; either version 2 of
# the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston,
# MA 02111-1307 USA
#
include $(TOPDIR)/config.mk
LIB = $(obj)libzloader.a
SRCS := $(wildcard *.c)
COBJS := $(SRCS:.c=.o)
OBJS := $(addprefix $(obj),$(COBJS))
$(LIB): $(obj).depend $(OBJS)
$(AR) $(ARFLAGS) $@ $(OBJS)
#########################################################################
# defines $(obj).depend target
include $(SRCTREE)/rules.mk
sinclude $(obj).depend
#########################################################################
@@ -0,0 +1,143 @@
#include <common.h>
#include <command.h>
#if defined(CONFIG_AR7240_GPIO) || defined(CONFIG_QCA955X_GPIO)
#include <asm/addrspace.h>
#ifdef CONFIG_AR7240_GPIO
#include <ar7240_soc.h>
#define MAX_GPIO_NUM CONFIG_AR7240_MAX_GPIO_NUM
#define REG_GPIO_OE AR7240_GPIO_OE
#define REG_GPIO_SET AR7240_GPIO_SET
#define REG_GPIO_CLEAR AR7240_GPIO_CLEAR
#define REG_GPIO_IN AR7240_GPIO_IN
#define REG_GPIO_OUT AR7240_GPIO_OUT
#define REG_GPIO_FUNC0 AR7240_GPIO_FUNC0
#define REG_GPIO_FUNC AR7240_GPIO_FUNC
#define REG_GPIO_ENABLE0 AR7240_GPIO_ENABLE0
#define REG_GPIO_ENABLE1 AR7240_GPIO_ENABLE1
#define REG_GPIO_ENABLE4 AR7240_GPIO_ENABLE4
#define REG_GPIO_ENABLE9 AR7240_GPIO_ENABLE9
#define ATH_REG_READ ar7240_reg_rd
#define ATH_REG_WRITE ar7240_reg_wr_nf
#elif defined(CONFIG_QCA955X_GPIO)
#include <atheros.h>
#define MAX_GPIO_NUM CONFIG_QCA955X_MAX_GPIO_NUM
#define REG_GPIO_OE GPIO_OE_ADDRESS
#define REG_GPIO_SET GPIO_SET_ADDRESS
#define REG_GPIO_CLEAR GPIO_CLEAR_ADDRESS
#define REG_GPIO_IN GPIO_IN_ADDRESS
#define REG_GPIO_OUT GPIO_OUT_ADDRESS
#define REG_GPIO_FUNC0 GPIO_OUT_FUNCTION0_ADDRESS
#define REG_GPIO_FUNC GPIO_FUNCTION_ADDRESS
#define REG_GPIO_ENABLE0 GPIO_IN_ENABLE0_ADDRESS
#define REG_GPIO_ENABLE1 GPIO_IN_ENABLE1_ADDRESS
#define REG_GPIO_ENABLE4 GPIO_IN_ENABLE4_ADDRESS
#define REG_GPIO_ENABLE9 GPIO_IN_ENABLE9_ADDRESS
#define ATH_REG_READ ath_reg_rd
#define ATH_REG_WRITE ath_reg_wr_nf
#endif
#include <zgpio.h>
int ar7240_configure_pio(int pio, int dir, unsigned char out_type)
{
switch ( dir ) {
case ZGPIO_CONFIG_OUTPUT:
{ int shift;
unsigned long reg = REG_GPIO_FUNC0;
//printf("GPIO_FUNC0=0x%08X + 0x%X(shift %d bits)", REG_GPIO_FUNC0, (pio/4)*4, (pio % 4)*8);
reg += ((pio / 4)*4);
shift = (pio % 4)*8;
ATH_REG_WRITE(REG_GPIO_OE, ATH_REG_READ(REG_GPIO_OE)&(~(1UL<<pio)));
ATH_REG_WRITE(reg, ATH_REG_READ(reg)&(~(0xffUL<<shift)));
if ( out_type ) {
ATH_REG_WRITE(reg, ATH_REG_READ(reg)|((unsigned long)out_type<<shift));
}
break;
}
case ZGPIO_CONFIG_INPUT:
ATH_REG_WRITE(REG_GPIO_OE, ATH_REG_READ(REG_GPIO_OE)|(1UL<<pio));
/* TODO: clear GPIO_IN_ENABLEn (n=0~9)*/
break;
default:
return -2;
}
udelay(1000);
return 0;
}
/*----------------------------------------------
* GPIO export functions
*/
int configure_pio(int pio, int dir)
{
return ar7240_configure_pio(pio, dir, 0);
}
int set_pio(int pio, int level)
{
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
#if 1
if ( ATH_REG_READ(REG_GPIO_OE) & (1UL<<pio) ) { /* input */
/* GPIO configure as input pin */
return -3;
}
switch (level) {
case ZGPIO_LEVEL_LOW:
ATH_REG_WRITE(REG_GPIO_CLEAR, 1UL<<pio);
break;
case ZGPIO_LEVEL_HIGH:
ATH_REG_WRITE(REG_GPIO_SET, 1UL<<pio);
break;
default:
return -2;
}
#endif
return 0;
}
int get_pio(int pio, int *level)
{
unsigned long value;
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
#if 1
if ( ATH_REG_READ(REG_GPIO_OE) & (1UL<<pio) ) { /* input */
value = ATH_REG_READ(REG_GPIO_IN);
} else { /* output */
value = ATH_REG_READ(REG_GPIO_OUT);
}
*level = (value&(1UL<<pio))?ZGPIO_LEVEL_HIGH:ZGPIO_LEVEL_LOW;
#endif
return 0;
}
int max_pio_num(void)
{
return MAX_GPIO_NUM;
}
#ifdef CONFIG_ZGPIO_CMD
void dump_pio_regs(void)
{
int i;
printf("GPIO_OE =0x%08X\n", ATH_REG_READ(REG_GPIO_OE));
printf("GPIO_IN =0x%08X\n", ATH_REG_READ(REG_GPIO_IN));
printf("GPIO_OUT =0x%08X\n", ATH_REG_READ(REG_GPIO_OUT));
printf("GPIO_FUNCTION =0x%08X\n", ATH_REG_READ(REG_GPIO_FUNC));
for (i=0; i<6; i++) {
printf("GPIO_OUT_FUN%d =0x%08X\n", i, ATH_REG_READ(REG_GPIO_FUNC0+i*4));
}
printf("GPIO_IN_ENABLE0=0x%08X\n", ATH_REG_READ(REG_GPIO_ENABLE0));
printf("GPIO_IN_ENABLE1=0x%08X\n", ATH_REG_READ(REG_GPIO_ENABLE1));
printf("GPIO_IN_ENABLE4=0x%08X\n", ATH_REG_READ(REG_GPIO_ENABLE4));
printf("GPIO_IN_ENABLE9=0x%08X\n", ATH_REG_READ(REG_GPIO_ENABLE9));
}
#endif
#endif
@@ -0,0 +1,57 @@
#include <common.h>
#include <command.h>
#ifdef CONFIG_ZGPIO_CMD
#include <zgpio.h>
int do_zgpio(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
{
int pio, val;
if ( argc == 2 && argv[1][0]=='d' ) {
dump_pio_regs();
return 0;
}
if ( argc <3 ) {
return -1;
}
pio = simple_strtoul(argv[2], NULL, 0);
if ( pio > max_pio_num() ) {
return -1;
}
if ( argc > 3 ) {
val = simple_strtoul(argv[3], NULL, 0);
if ( argv[1][0]=='s') {
if ( configure_pio(pio, val?ZGPIO_CONFIG_INPUT:ZGPIO_CONFIG_OUTPUT) ) {
printf("Fail to configure PIO %d as %s\n", pio, val?"Input":"Output");
return -1;
}
printf("Configure PIO %d as %s\n", pio, val?"Input":"Output");
} else if ( argv[1][0]=='w') {
if (set_pio(pio, val?ZGPIO_LEVEL_HIGH:ZGPIO_LEVEL_LOW)) {
printf("Fail to set PIO %d to %s\n", pio, val?"High":"Low");
return -1;
}
printf("Set PIO %d to %s\n", pio, val?"High":"Low");
}
} else if ( argv[1][0]=='r' ) {
if ( get_pio(pio, &val) ) {
printf("Fail to read PIO %d\n", pio);
return -1;
}
printf("PIO %d is %s\n", pio, val?"High":"Low");
} else {
return -1;
}
return 0;
}
U_BOOT_CMD(
zgpio, 4, 0, do_zgpio,
"GPIO access",
"s <pio> <dir> - PIO setup\n"
"zgpio w <pio> <0|1> - PIO output\n"
"zgpio r <pio> - PIO input\n"
"zgpio d - dump PIO registers\n"
);
#endif
@@ -0,0 +1,123 @@
/*
***************************************************************************
* Ralink Tech Inc.
* 4F, No. 2 Technology 5th Rd.
* Science-based Industrial Park
* Hsin-chu, Taiwan, R.O.C.
*
* (c) Copyright, Ralink Technology, Inc.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
* NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 675 Mass Ave, Cambridge, MA 02139, USA.
*
*
***************************************************************************
*/
#include <common.h>
#include <command.h>
#ifdef CONFIG_RT2880_GPIO
#include "rt2880_gpio.h"
#include <zgpio.h>
#define MAX_GPIO_NUM 31
/*----------------------------------------------
* GPIO export functions
*/
int configure_pio(int pio, int dir)
{
unsigned long tmpCtrl, tmpOE;
volatile unsigned long *gpioctrl;
int gpioctrl_bits;
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
gpioctrl_bits = pio;
if ( pio > 15 ) {
gpioctrl_bits -= 16;
gpioctrl = (volatile unsigned long *)RALINK_REG_PIO3116DIR;
} else {
gpioctrl = (volatile unsigned long *)RALINK_REG_PIODIR;
}
/* clear: default to set GPIO as input pin */
tmpCtrl = le32_to_cpu(*gpioctrl)&(~(0x3<<(gpioctrl_bits*2)));
tmpOE = le32_to_cpu(*(volatile unsigned long *)(RALINK_REG_GPIOOE))&(~(0x1<<pio));
switch ( dir ) {
case ZGPIO_CONFIG_OUTPUT:
tmpCtrl |= 0x1<<(gpioctrl_bits*2);
tmpOE |= 0x1<<pio;
break;
case ZGPIO_CONFIG_INPUT:
/* nothing need to do */
break;
default:
return -2;
}
*gpioctrl = cpu_to_le32(tmpCtrl);
*(volatile u32 *)(RALINK_REG_GPIOOE) = cpu_to_le32(tmpOE);
return 0;
}
int set_pio(int pio, int level)
{
unsigned long tmp;
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
tmp = le32_to_cpu(*(volatile u32 *)(RALINK_REG_PIODATA));
switch (level) {
case ZGPIO_LEVEL_LOW:
tmp &= (~(1<<pio));
break;
case ZGPIO_LEVEL_HIGH:
tmp |= (1<<pio);
break;
default:
return -2;
}
*(volatile u32 *)(RALINK_REG_PIODATA) = cpu_to_le32(tmp);
return 0;
}
int get_pio(int pio, int *level)
{
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
*level = (le32_to_cpu(*(volatile u32 *)(RALINK_REG_PIODATA))&(1<<pio))?ZGPIO_LEVEL_HIGH:ZGPIO_LEVEL_LOW;
return 0;
}
int max_pio_num(void)
{
return MAX_GPIO_NUM;
}
#ifdef CONFIG_ZGPIO_CMD
void dump_pio_regs(void)
{
puts("Not support!");
}
#endif
#endif
@@ -0,0 +1,151 @@
/*
***************************************************************************
* Ralink Tech Inc.
* 4F, No. 2 Technology 5th Rd.
* Science-based Industrial Park
* Hsin-chu, Taiwan, R.O.C.
*
* (c) Copyright, Ralink Technology, Inc.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
* NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 675 Mass Ave, Cambridge, MA 02139, USA.
*
*
***************************************************************************
*/
#ifndef __RT2880_GPIO_H__
#define __RT2880_GPIO_H__
#include <asm/arch/rt_mmap.h>
#define RALINK_GPIO_LED_LOW_ACT 1
#define GPIO_TRACE_NONE 0
#define GPIO_TRACE_IO 1
#define GPIO_TRACE_INT 2
#define GPIO_TRACE_ALL 3
/*
* ioctl commands
*/
#define RALINK_GPIO_SET_DIR 0x01
#define RALINK_GPIO_SET_DIR_IN 0x11
#define RALINK_GPIO_SET_DIR_OUT 0x12
#define RALINK_GPIO_READ 0x02
#define RALINK_GPIO_WRITE 0x03
#define RALINK_GPIO_SET 0x21
#define RALINK_GPIO_CLEAR 0x31
#define RALINK_GPIO_READ_BIT 0x04
#define RALINK_GPIO_WRITE_BIT 0x05
#define RALINK_GPIO_READ_BYTE 0x06
#define RALINK_GPIO_WRITE_BYTE 0x07
#define RALINK_GPIO_READ_INT 0x02 //same as read
#define RALINK_GPIO_WRITE_INT 0x03 //same as write
#define RALINK_GPIO_SET_INT 0x21 //same as set
#define RALINK_GPIO_CLEAR_INT 0x31 //same as clear
#define RALINK_GPIO_ENABLE_INTP 0x08
#define RALINK_GPIO_DISABLE_INTP 0x09
#define RALINK_GPIO_REG_IRQ 0x0A
#define RALINK_GPIO_LED_SET 0x41
#define RALINK_GPIO3116_SET_DIR 0x51
#define RALINK_GPIO3116_SET_DIR_IN 0x13
#define RALINK_GPIO3116_SET_DIR_OUT 0x14
/*
* Address of RALINK_ Registers
*/
#define RALINK_SYSCTL_ADDR RALINK_SYSCTL_BASE // system control
#define RALINK_REG_RSTCTRL2 (RALINK_SYSCTL_ADDR + 0x834) // RSTCTRL2
#define RALINK_REG_GPIOMODE (RALINK_SYSCTL_ADDR + 0x860) // GPIO share scheme
#define RALINK_IRQ_ADDR RALINK_INTCL_BASE
#define RALINK_REG_INTENA (RALINK_IRQ_ADDR + 0x04) // IMR
#define RALINK_REG_INTDIS RALINK_REG_INTENA // IMR
#define RALINK_PRGIO_ADDR RALINK_PIO_BASE // Programmable I/O
#define RALINK_REG_PIODIR (RALINK_PRGIO_ADDR + 0x0) // GPIOCTRL
#define RALINK_REG_PIODATA (RALINK_PRGIO_ADDR + 0x04) // GPIODATA
#define RALINK_REG_PIOINT (RALINK_PRGIO_ADDR + 0x08) // GPIOINT
#define RALINK_REG_PIOEDGE (RALINK_PRGIO_ADDR + 0x0C) // GPIOINTEDG
#define RALINK_REG_GPIOOE (RALINK_PRGIO_ADDR + 0x14)
#define RALINK_REG_PIO3116DIR (RALINK_PRGIO_ADDR + 0x20) // GPIOCTRL1
#define RALINK_REG_SGPIOLEDDATA (RALINK_PRGIO_ADDR + 0x24)
/*
* Values for the GPIOMODE Register
*/
#define RALINK_GPIOMODE_PCM 0x01 // GPIO_PCM
#define RALINK_GPIOMODE_SPICS1 0x02 // GPIO_SPI_CS1_N
#define RALINK_GPIOMODE_SPICS2 0x04 // GPIO_SPI_CS2_N
#define RALINK_GPIOMODE_SPICS3 0x08 // GPIO_SPI_CS3_N
#define RALINK_GPIOMODE_SPICS4 0x10 // GPIO_SPI_CS4_N
#define RALINK_GPIOMODE_SPICS5 0x20 // GPIO_SPI_CS5_N
#define RALINK_GPIOMODE_UARTF 0x40 // GPIO_UART2
#define RALINK_GPIOMODE_I2S 0x80 // GPIO_I2S
#define RALINK_GPIOMODE_NFD 0x100 // GPIO_NFD_DATA_BUS
#define RALINK_GPIOMODE_EPHY0 0x200 // GPIO_EPHY_LED0
#define RALINK_GPIOMODE_EPHY1 0x400 // GPIO_EPHY_LED1
#define RALINK_GPIOMODE_EPHY2 0x800 // GPIO_EPHY_LED2
#define RALINK_GPIOMODE_EPHY3 0x1000 // GPIO_EPHY_LED3
#define RALINK_GPIOMODE_EPHY4 0x2000 // GPIO_EPHY_LED4
#define RALINK_GPIOMODE_I2C 0x8000 // GPIO_I2C
// if you would like to enable GPIO mode for other pins, please modify this value
// !! Warning: changing this value may make other features(MDIO, PCI, etc) lose efficacy
#define RALINK_GPIOMODE_DFT (RALINK_GPIOMODE_UARTF)
/*
* bit is the unit of length
*/
#if defined (CONFIG_RT6855A_PCIE_PORT0_ENABLE)
#define RALINK_GPIO_NUMBER 33
#else
#define RALINK_GPIO_NUMBER 32
#endif
#define RALINK_GPIO_DATA_MASK 0x00FFFFFF
#define RALINK_GPIO_DATA_LEN 32
#define RALINK_GPIO_DIR_IN 0
#define RALINK_GPIO_DIR_OUT 1
#define RALINK_GPIO_DIR_ALLIN 0
#define RALINK_GPIO_DIR_ALLOUT 0x00FFFFFF
/*
* structure used at regsitration
*/
typedef struct {
unsigned int irq; //request irq pin number
pid_t pid; //process id to notify
} ralink_gpio_reg_info;
#define RALINK_GPIO_LED_INFINITY 4000
typedef struct {
int gpio; //gpio number (0 ~ 23)
unsigned int on; //interval of led on
unsigned int off; //interval of led off
unsigned int blinks; //number of blinking cycles
unsigned int rests; //number of break cycles
unsigned int times; //blinking times
} ralink_gpio_led_info;
#define RALINK_GPIO(x) (1 << x)
#endif
@@ -0,0 +1,81 @@
#include <common.h>
#include <command.h>
#ifdef CONFIG_RUBY_GPIO
#include <asm/io.h>
#include <asm/global_data.h>
#include <asm/uboot-arc.h>
#include <asm/arcregs.h>
#include <asm/arch/platform.h>
#include <zgpio.h>
#define MAX_GPIO_NUM RUBY_GPIO_MAX
extern void gpio_config(u32 pin, u32 cfg);
extern void gpio_output(u32 pin, u32 state);
extern u32 gpio_input(u32 pin);
/*----------------------------------------------
* GPIO export functions
*/
int configure_pio(int pio, int dir)
{
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
switch ( dir ) {
case ZGPIO_CONFIG_OUTPUT:
gpio_config(pio, RUBY_GPIO_MODE_OUTPUT);
break;
case ZGPIO_CONFIG_INPUT:
gpio_config(pio, RUBY_GPIO_MODE_INPUT);
break;
default:
return -2;
}
return 0;
}
int set_pio(int pio, int level)
{
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
switch (level) {
case ZGPIO_LEVEL_LOW:
gpio_output(pio, 0);
break;
case ZGPIO_LEVEL_HIGH:
gpio_output(pio, 1);
break;
default:
return -2;
}
return 0;
}
int get_pio(int pio, int *level)
{
if ( pio<0 || pio >MAX_GPIO_NUM ) {
return -1;
}
*level = gpio_input(pio)?ZGPIO_LEVEL_HIGH:ZGPIO_LEVEL_LOW;
return 0;
}
int max_pio_num(void)
{
return MAX_GPIO_NUM;
}
#ifdef CONFIG_ZGPIO_CMD
void dump_pio_regs(void)
{
puts("Not support!");
}
#endif
#endif
@@ -0,0 +1,191 @@
/*****************************************************************************
* Copyright (C) ZyXEL Communications, Corp.
* All Rights Reserved.
*
* ZyXEL Confidential; Need to Know only.
* Protected as an unpublished work.
*
* The computer program listings, specifications and documentation
* herein are the property of ZyXEL Communications, Corp. and
* shall not be reproduced, copied, disclosed, or used in whole or
* in part for any reason without the prior express written permission of
* ZyXEL Communications, Corp.
*****************************************************************************/
/*****************************************************************************
* Program: flash driver for zloader
* Author: Chang-Hsing Lee.(changhsing.lee@zyxel.com.tw), 2012/6/19
*****************************************************************************/
#include <common.h>
#include <exports.h>
#ifdef CONFIG_ENV_IS_IN_SPI_FLASH
#include <spi_flash.h>
#ifndef CONFIG_ENV_SPI_BUS
# define CONFIG_ENV_SPI_BUS 0
#endif
#ifndef CONFIG_ENV_SPI_CS
# define CONFIG_ENV_SPI_CS 0
#endif
#ifndef CONFIG_ENV_SPI_MAX_HZ
# define CONFIG_ENV_SPI_MAX_HZ 1000000
#endif
#ifndef CONFIG_ENV_SPI_MODE
# define CONFIG_ENV_SPI_MODE SPI_MODE_3
#endif
static struct spi_flash *flash=NULL;
#elif !defined(CONFIG_SYS_NO_FLASH)
#include <flash.h>
extern flash_info_t flash_info[]; /* info for FLASH chips */
#endif
#include "zflash.h"
#ifdef CONFIG_CMD_NAND
#include <nand.h>
int znand_init(void)
{
/* TODO */
return 0;
}
int znand_read(unsigned long offs, unsigned long len, char *buf)
{
return nand_read_skip_bad(&nand_info[0], offs, &len, (u_char *)buf);
}
int znand_write(unsigned long offs, unsigned long len, char *buf)
{
return nand_write_skip_bad(&nand_info[0], offs, &len, (u_char *)buf);
}
int znand_erase(unsigned long offs, unsigned long len)
{
nand_erase_options_t opts;
opts.offset = offs;
opts.length = len;
opts.quiet = 0;
opts.jffs2 = 0;
opts.scrub = 0;
return nand_erase_opts(&nand_info[0], &opts);
}
#endif
int zflash_init(void)
{
#if defined(CONFIG_ENV_IS_IN_SPI_FLASH)
/* have SPI NOR flash */
if (flash==NULL) {
flash = spi_flash_probe(CONFIG_ENV_SPI_BUS, CONFIG_ENV_SPI_CS,
CONFIG_ENV_SPI_MAX_HZ, CONFIG_ENV_SPI_MODE);
if ( flash == NULL ) {
printf("!!! not found SPI flash !!!\n");
return -1;
}
}
#elif !defined(CONFIG_SYS_NO_FLASH)
/* have parallel NOR flash */
/* TODO */
#else
#error "Unknown NOR flash!"
#endif
return 0;
}
int zflash_read(unsigned long offs, unsigned long len, char *buf)
{
DECLARE_GLOBAL_DATA_PTR __maybe_unused;
if ( buf == NULL ) {
return -1;
}
#if defined(CONFIG_ENV_IS_IN_SPI_FLASH)
if (flash==NULL) {
return -2;
}
return flash->read(flash, offs, len, buf);
#elif !defined(CONFIG_SYS_NO_FLASH) /* parallel NOR flash */
if ( offs<CONFIG_SYS_FLASH_BASE || offs+len>(CONFIG_SYS_FLASH_BASE+gd->ram_size) ) {
return -3;
}
memcpy(buf, (void *)offs, len);
flush_cache((unsigned long)buf, len);
#endif
return 0;
}
int zflash_write(unsigned long offs, unsigned long len, char *buf)
{
if ( buf == NULL ) {
return -1;
}
#if defined(CONFIG_ENV_IS_IN_SPI_FLASH)
if (flash==NULL) {
return -2;
}
return flash->write(flash, offs, len, buf);
#elif !defined(CONFIG_SYS_NO_FLASH)
extern int flash_write (char *src, ulong addr, ulong cnt);
return flash_write (buf, offs, len);
#endif
return 0;
}
int zflash_erase(unsigned long offs, unsigned long len)
{
#if defined(CONFIG_ENV_IS_IN_SPI_FLASH) /* serial NOR flash */
if (flash==NULL) {
return -2;
}
return flash->erase(flash, offs, len);
#elif !defined(CONFIG_SYS_NO_FLASH) /* parallel NOR flash */
extern int flash_sect_erase (ulong addr_first, ulong addr_last);
return flash_sect_erase(offs, offs+len-1);
#endif
return 0;
}
#ifdef CONFIG_ZFLASH_CMD
#include <command.h>
static int do_zflash_cmd(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
{
if ( argc < 4 ) {
goto zflash_cmd_failed;
}
if (argc>=5 && !strncmp(argv[1], "read", 5)) {
unsigned long addr, offs, len;
addr = simple_strtoul(argv[2], NULL, 16);
offs = simple_strtoul(argv[3], NULL, 16);
len = simple_strtoul(argv[4], NULL, 16);
if ( zflash_read(offs, len, (char *)addr) ) return -1;
} else if (argc>=4 && !strncmp(argv[1], "erase", 6)) {
unsigned int o, l;
o = simple_strtoul(argv[2], NULL, 16);
l = simple_strtoul(argv[3], NULL, 16);
if ( zflash_erase(o, l) ) return -1;
} else if (argc>=5 && !strncmp(argv[1], "write", 6)) {
unsigned long addr, offs, len;
addr = simple_strtoul(argv[2], NULL, 16);
offs = simple_strtoul(argv[3], NULL, 16);
len = simple_strtoul(argv[4], NULL, 16);
if ( zflash_write(offs, len, (char *)addr) ) return -1;
} else {
zflash_cmd_failed:
#ifdef CONFIG_SYS_LONGHELP
printf("\nUsage:\n%s\n", cmdtp->help);
#else
printf("wrong syntax\n");
#endif
return -1;
}
return 0;
}
U_BOOT_CMD (
zflash, 5, 0, do_zflash_cmd,
"Flash access commands, length must be align to block/page size",
"erase <offs> <len> - erase flash\n"
"zflash read <addr> <offs> <len> - read data from flash to memory\n"
"zflash write <addr> <offs> <len> - write data from memory to flash\n"
" <addr>: memory address\n"
" <offs>: flash offset/address\n"
);
#endif