@ -42,8 +42,7 @@
DECLARE_GLOBAL_DATA_PTR ;
DECLARE_GLOBAL_DATA_PTR ;
static int fdt_valid ( void ) ;
static int fdt_valid ( void ) ;
static int fdt_parse_prop ( char * pathp , char * prop , char * newval ,
static int fdt_parse_prop ( char * * newval , int count , char * data , int * len ) ;
char * data , int * len ) ;
static int fdt_print ( const char * pathp , char * prop , int depth ) ;
static int fdt_print ( const char * pathp , char * prop , int depth ) ;
/*
/*
@ -202,7 +201,7 @@ int do_fdt (cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
if ( argc = = 4 ) {
if ( argc = = 4 ) {
len = 0 ;
len = 0 ;
} else {
} else {
ret = fdt_parse_prop ( pathp , prop , argv [ 4 ] , data , & len ) ;
ret = fdt_parse_prop ( & argv [ 4 ] , argc - 4 , data , & len ) ;
if ( ret ! = 0 )
if ( ret ! = 0 )
return ret ;
return ret ;
}
}
@ -464,69 +463,77 @@ static int fdt_valid(void)
/*
/*
* Parse the user ' s input , partially heuristic . Valid formats :
* Parse the user ' s input , partially heuristic . Valid formats :
* < 00 > - hex byte
* < 0x00112233 4 05 > - an array of cells . Numbers follow standard
* < 0011 > - hex half word ( 16 bits )
* C conventions .
* < 00112233 > - hex word ( 32 bits )
* - hex double words ( 64 bits ) are not supported , must use
* a byte stream instead .
* [ 00 11 22 . . nn ] - byte stream
* [ 00 11 22 . . nn ] - byte stream
* " string " - If the the value doesn ' t start with " < " or " [ " , it is
* " string " - If the the value doesn ' t start with " < " or " [ " , it is
* treated as a string . Note that the quotes are
* treated as a string . Note that the quotes are
* stripped by the parser before we get the string .
* stripped by the parser before we get the string .
* newval : An array of strings containing the new property as specified
* on the command line
* count : The number of strings in the array
* data : A bytestream to be placed in the property
* len : The length of the resulting bytestream
*/
*/
static int fdt_parse_prop ( char * pathp , char * prop , char * newval ,
static int fdt_parse_prop ( char * * newval , int count , char * data , int * len )
char * data , int * len )
{
{
char * cp ; /* temporary char pointer */
char * cp ; /* temporary char pointer */
char * newp ; /* temporary newval char pointer */
unsigned long tmp ; /* holds converted values */
unsigned long tmp ; /* holds converted values */
int stridx = 0 ;
if ( * newval = = ' < ' ) {
* len = 0 ;
/*
newp = newval [ 0 ] ;
* Bigger values than bytes .
*/
/* An array of cells */
* len = 0 ;
if ( * newp = = ' < ' ) {
newval + + ;
newp + + ;
while ( ( * newval ! = ' > ' ) & & ( * newval ! = ' \0 ' ) ) {
while ( ( * newp ! = ' > ' ) & & ( stridx < count ) ) {
cp = newval ;
/*
tmp = simple_strtoul ( cp , & newval , 16 ) ;
* Keep searching until we find that last " > "
if ( ( newval - cp ) < = 2 ) {
* That way users don ' t have to escape the spaces
* data = tmp & 0xFF ;
*/
data + = 1 ;
if ( * newp = = ' \0 ' ) {
* len + = 1 ;
newp = newval [ + + stridx ] ;
} else if ( ( newval - cp ) < = 4 ) {
continue ;
* ( uint16_t * ) data = __cpu_to_be16 ( tmp ) ;
}
data + = 2 ;
* len + = 2 ;
cp = newp ;
} else if ( ( newval - cp ) < = 8 ) {
tmp = simple_strtoul ( cp , & newp , 0 ) ;
* ( uint32_t * ) data = __cpu_to_be32 ( tmp ) ;
* ( uint32_t * ) data = __cpu_to_be32 ( tmp ) ;
data + = 4 ;
data + = 4 ;
* len + = 4 ;
* len + = 4 ;
} else {
/* If the ptr didn't advance, something went wrong */
if ( ( newp - cp ) < = 0 ) {
printf ( " Sorry, I could not convert \" %s \" \n " ,
printf ( " Sorry, I could not convert \" %s \" \n " ,
cp ) ;
cp ) ;
return 1 ;
return 1 ;
}
}
while ( * newval = = ' ' )
newval + + ;
while ( * newp = = ' ' )
newp + + ;
}
}
if ( * newval ! = ' > ' ) {
printf ( " Unexpected character '%c' \n " , * newval ) ;
if ( * newp ! = ' > ' ) {
printf ( " Unexpected character '%c' \n " , * newp ) ;
return 1 ;
return 1 ;
}
}
} else if ( * newval = = ' [ ' ) {
} else if ( * newp = = ' [ ' ) {
/*
/*
* Byte stream . Convert the values .
* Byte stream . Convert the values .
*/
*/
* len = 0 ;
newp + + ;
newval + + ;
while ( ( * newp ! = ' ] ' ) & & ( stridx < count ) ) {
while ( ( * newval ! = ' ] ' ) & & ( * newval ! = ' \0 ' ) ) {
tmp = simple_strtoul ( newp , & newp , 16 ) ;
tmp = simple_strtoul ( newval , & newval , 16 ) ;
* data + + = tmp & 0xFF ;
* data + + = tmp & 0xFF ;
* len = * len + 1 ;
* len = * len + 1 ;
while ( * newval = = ' ' )
while ( * newp = = ' ' )
newval + + ;
newp + + ;
if ( * newp ! = ' \0 ' )
newp = newval [ + + stridx ] ;
}
}
if ( * newval ! = ' ] ' ) {
if ( * newp ! = ' ] ' ) {
printf ( " Unexpected character '%c' \n " , * newval ) ;
printf ( " Unexpected character '%c' \n " , * newval ) ;
return 1 ;
return 1 ;
}
}
@ -535,8 +542,11 @@ static int fdt_parse_prop(char *pathp, char *prop, char *newval,
* Assume it is a string . Copy it into our data area for
* Assume it is a string . Copy it into our data area for
* convenience ( including the terminating ' \0 ' ) .
* convenience ( including the terminating ' \0 ' ) .
*/
*/
* len = strlen ( newval ) + 1 ;
while ( stridx < count ) {
strcpy ( data , newval ) ;
* len = strlen ( newp ) + 1 ;
strcpy ( data , newp ) ;
newp = newval [ + + stridx ] ;
}
}
}
return 0 ;
return 0 ;
}
}
@ -593,7 +603,6 @@ static int is_printable_string(const void *data, int len)
static void print_data ( const void * data , int len )
static void print_data ( const void * data , int len )
{
{
int j ;
int j ;
const u8 * s ;
/* no data, don't print */
/* no data, don't print */
if ( len = = 0 )
if ( len = = 0 )
@ -616,32 +625,20 @@ static void print_data(const void *data, int len)
return ;
return ;
}
}
switch ( len ) {
if ( ( len % 4 ) = = 0 ) {
case 1 : /* byte */
const u32 * p ;
printf ( " <0x%02x> " , ( * ( u8 * ) data ) & 0xff ) ;
break ;
printf ( " < " ) ;
case 2 : /* half-word */
for ( j = 0 , p = data ; j < len / 4 ; j + + )
printf ( " <0x%04x> " , be16_to_cpu ( * ( u16 * ) data ) & 0xffff ) ;
printf ( " 0x%x%s " , p [ j ] , j < ( len / 4 - 1 ) ? " " : " " ) ;
break ;
printf ( " > " ) ;
case 4 : /* word */
} else { /* anything else... hexdump */
printf ( " <0x%08x> " , be32_to_cpu ( * ( u32 * ) data ) & 0xffffffffU ) ;
const u8 * s ;
break ;
case 8 : /* double-word */
# if __WORDSIZE == 64
printf ( " <0x%016llx> " , be64_to_cpu ( * ( uint64_t * ) data ) ) ;
# else
printf ( " <0x%08x " , be32_to_cpu ( * ( u32 * ) data ) & 0xffffffffU ) ;
data + = 4 ;
printf ( " 0x%08x> " , be32_to_cpu ( * ( u32 * ) data ) & 0xffffffffU ) ;
# endif
break ;
default : /* anything else... hexdump */
printf ( " [ " ) ;
printf ( " [ " ) ;
for ( j = 0 , s = data ; j < len ; j + + )
for ( j = 0 , s = data ; j < len ; j + + )
printf ( " %02x%s " , s [ j ] , j < len - 1 ? " " : " " ) ;
printf ( " %02x%s " , s [ j ] , j < len - 1 ? " " : " " ) ;
printf ( " ] " ) ;
printf ( " ] " ) ;
break ;
}
}
}
}
@ -771,7 +768,7 @@ static int fdt_print(const char *pathp, char *prop, int depth)
/********************************************************************/
/********************************************************************/
U_BOOT_CMD (
U_BOOT_CMD (
fdt , 5 , 0 , do_fdt ,
fdt , 25 5, 0 , do_fdt ,
" fdt - flattened device tree utility commands \n " ,
" fdt - flattened device tree utility commands \n " ,
" addr <addr> [<length>] - Set the fdt location to <addr> \n "
" addr <addr> [<length>] - Set the fdt location to <addr> \n "
# ifdef CONFIG_OF_BOARD_SETUP
# ifdef CONFIG_OF_BOARD_SETUP