Merge branch 'next'
This commit is contained in:
@@ -31,7 +31,7 @@ DECLARE_GLOBAL_DATA_PTR;
|
||||
|
||||
static void print_num(const char *, ulong);
|
||||
|
||||
#if !defined(CONFIG_ARM) || defined(CONFIG_CMD_NET)
|
||||
#if !(defined(CONFIG_ARM) || defined(CONFIG_M68K)) || defined(CONFIG_CMD_NET)
|
||||
static void print_eth(int idx);
|
||||
#endif
|
||||
|
||||
@@ -350,7 +350,7 @@ static void print_num(const char *name, ulong value)
|
||||
printf ("%-12s= 0x%08lX\n", name, value);
|
||||
}
|
||||
|
||||
#if !defined(CONFIG_ARM) || defined(CONFIG_CMD_NET)
|
||||
#if !(defined(CONFIG_ARM) || defined(CONFIG_M68K)) || defined(CONFIG_CMD_NET)
|
||||
static void print_eth(int idx)
|
||||
{
|
||||
char name[10], *val;
|
||||
|
||||
@@ -463,7 +463,7 @@ static int bootm_start_standalone(ulong iflag, int argc, char *argv[])
|
||||
|
||||
/* we overload the cmd field with our state machine info instead of a
|
||||
* function pointer */
|
||||
cmd_tbl_t cmd_bootm_sub[] = {
|
||||
static cmd_tbl_t cmd_bootm_sub[] = {
|
||||
U_BOOT_CMD_MKENT(start, 0, 1, (void *)BOOTM_STATE_START, "", ""),
|
||||
U_BOOT_CMD_MKENT(loados, 0, 1, (void *)BOOTM_STATE_LOADOS, "", ""),
|
||||
#if defined(CONFIG_PPC) || defined(CONFIG_M68K) || defined(CONFIG_SPARC)
|
||||
|
||||
271
common/cmd_i2c.c
271
common/cmd_i2c.c
@@ -130,6 +130,8 @@ DECLARE_GLOBAL_DATA_PTR;
|
||||
|
||||
#endif
|
||||
|
||||
#define DISP_LINE_LEN 16
|
||||
|
||||
/* TODO: Implement architecture-specific get/set functions */
|
||||
unsigned int __def_i2c_get_bus_speed(void)
|
||||
{
|
||||
@@ -148,13 +150,83 @@ int __def_i2c_set_bus_speed(unsigned int speed)
|
||||
int i2c_set_bus_speed(unsigned int)
|
||||
__attribute__((weak, alias("__def_i2c_set_bus_speed")));
|
||||
|
||||
/*
|
||||
* get_alen: small parser helper function to get address length
|
||||
* returns the address length,or 0 on error
|
||||
*/
|
||||
static uint get_alen(char *arg)
|
||||
{
|
||||
int j;
|
||||
int alen;
|
||||
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (arg[j] == '.') {
|
||||
alen = arg[j+1] - '0';
|
||||
if (alen > 3) {
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
} else if (arg[j] == '\0')
|
||||
break;
|
||||
}
|
||||
return alen;
|
||||
}
|
||||
|
||||
/*
|
||||
* Syntax:
|
||||
* i2c read {i2c_chip} {devaddr}{.0, .1, .2} {len} {memaddr}
|
||||
*/
|
||||
|
||||
static int do_i2c_read ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
u_char chip;
|
||||
uint devaddr, alen, length;
|
||||
u_char *memaddr;
|
||||
|
||||
if (argc != 5) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* I2C chip address
|
||||
*/
|
||||
chip = simple_strtoul(argv[1], NULL, 16);
|
||||
|
||||
/*
|
||||
* I2C data address within the chip. This can be 1 or
|
||||
* 2 bytes long. Some day it might be 3 bytes long :-).
|
||||
*/
|
||||
devaddr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Length is the number of objects, not number of bytes.
|
||||
*/
|
||||
length = simple_strtoul(argv[3], NULL, 16);
|
||||
|
||||
/*
|
||||
* memaddr is the address where to store things in memory
|
||||
*/
|
||||
memaddr = (u_char *)simple_strtoul(argv[4], NULL, 16);
|
||||
|
||||
if (i2c_read(chip, devaddr, alen, memaddr, length) != 0) {
|
||||
puts ("Error reading the chip.\n");
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Syntax:
|
||||
* i2c md {i2c_chip} {addr}{.0, .1, .2} {len}
|
||||
*/
|
||||
#define DISP_LINE_LEN 16
|
||||
|
||||
int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
u_char chip;
|
||||
uint addr, alen, length;
|
||||
@@ -177,7 +249,6 @@ int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
/*
|
||||
* New command specified.
|
||||
*/
|
||||
alen = 1;
|
||||
|
||||
/*
|
||||
* I2C chip address
|
||||
@@ -189,17 +260,10 @@ int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* 2 bytes long. Some day it might be 3 bytes long :-).
|
||||
*/
|
||||
addr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (argv[2][j] == '.') {
|
||||
alen = argv[2][j+1] - '0';
|
||||
if (alen > 4) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
} else if (argv[2][j] == '\0')
|
||||
break;
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -260,14 +324,13 @@ int do_i2c_md ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* Syntax:
|
||||
* i2c mw {i2c_chip} {addr}{.0, .1, .2} {data} [{count}]
|
||||
*/
|
||||
int do_i2c_mw ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_mw ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
uchar chip;
|
||||
ulong addr;
|
||||
uint alen;
|
||||
uchar byte;
|
||||
int count;
|
||||
int j;
|
||||
|
||||
if ((argc < 4) || (argc > 5)) {
|
||||
cmd_usage(cmdtp);
|
||||
@@ -283,17 +346,10 @@ int do_i2c_mw ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* Address is always specified.
|
||||
*/
|
||||
addr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (argv[2][j] == '.') {
|
||||
alen = argv[2][j+1] - '0';
|
||||
if (alen > 4) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
} else if (argv[2][j] == '\0')
|
||||
break;
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -332,7 +388,7 @@ int do_i2c_mw ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* Syntax:
|
||||
* i2c crc32 {i2c_chip} {addr}{.0, .1, .2} {count}
|
||||
*/
|
||||
int do_i2c_crc (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_crc (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
uchar chip;
|
||||
ulong addr;
|
||||
@@ -341,7 +397,6 @@ int do_i2c_crc (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
uchar byte;
|
||||
ulong crc;
|
||||
ulong err;
|
||||
int j;
|
||||
|
||||
if (argc < 4) {
|
||||
cmd_usage(cmdtp);
|
||||
@@ -357,17 +412,10 @@ int do_i2c_crc (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* Address is always specified.
|
||||
*/
|
||||
addr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (argv[2][j] == '.') {
|
||||
alen = argv[2][j+1] - '0';
|
||||
if (alen > 4) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
} else if (argv[2][j] == '\0')
|
||||
break;
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -412,7 +460,6 @@ mod_i2c_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char *argv[])
|
||||
ulong data;
|
||||
int size = 1;
|
||||
int nbytes;
|
||||
int j;
|
||||
extern char console_buffer[];
|
||||
|
||||
if (argc != 3) {
|
||||
@@ -447,17 +494,10 @@ mod_i2c_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char *argv[])
|
||||
* Address is always specified.
|
||||
*/
|
||||
addr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (argv[2][j] == '.') {
|
||||
alen = argv[2][j+1] - '0';
|
||||
if (alen > 4) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
} else if (argv[2][j] == '\0')
|
||||
break;
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -535,7 +575,7 @@ mod_i2c_mem(cmd_tbl_t *cmdtp, int incrflag, int flag, int argc, char *argv[])
|
||||
* Syntax:
|
||||
* i2c probe {addr}{.0, .1, .2}
|
||||
*/
|
||||
int do_i2c_probe (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_probe (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
int j;
|
||||
#if defined(CONFIG_SYS_I2C_NOPROBES)
|
||||
@@ -579,7 +619,7 @@ int do_i2c_probe (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* {length} - Number of bytes to read
|
||||
* {delay} - A DECIMAL number and defaults to 1000 uSec
|
||||
*/
|
||||
int do_i2c_loop(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_loop(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
u_char chip;
|
||||
ulong alen;
|
||||
@@ -587,7 +627,6 @@ int do_i2c_loop(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
uint length;
|
||||
u_char bytes[16];
|
||||
int delay;
|
||||
int j;
|
||||
|
||||
if (argc < 3) {
|
||||
cmd_usage(cmdtp);
|
||||
@@ -603,17 +642,10 @@ int do_i2c_loop(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
* Address is always specified.
|
||||
*/
|
||||
addr = simple_strtoul(argv[2], NULL, 16);
|
||||
alen = 1;
|
||||
for (j = 0; j < 8; j++) {
|
||||
if (argv[2][j] == '.') {
|
||||
alen = argv[2][j+1] - '0';
|
||||
if (alen > 4) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
break;
|
||||
} else if (argv[2][j] == '\0')
|
||||
break;
|
||||
alen = get_alen(argv[2]);
|
||||
if (alen == 0) {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -699,7 +731,7 @@ static void decode_bits (u_char const b, char const *str[], int const do_once)
|
||||
* Syntax:
|
||||
* i2c sdram {i2c_chip}
|
||||
*/
|
||||
int do_sdram (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_sdram (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
enum { unknown, EDO, SDRAM, DDR2 } type;
|
||||
|
||||
@@ -1176,7 +1208,7 @@ int do_sdram (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_I2C_MUX)
|
||||
int do_i2c_add_bus(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_add_bus(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
int ret=0;
|
||||
|
||||
@@ -1207,7 +1239,7 @@ int do_i2c_add_bus(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
#endif /* CONFIG_I2C_MUX */
|
||||
|
||||
#if defined(CONFIG_I2C_MULTI_BUS)
|
||||
int do_i2c_bus_num(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_bus_num(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
int bus_idx, ret=0;
|
||||
|
||||
@@ -1225,7 +1257,7 @@ int do_i2c_bus_num(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
}
|
||||
#endif /* CONFIG_I2C_MULTI_BUS */
|
||||
|
||||
int do_i2c_bus_speed(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_bus_speed(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
int speed, ret=0;
|
||||
|
||||
@@ -1242,46 +1274,60 @@ int do_i2c_bus_speed(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
return ret;
|
||||
}
|
||||
|
||||
int do_i2c(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
static int do_i2c_mm(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
return mod_i2c_mem (cmdtp, 1, flag, argc, argv);
|
||||
}
|
||||
|
||||
static int do_i2c_nm(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
return mod_i2c_mem (cmdtp, 0, flag, argc, argv);
|
||||
}
|
||||
|
||||
static int do_i2c_reset(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static cmd_tbl_t cmd_i2c_sub[] = {
|
||||
#if defined(CONFIG_I2C_MUX)
|
||||
U_BOOT_CMD_MKENT(bus, 1, 1, do_i2c_add_bus, "", ""),
|
||||
#endif /* CONFIG_I2C_MUX */
|
||||
U_BOOT_CMD_MKENT(crc32, 3, 1, do_i2c_crc, "", ""),
|
||||
#if defined(CONFIG_I2C_MULTI_BUS)
|
||||
U_BOOT_CMD_MKENT(dev, 1, 1, do_i2c_bus_num, "", ""),
|
||||
#endif /* CONFIG_I2C_MULTI_BUS */
|
||||
U_BOOT_CMD_MKENT(loop, 3, 1, do_i2c_loop, "", ""),
|
||||
U_BOOT_CMD_MKENT(md, 3, 1, do_i2c_md, "", ""),
|
||||
U_BOOT_CMD_MKENT(mm, 2, 1, do_i2c_mm, "", ""),
|
||||
U_BOOT_CMD_MKENT(mw, 3, 1, do_i2c_mw, "", ""),
|
||||
U_BOOT_CMD_MKENT(nm, 2, 1, do_i2c_nm, "", ""),
|
||||
U_BOOT_CMD_MKENT(probe, 0, 1, do_i2c_probe, "", ""),
|
||||
U_BOOT_CMD_MKENT(read, 5, 1, do_i2c_read, "", ""),
|
||||
U_BOOT_CMD_MKENT(reset, 0, 1, do_i2c_reset, "", ""),
|
||||
#if defined(CONFIG_CMD_SDRAM)
|
||||
U_BOOT_CMD_MKENT(sdram, 1, 1, do_sdram, "", ""),
|
||||
#endif
|
||||
U_BOOT_CMD_MKENT(speed, 1, 1, do_i2c_bus_speed, "", ""),
|
||||
};
|
||||
|
||||
static int do_i2c(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
cmd_tbl_t *c;
|
||||
|
||||
/* Strip off leading 'i2c' command argument */
|
||||
argc--;
|
||||
argv++;
|
||||
|
||||
#if defined(CONFIG_I2C_MUX)
|
||||
if (!strncmp(argv[0], "bu", 2))
|
||||
return do_i2c_add_bus(cmdtp, flag, argc, argv);
|
||||
#endif /* CONFIG_I2C_MUX */
|
||||
if (!strncmp(argv[0], "sp", 2))
|
||||
return do_i2c_bus_speed(cmdtp, flag, argc, argv);
|
||||
#if defined(CONFIG_I2C_MULTI_BUS)
|
||||
if (!strncmp(argv[0], "de", 2))
|
||||
return do_i2c_bus_num(cmdtp, flag, argc, argv);
|
||||
#endif /* CONFIG_I2C_MULTI_BUS */
|
||||
if (!strncmp(argv[0], "md", 2))
|
||||
return do_i2c_md(cmdtp, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "mm", 2))
|
||||
return mod_i2c_mem (cmdtp, 1, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "mw", 2))
|
||||
return do_i2c_mw(cmdtp, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "nm", 2))
|
||||
return mod_i2c_mem (cmdtp, 0, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "cr", 2))
|
||||
return do_i2c_crc(cmdtp, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "pr", 2))
|
||||
return do_i2c_probe(cmdtp, flag, argc, argv);
|
||||
if (!strncmp(argv[0], "re", 2)) {
|
||||
i2c_init(CONFIG_SYS_I2C_SPEED, CONFIG_SYS_I2C_SLAVE);
|
||||
return 0;
|
||||
c = find_cmd_tbl(argv[0], &cmd_i2c_sub[0], ARRAY_SIZE(cmd_i2c_sub));
|
||||
|
||||
if (c) {
|
||||
return c->cmd(cmdtp, flag, argc, argv);
|
||||
} else {
|
||||
cmd_usage(cmdtp);
|
||||
return 1;
|
||||
}
|
||||
if (!strncmp(argv[0], "lo", 2))
|
||||
return do_i2c_loop(cmdtp, flag, argc, argv);
|
||||
#if defined(CONFIG_CMD_SDRAM)
|
||||
if (!strncmp(argv[0], "sd", 2))
|
||||
return do_sdram(cmdtp, flag, argc, argv);
|
||||
#endif
|
||||
cmd_usage(cmdtp);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/***************************************************/
|
||||
@@ -1289,30 +1335,29 @@ int do_i2c(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
U_BOOT_CMD(
|
||||
i2c, 6, 1, do_i2c,
|
||||
"I2C sub-system",
|
||||
"speed [speed] - show or set I2C bus speed\n"
|
||||
#if defined(CONFIG_I2C_MUX)
|
||||
"i2c bus [muxtype:muxaddr:muxchannel] - add a new bus reached over muxes\n"
|
||||
"bus [muxtype:muxaddr:muxchannel] - add a new bus reached over muxes\ni2c "
|
||||
#endif /* CONFIG_I2C_MUX */
|
||||
"crc32 chip address[.0, .1, .2] count - compute CRC32 checksum\n"
|
||||
#if defined(CONFIG_I2C_MULTI_BUS)
|
||||
"i2c dev [dev] - show or set current I2C bus\n"
|
||||
#endif /* CONFIG_I2C_MULTI_BUS */
|
||||
"i2c loop chip address[.0, .1, .2] [# of objects] - looping read of device\n"
|
||||
"i2c md chip address[.0, .1, .2] [# of objects] - read from I2C device\n"
|
||||
"i2c mm chip address[.0, .1, .2] - write to I2C device (auto-incrementing)\n"
|
||||
"i2c mw chip address[.0, .1, .2] value [count] - write to I2C device (fill)\n"
|
||||
"i2c nm chip address[.0, .1, .2] - write to I2C device (constant address)\n"
|
||||
"i2c crc32 chip address[.0, .1, .2] count - compute CRC32 checksum\n"
|
||||
"i2c probe - show devices on the I2C bus\n"
|
||||
"i2c read chip address[.0, .1, .2] length memaddress - read to memory \n"
|
||||
"i2c reset - re-init the I2C Controller\n"
|
||||
"i2c loop chip address[.0, .1, .2] [# of objects] - looping read of device"
|
||||
#if defined(CONFIG_CMD_SDRAM)
|
||||
"\n"
|
||||
"i2c sdram chip - print SDRAM configuration information"
|
||||
"i2c sdram chip - print SDRAM configuration information\n"
|
||||
#endif
|
||||
"i2c speed [speed] - show or set I2C bus speed"
|
||||
);
|
||||
|
||||
#if defined(CONFIG_I2C_MUX)
|
||||
|
||||
int i2c_mux_add_device(I2C_MUX_DEVICE *dev)
|
||||
static int i2c_mux_add_device(I2C_MUX_DEVICE *dev)
|
||||
{
|
||||
I2C_MUX_DEVICE *devtmp = i2c_mux_devices;
|
||||
|
||||
|
||||
@@ -776,7 +776,7 @@ static int device_del(struct mtd_device *dev)
|
||||
* @param num device number
|
||||
* @return NULL if requested device does not exist
|
||||
*/
|
||||
static struct mtd_device* device_find(u8 type, u8 num)
|
||||
struct mtd_device *device_find(u8 type, u8 num)
|
||||
{
|
||||
struct list_head *entry;
|
||||
struct mtd_device *dev_tmp;
|
||||
|
||||
@@ -327,8 +327,14 @@ int do_nand(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
|
||||
"are sure of what you are doing!\n"
|
||||
"\nReally scrub this NAND flash? <y/N>\n");
|
||||
|
||||
if (getc() == 'y' && getc() == '\r') {
|
||||
opts.scrub = 1;
|
||||
if (getc() == 'y') {
|
||||
puts("y");
|
||||
if (getc() == '\r')
|
||||
opts.scrub = 1;
|
||||
else {
|
||||
puts("scrub aborted\n");
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
puts("scrub aborted\n");
|
||||
return -1;
|
||||
|
||||
@@ -28,10 +28,33 @@
|
||||
#include <config.h>
|
||||
#include <command.h>
|
||||
|
||||
static ulong get_arg(char *s, int w)
|
||||
{
|
||||
ulong *p;
|
||||
|
||||
/*
|
||||
* if the parameter starts with a '*' then assume
|
||||
* it is a pointer to the value we want
|
||||
*/
|
||||
|
||||
if (s[0] == '*') {
|
||||
p = (ulong *)simple_strtoul(&s[1], NULL, 16);
|
||||
switch (w) {
|
||||
case 1: return((ulong)(*(uchar *)p));
|
||||
case 2: return((ulong)(*(ushort *)p));
|
||||
case 4:
|
||||
default: return(*p);
|
||||
}
|
||||
} else {
|
||||
return simple_strtoul(s, NULL, 16);
|
||||
}
|
||||
}
|
||||
|
||||
int do_setexpr(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
{
|
||||
ulong a, b;
|
||||
char buf[16];
|
||||
int w;
|
||||
|
||||
/* Validate arguments */
|
||||
if ((argc != 5) || (strlen(argv[3]) != 1)) {
|
||||
@@ -39,8 +62,10 @@ int do_setexpr(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
return 1;
|
||||
}
|
||||
|
||||
a = simple_strtoul(argv[2], NULL, 16);
|
||||
b = simple_strtoul(argv[4], NULL, 16);
|
||||
w = cmd_get_data_size(argv[0], 4);
|
||||
|
||||
a = get_arg(argv[2], w);
|
||||
b = get_arg(argv[4], w);
|
||||
|
||||
switch (argv[3][0]) {
|
||||
case '|': sprintf(buf, "%lx", (a | b)); break;
|
||||
@@ -64,7 +89,8 @@ int do_setexpr(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
|
||||
U_BOOT_CMD(
|
||||
setexpr, 5, 0, do_setexpr,
|
||||
"set environment variable as the result of eval expression",
|
||||
"name value1 <op> value2\n"
|
||||
"[.b, .w, .l] name value1 <op> value2\n"
|
||||
" - set environment variable 'name' to the result of the evaluated\n"
|
||||
" express specified by <op>. <op> can be &, |, ^, +, -, *, /, %"
|
||||
" express specified by <op>. <op> can be &, |, ^, +, -, *, /, %\n"
|
||||
" size argument is only meaningful if value1 and/or value2 are memory addresses"
|
||||
);
|
||||
|
||||
@@ -757,3 +757,222 @@ int fdt_fixup_nor_flash_size(void *blob, int cs, u32 size)
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_FDT_FIXUP_PARTITIONS
|
||||
#include <jffs2/load_kernel.h>
|
||||
#include <mtd_node.h>
|
||||
|
||||
struct reg_cell {
|
||||
unsigned int r0;
|
||||
unsigned int r1;
|
||||
};
|
||||
|
||||
int fdt_del_subnodes(const void *blob, int parent_offset)
|
||||
{
|
||||
int off, ndepth;
|
||||
int ret;
|
||||
|
||||
for (ndepth = 0, off = fdt_next_node(blob, parent_offset, &ndepth);
|
||||
(off >= 0) && (ndepth > 0);
|
||||
off = fdt_next_node(blob, off, &ndepth)) {
|
||||
if (ndepth == 1) {
|
||||
debug("delete %s: offset: %x\n",
|
||||
fdt_get_name(blob, off, 0), off);
|
||||
ret = fdt_del_node((void *)blob, off);
|
||||
if (ret < 0) {
|
||||
printf("Can't delete node: %s\n",
|
||||
fdt_strerror(ret));
|
||||
return ret;
|
||||
} else {
|
||||
ndepth = 0;
|
||||
off = parent_offset;
|
||||
}
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int fdt_increase_size(void *fdt, int add_len)
|
||||
{
|
||||
int newlen;
|
||||
|
||||
newlen = fdt_totalsize(fdt) + add_len;
|
||||
|
||||
/* Open in place with a new len */
|
||||
return fdt_open_into(fdt, fdt, newlen);
|
||||
}
|
||||
|
||||
int fdt_del_partitions(void *blob, int parent_offset)
|
||||
{
|
||||
const void *prop;
|
||||
int ndepth = 0;
|
||||
int off;
|
||||
int ret;
|
||||
|
||||
off = fdt_next_node(blob, parent_offset, &ndepth);
|
||||
if (off > 0 && ndepth == 1) {
|
||||
prop = fdt_getprop(blob, off, "label", NULL);
|
||||
if (prop == NULL) {
|
||||
/*
|
||||
* Could not find label property, nand {}; node?
|
||||
* Check subnode, delete partitions there if any.
|
||||
*/
|
||||
return fdt_del_partitions(blob, off);
|
||||
} else {
|
||||
ret = fdt_del_subnodes(blob, parent_offset);
|
||||
if (ret < 0) {
|
||||
printf("Can't remove subnodes: %s\n",
|
||||
fdt_strerror(ret));
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int fdt_node_set_part_info(void *blob, int parent_offset,
|
||||
struct mtd_device *dev)
|
||||
{
|
||||
struct list_head *pentry;
|
||||
struct part_info *part;
|
||||
struct reg_cell cell;
|
||||
int off, ndepth = 0;
|
||||
int part_num, ret;
|
||||
char buf[64];
|
||||
|
||||
ret = fdt_del_partitions(blob, parent_offset);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
/*
|
||||
* Check if it is nand {}; subnode, adjust
|
||||
* the offset in this case
|
||||
*/
|
||||
off = fdt_next_node(blob, parent_offset, &ndepth);
|
||||
if (off > 0 && ndepth == 1)
|
||||
parent_offset = off;
|
||||
|
||||
part_num = 0;
|
||||
list_for_each_prev(pentry, &dev->parts) {
|
||||
int newoff;
|
||||
|
||||
part = list_entry(pentry, struct part_info, link);
|
||||
|
||||
debug("%2d: %-20s0x%08x\t0x%08x\t%d\n",
|
||||
part_num, part->name, part->size,
|
||||
part->offset, part->mask_flags);
|
||||
|
||||
sprintf(buf, "partition@%x", part->offset);
|
||||
add_sub:
|
||||
ret = fdt_add_subnode(blob, parent_offset, buf);
|
||||
if (ret == -FDT_ERR_NOSPACE) {
|
||||
ret = fdt_increase_size(blob, 512);
|
||||
if (!ret)
|
||||
goto add_sub;
|
||||
else
|
||||
goto err_size;
|
||||
} else if (ret < 0) {
|
||||
printf("Can't add partition node: %s\n",
|
||||
fdt_strerror(ret));
|
||||
return ret;
|
||||
}
|
||||
newoff = ret;
|
||||
|
||||
/* Check MTD_WRITEABLE_CMD flag */
|
||||
if (part->mask_flags & 1) {
|
||||
add_ro:
|
||||
ret = fdt_setprop(blob, newoff, "read_only", NULL, 0);
|
||||
if (ret == -FDT_ERR_NOSPACE) {
|
||||
ret = fdt_increase_size(blob, 512);
|
||||
if (!ret)
|
||||
goto add_ro;
|
||||
else
|
||||
goto err_size;
|
||||
} else if (ret < 0)
|
||||
goto err_prop;
|
||||
}
|
||||
|
||||
cell.r0 = cpu_to_fdt32(part->offset);
|
||||
cell.r1 = cpu_to_fdt32(part->size);
|
||||
add_reg:
|
||||
ret = fdt_setprop(blob, newoff, "reg", &cell, sizeof(cell));
|
||||
if (ret == -FDT_ERR_NOSPACE) {
|
||||
ret = fdt_increase_size(blob, 512);
|
||||
if (!ret)
|
||||
goto add_reg;
|
||||
else
|
||||
goto err_size;
|
||||
} else if (ret < 0)
|
||||
goto err_prop;
|
||||
|
||||
add_label:
|
||||
ret = fdt_setprop_string(blob, newoff, "label", part->name);
|
||||
if (ret == -FDT_ERR_NOSPACE) {
|
||||
ret = fdt_increase_size(blob, 512);
|
||||
if (!ret)
|
||||
goto add_label;
|
||||
else
|
||||
goto err_size;
|
||||
} else if (ret < 0)
|
||||
goto err_prop;
|
||||
|
||||
part_num++;
|
||||
}
|
||||
return 0;
|
||||
err_size:
|
||||
printf("Can't increase blob size: %s\n", fdt_strerror(ret));
|
||||
return ret;
|
||||
err_prop:
|
||||
printf("Can't add property: %s\n", fdt_strerror(ret));
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* Update partitions in nor/nand nodes using info from
|
||||
* mtdparts environment variable. The nodes to update are
|
||||
* specified by node_info structure which contains mtd device
|
||||
* type and compatible string: E. g. the board code in
|
||||
* ft_board_setup() could use:
|
||||
*
|
||||
* struct node_info nodes[] = {
|
||||
* { "fsl,mpc5121-nfc", MTD_DEV_TYPE_NAND, },
|
||||
* { "cfi-flash", MTD_DEV_TYPE_NOR, },
|
||||
* };
|
||||
*
|
||||
* fdt_fixup_mtdparts(blob, nodes, ARRAY_SIZE(nodes));
|
||||
*/
|
||||
void fdt_fixup_mtdparts(void *blob, void *node_info, int node_info_size)
|
||||
{
|
||||
struct node_info *ni = node_info;
|
||||
struct mtd_device *dev;
|
||||
char *parts;
|
||||
int i, idx;
|
||||
int noff;
|
||||
|
||||
parts = getenv("mtdparts");
|
||||
if (!parts)
|
||||
return;
|
||||
|
||||
if (mtdparts_init() != 0)
|
||||
return;
|
||||
|
||||
for (i = 0; i < node_info_size; i++) {
|
||||
idx = 0;
|
||||
noff = fdt_node_offset_by_compatible(blob, -1, ni[i].compat);
|
||||
while (noff != -FDT_ERR_NOTFOUND) {
|
||||
debug("%s: %s, mtd dev type %d\n",
|
||||
fdt_get_name(blob, noff, 0),
|
||||
ni[i].compat, ni[i].type);
|
||||
dev = device_find(ni[i].type, idx++);
|
||||
if (dev) {
|
||||
if (fdt_node_set_part_info(blob, noff, dev))
|
||||
return; /* return on error */
|
||||
}
|
||||
|
||||
/* Jump to next flash node */
|
||||
noff = fdt_node_offset_by_compatible(blob, noff,
|
||||
ni[i].compat);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -68,7 +68,7 @@ static int abortboot(int);
|
||||
|
||||
#undef DEBUG_PARSER
|
||||
|
||||
char console_buffer[CONFIG_SYS_CBSIZE]; /* console I/O buffer */
|
||||
char console_buffer[CONFIG_SYS_CBSIZE + 1]; /* console I/O buffer */
|
||||
|
||||
static char * delete_char (char *buffer, char *p, int *colp, int *np, int plen);
|
||||
static char erase_seq[] = "\b \b"; /* erase sequence */
|
||||
@@ -526,7 +526,7 @@ void reset_cmd_timeout(void)
|
||||
|
||||
#define CTL_CH(c) ((c) - 'a' + 1)
|
||||
|
||||
#define MAX_CMDBUF_SIZE 256
|
||||
#define MAX_CMDBUF_SIZE CONFIG_SYS_CBSIZE
|
||||
|
||||
#define CTL_BACKSPACE ('\b')
|
||||
#define DEL ((char)255)
|
||||
@@ -546,7 +546,7 @@ static int hist_cur = -1;
|
||||
unsigned hist_num = 0;
|
||||
|
||||
char* hist_list[HIST_MAX];
|
||||
char hist_lines[HIST_MAX][HIST_SIZE];
|
||||
char hist_lines[HIST_MAX][HIST_SIZE + 1]; /* Save room for NULL */
|
||||
|
||||
#define add_idx_minus_one() ((hist_add_idx == 0) ? hist_max : hist_add_idx-1)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user