diff options
Diffstat (limited to 'main/common/struct.c')
-rw-r--r-- | main/common/struct.c | 1303 |
1 files changed, 681 insertions, 622 deletions
diff --git a/main/common/struct.c b/main/common/struct.c index 5a60a3c..745d3fd 100644 --- a/main/common/struct.c +++ b/main/common/struct.c @@ -1,7 +1,7 @@ /************************************************************************** * * Copyright (c) 2013 Alcatel-Lucent - * + * * Alcatel Lucent licenses this file to You under the Apache License, * Version 2.0 (the "License"); you may not use this file except in * compliance with the License. A copy of the License is contained the @@ -21,7 +21,7 @@ * struct.c: * * This command allows the user to build a structure into memory based - * on a structure set up in the definition file ("structfile"). + * on a structure set up in the definition file ("structfile"). * * Original author: Ed Sutter (ed.sutter@alcatel-lucent.com) * @@ -38,22 +38,22 @@ #if INCLUDE_STRUCT -#define OPENBRACE '{' -#define CLOSEBRACE '}' -#define PTRSIZE 4 +#define OPENBRACE '{' +#define CLOSEBRACE '}' +#define PTRSIZE 4 int structsize(char *name); struct mbrtype { - char *type; - int size; + char *type; + int size; }; struct mbrtype types[] = { - { "long", 4 }, - { "short", 2 }, - { "char", 1 }, - { 0, -1 } + { "long", 4 }, + { "short", 2 }, + { "char", 1 }, + { 0, -1 } }; static int struct_sfd; @@ -68,42 +68,43 @@ static char struct_scriptisstructfile; static void err_general(int errnum,int linenum, long tfsloc) { - printf("%s: err%d at ln %d\n",struct_fname,errnum,linenum); - tfsseek(struct_sfd,tfsloc,TFS_BEGIN); + printf("%s: err%d at ln %d\n",struct_fname,errnum,linenum); + tfsseek(struct_sfd,tfsloc,TFS_BEGIN); } static void err_nostruct(char *structname, long tfsloc) { - printf("%s: can't find struct '%s'\n",struct_fname,structname); - tfsseek(struct_sfd,tfsloc,TFS_BEGIN); + printf("%s: can't find struct '%s'\n",struct_fname,structname); + tfsseek(struct_sfd,tfsloc,TFS_BEGIN); } static void err_nomember(char *structname, char *mbrname, long tfsloc) { - printf("%s: member '%s' not in struct '%s'\n", - struct_fname,mbrname,structname); - tfsseek(struct_sfd,tfsloc,TFS_BEGIN); + printf("%s: member '%s' not in struct '%s'\n", + struct_fname,mbrname,structname); + tfsseek(struct_sfd,tfsloc,TFS_BEGIN); } /* struct_printf(): - * Use this function instead of "if (struct_verbose) printf(...)" + * Use this function instead of "if (struct_verbose) printf(...)" * all over the place. */ static int struct_printf(int mask, char *fmt, ...) { - int tot; - va_list argp; + int tot; + va_list argp; - if (!(struct_verbose & mask)) - return(0); + if(!(struct_verbose & mask)) { + return(0); + } - va_start(argp,fmt); - tot = vsnprintf(0,0,fmt,argp); - va_end(argp); - return(tot); + va_start(argp,fmt); + tot = vsnprintf(0,0,fmt,argp); + va_end(argp); + return(tot); } /* struct_prleft(): @@ -114,21 +115,22 @@ struct_printf(int mask, char *fmt, ...) static int struct_prleft(int mask, char *str, char *fmt, ...) { - int tot = 0; - va_list argp; - - if (!(struct_verbose & mask)) - return(tot); - - while((*str) && (*str != '=')) { - tot++; - putchar(*str++); - } - - va_start(argp,fmt); - tot += vsnprintf(0,0,fmt,argp); - va_end(argp); - return(tot); + int tot = 0; + va_list argp; + + if(!(struct_verbose & mask)) { + return(tot); + } + + while((*str) && (*str != '=')) { + tot++; + putchar(*str++); + } + + va_start(argp,fmt); + tot += vsnprintf(0,0,fmt,argp); + va_end(argp); + return(tot); } /* skipline(): @@ -138,24 +140,25 @@ struct_prleft(int mask, char *str, char *fmt, ...) static int skipline(char *line) { - if (struct_scriptisstructfile) { - if (strncmp(line,"###>>",5) == 0) { - strcpy(line,line+5); - return(0); - } - else - return(1); - } - else { - while(isspace(*line)) line++; - - switch(*line) { - case 0: - case '#': - return(1); - } - return(0); - } + if(struct_scriptisstructfile) { + if(strncmp(line,"###>>",5) == 0) { + strcpy(line,line+5); + return(0); + } else { + return(1); + } + } else { + while(isspace(*line)) { + line++; + } + + switch(*line) { + case 0: + case '#': + return(1); + } + return(0); + } } /* typesize(): @@ -166,38 +169,44 @@ skipline(char *line) static int typesize(char *typename, char *name) { - char *np; - struct mbrtype *mp; - int nlen, ptr, arraysize; - - ptr = 0; - arraysize = 1; - - struct_printf(4,"typesize(%s,%s)\n",typename,name); - - if (name[0] == '*') - ptr = 1; - - nlen = strlen(name); - np = name+nlen-1; - if (*np == ']') { - while(*np && (*np != '[')) np--; - if (*np == 0) - return(-1); - arraysize = atoi(np+1); - } - - mp = types; - while(mp->type) { - if (strncmp(mp->type,typename,strlen(mp->type)) == 0) - break; - mp++; - } - - if (ptr) - return(PTRSIZE * arraysize); - - return(mp->size * arraysize); + char *np; + struct mbrtype *mp; + int nlen, ptr, arraysize; + + ptr = 0; + arraysize = 1; + + struct_printf(4,"typesize(%s,%s)\n",typename,name); + + if(name[0] == '*') { + ptr = 1; + } + + nlen = strlen(name); + np = name+nlen-1; + if(*np == ']') { + while(*np && (*np != '[')) { + np--; + } + if(*np == 0) { + return(-1); + } + arraysize = atoi(np+1); + } + + mp = types; + while(mp->type) { + if(strncmp(mp->type,typename,strlen(mp->type)) == 0) { + break; + } + mp++; + } + + if(ptr) { + return(PTRSIZE * arraysize); + } + + return(mp->size * arraysize); } /* structline(): @@ -209,43 +218,60 @@ typesize(char *typename, char *name) static int structline(char *line, char **type, char **name) { - int tot; - char *cp, *token1, *token2, *token3; - - cp = line; - while(isspace(*cp)) cp++; - token1 = cp; - while(!isspace(*cp)) cp++; - *cp++ = 0; - - if (!strcmp(token1,"struct")) { - while(isspace(*cp)) cp++; - token2 = cp; - while(!isspace(*cp)) cp++; - *cp++ = 0; - while(isspace(*cp)) cp++; - token3 = cp; - while((!isspace(*cp)) && (*cp != ';')) cp++; - if (*cp != ';') - return(-1); - *cp++ = 0; - *type = token2; - *name = token3; - tot = 3; - } - else { - while(isspace(*cp)) cp++; - token2 = cp; - while((!isspace(*cp)) && (*cp != ';')) cp++; - if (*cp != ';') - return(-1); - *cp++ = 0; - *type = token1; - *name = token2; - tot = 2; - } - struct_printf(4,"structline: type='%s', name='%s'\n",*type,*name); - return(tot); + int tot; + char *cp, *token1, *token2, *token3; + + cp = line; + while(isspace(*cp)) { + cp++; + } + token1 = cp; + while(!isspace(*cp)) { + cp++; + } + *cp++ = 0; + + if(!strcmp(token1,"struct")) { + while(isspace(*cp)) { + cp++; + } + token2 = cp; + while(!isspace(*cp)) { + cp++; + } + *cp++ = 0; + while(isspace(*cp)) { + cp++; + } + token3 = cp; + while((!isspace(*cp)) && (*cp != ';')) { + cp++; + } + if(*cp != ';') { + return(-1); + } + *cp++ = 0; + *type = token2; + *name = token3; + tot = 3; + } else { + while(isspace(*cp)) { + cp++; + } + token2 = cp; + while((!isspace(*cp)) && (*cp != ';')) { + cp++; + } + if(*cp != ';') { + return(-1); + } + *cp++ = 0; + *type = token1; + *name = token2; + tot = 2; + } + struct_printf(4,"structline: type='%s', name='%s'\n",*type,*name); + return(tot); } @@ -258,526 +284,559 @@ structline(char *line, char **type, char **name) int structsize(char *structname) { - long loc; - int offset, slen, lno, size; - char line[80], *cp, *cp1, *type, *name; - - struct_printf(4,"structsize(%s)\n",structname); - - loc = tfstell(struct_sfd); - - if (tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - return(-1); - } - - offset = 0; - slen = strlen(structname); - lno = 0; - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (!strncmp(line,"struct ",7)) { - cp = line+7; - while(isspace(*cp)) cp++; - if ((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { - cp1 = cp+slen; - while(isspace(*cp1)) cp1++; - if (*cp1 != OPENBRACE) { - err_general(1,lno,loc); - return(-1); - } - - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (line[0] == CLOSEBRACE) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - return(offset); - } - switch(structline(line,&type,&name)) { - case 2: - if ((size = typesize(type,name)) < 0) { - err_general(2,lno,loc); - return(-1); - } - break; - case 3: - if ((size = structsize(type)) < 0) { - err_general(3,lno,loc); - return(-1); - } - break; - default: - err_general(4,lno,loc); - return(-1); - } - offset += size; - } - err_general(5,lno,loc); - return(-1); - } - } - } - err_nostruct(structname,loc); - return(-1); + long loc; + int offset, slen, lno, size; + char line[80], *cp, *cp1, *type, *name; + + struct_printf(4,"structsize(%s)\n",structname); + + loc = tfstell(struct_sfd); + + if(tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + return(-1); + } + + offset = 0; + slen = strlen(structname); + lno = 0; + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(!strncmp(line,"struct ",7)) { + cp = line+7; + while(isspace(*cp)) { + cp++; + } + if((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { + cp1 = cp+slen; + while(isspace(*cp1)) { + cp1++; + } + if(*cp1 != OPENBRACE) { + err_general(1,lno,loc); + return(-1); + } + + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(line[0] == CLOSEBRACE) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + return(offset); + } + switch(structline(line,&type,&name)) { + case 2: + if((size = typesize(type,name)) < 0) { + err_general(2,lno,loc); + return(-1); + } + break; + case 3: + if((size = structsize(type)) < 0) { + err_general(3,lno,loc); + return(-1); + } + break; + default: + err_general(4,lno,loc); + return(-1); + } + offset += size; + } + err_general(5,lno,loc); + return(-1); + } + } + } + err_nostruct(structname,loc); + return(-1); } int membertype(char *structname, char *mbrname, char *mbrtype) { - long loc; - int rc, slen, lno; - char line[80], *cp, *cp1, *type, *name; - - struct_printf(4,"membertype(%s,%s)\n",structname,mbrname); - - loc = tfstell(struct_sfd); - - if (tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - return(-1); - } - - slen = strlen(structname); - lno = 0; - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (!strncmp(line,"struct ",7)) { - cp = line+7; - while(isspace(*cp)) cp++; - if ((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { - cp1 = cp+slen; - while(isspace(*cp1)) cp1++; - if (*cp1 != OPENBRACE) { - err_general(6,lno,loc); - return(-1); - } - - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (line[0] == CLOSEBRACE) { - err_nomember(structname,mbrname,loc); - return(-1); - } - if ((rc = structline(line,&type,&name)) < 0) { - err_general(7,lno,loc); - return(-1); - } - if (!strcmp(name,mbrname)) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - if (mbrtype) - strcpy(mbrtype,type); - return(rc); - } - } - err_general(8,lno,loc); - return(-1); - } - } - } - err_nostruct(structname,loc); - return(-1); + long loc; + int rc, slen, lno; + char line[80], *cp, *cp1, *type, *name; + + struct_printf(4,"membertype(%s,%s)\n",structname,mbrname); + + loc = tfstell(struct_sfd); + + if(tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + return(-1); + } + + slen = strlen(structname); + lno = 0; + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(!strncmp(line,"struct ",7)) { + cp = line+7; + while(isspace(*cp)) { + cp++; + } + if((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { + cp1 = cp+slen; + while(isspace(*cp1)) { + cp1++; + } + if(*cp1 != OPENBRACE) { + err_general(6,lno,loc); + return(-1); + } + + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(line[0] == CLOSEBRACE) { + err_nomember(structname,mbrname,loc); + return(-1); + } + if((rc = structline(line,&type,&name)) < 0) { + err_general(7,lno,loc); + return(-1); + } + if(!strcmp(name,mbrname)) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + if(mbrtype) { + strcpy(mbrtype,type); + } + return(rc); + } + } + err_general(8,lno,loc); + return(-1); + } + } + } + err_nostruct(structname,loc); + return(-1); } /* memberoffset(): * Return the offset into the structure at which point the member resides. - * If mbrsize is non-zero, then assume it is a pointer to an integer + * If mbrsize is non-zero, then assume it is a pointer to an integer * into which this function will also load the size of the member. */ int memberoffset(char *structname, char *mbrname, int *mbrsize) { - long loc; - int offset, slen, size, lno; - char line[80], *cp, *cp1, *type, *name; - - struct_printf(4,"memberoffset(%s,%s)\n",structname,mbrname); - - loc = tfstell(struct_sfd); - - if (tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - return(-1); - } - - offset = 0; - slen = strlen(structname); - lno = 0; - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (!strncmp(line,"struct ",7)) { - cp = line+7; - while(isspace(*cp)) cp++; - if ((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { - cp1 = cp+slen; - while(isspace(*cp1)) cp1++; - if (*cp1 != OPENBRACE) { - err_general(9,lno,loc); - return(-1); - } - - while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { - lno++; - if (skipline(line)) - continue; - if (line[0] == '#') - continue; - if (line[0] == CLOSEBRACE) { - err_nomember(structname,mbrname,loc); - return(-1); - } - switch(structline(line,&type,&name)) { - case 2: - if ((size = typesize(type,name)) < 0) { - err_general(10,lno,loc); - return(-1); - } - break; - case 3: - if ((size = structsize(type)) < 0) { - err_general(11,lno,loc); - return(-1); - } - break; - default: - err_general(12,lno,loc); - return(-1); - } - if (!strcmp(name,mbrname)) { - tfsseek(struct_sfd,loc,TFS_BEGIN); - if (mbrsize) - *mbrsize = size; - return(offset); - } - offset += size; - } - err_general(13,lno,loc); - return(-1); - } - } - } - err_nostruct(structname,loc); - return(-1); + long loc; + int offset, slen, size, lno; + char line[80], *cp, *cp1, *type, *name; + + struct_printf(4,"memberoffset(%s,%s)\n",structname,mbrname); + + loc = tfstell(struct_sfd); + + if(tfsseek(struct_sfd,0,TFS_BEGIN) < 0) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + return(-1); + } + + offset = 0; + slen = strlen(structname); + lno = 0; + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(!strncmp(line,"struct ",7)) { + cp = line+7; + while(isspace(*cp)) { + cp++; + } + if((!strncmp(structname,cp,slen)) && (isspace(cp[slen]))) { + cp1 = cp+slen; + while(isspace(*cp1)) { + cp1++; + } + if(*cp1 != OPENBRACE) { + err_general(9,lno,loc); + return(-1); + } + + while(tfsgetline(struct_sfd,line,sizeof(line)) > 0) { + lno++; + if(skipline(line)) { + continue; + } + if(line[0] == '#') { + continue; + } + if(line[0] == CLOSEBRACE) { + err_nomember(structname,mbrname,loc); + return(-1); + } + switch(structline(line,&type,&name)) { + case 2: + if((size = typesize(type,name)) < 0) { + err_general(10,lno,loc); + return(-1); + } + break; + case 3: + if((size = structsize(type)) < 0) { + err_general(11,lno,loc); + return(-1); + } + break; + default: + err_general(12,lno,loc); + return(-1); + } + if(!strcmp(name,mbrname)) { + tfsseek(struct_sfd,loc,TFS_BEGIN); + if(mbrsize) { + *mbrsize = size; + } + return(offset); + } + offset += size; + } + err_general(13,lno,loc); + return(-1); + } + } + } + err_nostruct(structname,loc); + return(-1); } char *StructHelp[] = { - "Build a structure in memory", - "-[b:f:v] {struct.mbr[=val]} [struct.mbr1[=val1]] ...", + "Build a structure in memory", + "-[b:f:v] {struct.mbr[=val]} [struct.mbr1[=val1]] ...", #if INCLUDE_VERBOSEHELP - "Options:", - " -b{addr} base address of structure (overrides STRUCTBASE)", - " -f{fname} structure definition filename (overrides STRUCTFILE)", - " -v additive verbosity", - "", - "Notes:", - " * The 'val' can be a normal value or a processed function...", + "Options:", + " -b{addr} base address of structure (overrides STRUCTBASE)", + " -f{fname} structure definition filename (overrides STRUCTFILE)", + " -v additive verbosity", + "", + "Notes:", + " * The 'val' can be a normal value or a processed function...", " strcpy(str|src), strcat(str|src), memcpy(src,size)", - " sizeof(structtype), tagsiz(str1,str2), e2b(enet), i2l(ip)", - " * If '=val' is not specified, then the size and offset of the", - " specified structure/member is loaded into STRUCTSIZE and", - " STRUCTOFFSET shellvars respectively.", + " sizeof(structtype), tagsiz(str1,str2), e2b(enet), i2l(ip)", + " * If '=val' is not specified, then the size and offset of the", + " specified structure/member is loaded into STRUCTSIZE and", + " STRUCTOFFSET shellvars respectively.", #endif - 0, + 0, }; int StructCmd(int argc,char *argv[]) { - unsigned long lval, dest; - char copy[CMDLINESIZE], type[32]; - char *eq, *dot, *str, *mbr, *env, *equation; - int opt, i, offset, mbrtype, rc, size, processlval; - - struct_fname = 0; - struct_verbose = 0; - struct_base = 0xffffffff; - while((opt=getopt(argc,argv,"b:f:v")) != -1) { - switch(opt) { - case 'b': - struct_base = strtoul(optarg,0,0); - break; - case 'f': - struct_fname = optarg; - break; - case 'v': - struct_verbose++; - break; - default: - return(CMD_PARAM_ERROR); - } - } - - if (argc < optind + 1) - return(CMD_PARAM_ERROR); - - /* If base and/or filename are not set, get them from environment - * variables... - */ - if (struct_base == 0xffffffff) { - if ((env = getenv("STRUCTBASE")) == 0) { - printf("No struct base\n"); - return(CMD_FAILURE); - } - struct_base = strtoul(env,0,0); - } - if (struct_fname == 0) { - if ((struct_fname = getenv("STRUCTFILE")) == 0) { - printf("No struct filename\n"); - return(CMD_FAILURE); - } - } - - struct_sfd = tfsopen(struct_fname,TFS_RDONLY,0); - - if (struct_sfd < 0) { - printf("Can't find file '%s'\n",struct_fname); - return(CMD_FAILURE); - } - - /* If the specified structure description file is the currently - * running script, then set a flag so that this code will look - * for the "###>>" prefix as a required line prefix in the - * structure file. - */ - if (strcmp(struct_fname,tfsscriptname()) == 0) - struct_scriptisstructfile = 1; - else - struct_scriptisstructfile = 0; - - /* Assume each command line argument is some "struct=val" statement, - * and process each one... - */ - for(i=optind;i<argc;i++) { - equation = argv[i]; - - /* Make a copy of the argument so we can modify it. - * (no need to check length because sizeof(copy) is CMDLINESIZE). - */ - strcpy(copy,equation); - - /* Check for equal sign... - */ - if ((eq = strchr(copy,'='))) - *eq = 0; - - /* Start parsing and processing the structure request... - */ - offset = mbrtype = 0; - dot = strchr(copy,'.'); - if (!dot) { - size = structsize(copy); - } - else { - while(dot) { - *dot++ = 0; - mbr = dot; - str = dot-2; - while((*str != 0) && (str != copy) && (*str != '.')) - str--; - if (str != copy) - str++; - while((dot != 0) && (*dot != '.')) - dot++; - *dot = 0; - - if (mbrtype == 3) - str = type; - - if ((rc = memberoffset(str,mbr,&size)) < 0) - goto done; - - if ((mbrtype = membertype(str,mbr,type)) < 0) - goto done; - - offset += rc; - *dot = '.'; - dot = strchr(mbr,'.'); - } - } - - shell_sprintf("STRUCTOFFSET","0x%lx",offset); - shell_sprintf("STRUCTSIZE","0x%lx",size); - - /* If there is no "right half" of the equation, then just - * continue here... - */ - if (!eq) - continue; - - /* At this point we have the size of the member and its offset - * from the base, so now we parse the "val" side of the - * equation... - */ - - /* Check for functions (sizeof, strcpy, enet, ip, etc...). - * If found, then something other than just normal lval processing - * is done... - */ - eq++; - lval = processlval = 0; - dest = struct_base + offset; - if (!strncmp(eq,"sizeof(",7)) { - char *cp; - - eq += 7; - cp = eq; - if ((cp = strchr(cp,')')) == 0) - goto paramerr; - *cp=0; - lval = structsize(eq); - processlval = 1; - } - else if (!strncmp(eq,"i2l(",4)) { - char *cp, *cp1; - - eq += 4; - cp = cp1 = eq; - if ((cp1 = strchr(cp,')')) == 0) - goto paramerr; - *cp1 = 0; - if (struct_verbose & 1) { - } - struct_printf(3,"i2l(0x%lx,%s)\n", dest, cp); - - if (IpToBin(cp,(uchar *)dest) < 0) - goto paramerr; - } - else if (!strncmp(eq,"e2b(",4)) { - char *cp, *cp1; - - cp = cp1 = eq+4; - if ((cp1 = strchr(cp,')')) == 0) - goto paramerr; - *cp1 = 0; - struct_printf(3,"e2b(0x%lx,%s)\n", dest, cp); - - if (EtherToBin(cp,(uchar *)dest) < 0) - goto paramerr; - } - else if (!strncmp(eq,"tagsiz(",7)) { - char *comma, *paren; - int siz1, siz2; - - eq += 7; - comma = eq; - if ((comma = strchr(comma,',')) == 0) - goto paramerr; - *comma++ = 0; - if ((paren = strrchr(comma,')')) == 0) - goto paramerr; - *paren = 0; - if ((siz1=structsize(eq)) < 0) - goto paramerr; - if ((siz2=structsize(comma)) < 0) - goto paramerr; - lval = (siz1+siz2)/4; - processlval = 1; - } - else if (!strncmp(eq,"memcpy(",7)) { - int len; - char *comma, *cp; - - eq += 7; - comma = eq; - if ((comma = strchr(comma,',')) == 0) - goto paramerr; - *comma++ = 0; - cp = comma; - cp = (char *)strtoul(eq,0,0); - len = (int)strtoul(comma,0,0); - struct_printf(3,"memcpy(0x%lx,0x%lx,%d)\n",dest,(long)cp,len); - memcpy((void *)dest,(void *)cp,len); - } - else if (!strncmp(eq,"strcpy(",7)) { - char *cp, *cp1; - - eq += 7; - cp = cp1 = eq; - if ((cp1 = strrchr(cp,')')) == 0) - goto paramerr; - *cp1 = 0; - - - if (!strncmp(cp,"0x",2)) { - cp = (char *)strtoul(eq,0,0); - struct_printf(3,"strcpy(0x%lx,0x%lx)\n",dest,(long)cp); - } - else { - struct_prleft(1,equation," = \"%s\"\n",cp); - struct_printf(2,"strcpy(0x%lx,%s)\n", dest,cp); - } - strcpy((char *)dest,cp); - } - else if (!strncmp(eq,"strcat(",7)) { - char *cp, *cp1; - - eq += 7; - cp = cp1 = eq; - if ((cp1 = strrchr(cp,')')) == 0) - goto paramerr; - *cp1 = 0; - - if (!strncmp(cp,"0x",2)) { - cp = (char *)strtoul(eq,0,0); - struct_printf(3,"strcat(0x%lx,0x%lx)\n",dest,(long)cp); - } - else { - struct_prleft(1,equation," += \"%s\"\n",cp); - struct_printf(2,"strcat(0x%lx,%s)\n", dest,cp); - } - strcat((char *)dest,cp); - } - else { - lval = strtoul(eq,0,0); - processlval = 1; - } - - if (processlval) { - switch(size) { - case 1: - struct_prleft(1,equation," = %d (0x%x)\n", - (uchar)lval,(uchar)lval); - struct_printf(2,"*(uchar *)0x%lx = %d (0x%x)\n", - dest,(uchar)lval,(uchar)lval); - *(uchar *)(dest) = (uchar)lval; - break; - case 2: - struct_prleft(1,equation," = %d (0x%x)\n", - (ushort)lval,(ushort)lval); - struct_printf(2,"*(ushort *)0x%lx = %d (0x%x)\n", - dest,(ushort)lval,(ushort)lval); - *(ushort *)dest = (ushort)lval; - break; - case 4: - struct_prleft(1,equation," = %ld (0x%lx)\n", - (ulong)lval,(ulong)lval); - struct_printf(2,"*(ulong *)0x%lx = %d (0x%x)\n", - dest,lval,lval); - *(ulong *)dest = lval; - break; - default: - struct_printf(3,"memset(0x%lx,0x%x,%d)\n", - dest,(uchar)lval,size); - memset((void *)dest,lval,size); - break; - } - } - } + unsigned long lval, dest; + char copy[CMDLINESIZE], type[32]; + char *eq, *dot, *str, *mbr, *env, *equation; + int opt, i, offset, mbrtype, rc, size, processlval; + + struct_fname = 0; + struct_verbose = 0; + struct_base = 0xffffffff; + while((opt=getopt(argc,argv,"b:f:v")) != -1) { + switch(opt) { + case 'b': + struct_base = strtoul(optarg,0,0); + break; + case 'f': + struct_fname = optarg; + break; + case 'v': + struct_verbose++; + break; + default: + return(CMD_PARAM_ERROR); + } + } + + if(argc < optind + 1) { + return(CMD_PARAM_ERROR); + } + + /* If base and/or filename are not set, get them from environment + * variables... + */ + if(struct_base == 0xffffffff) { + if((env = getenv("STRUCTBASE")) == 0) { + printf("No struct base\n"); + return(CMD_FAILURE); + } + struct_base = strtoul(env,0,0); + } + if(struct_fname == 0) { + if((struct_fname = getenv("STRUCTFILE")) == 0) { + printf("No struct filename\n"); + return(CMD_FAILURE); + } + } + + struct_sfd = tfsopen(struct_fname,TFS_RDONLY,0); + + if(struct_sfd < 0) { + printf("Can't find file '%s'\n",struct_fname); + return(CMD_FAILURE); + } + + /* If the specified structure description file is the currently + * running script, then set a flag so that this code will look + * for the "###>>" prefix as a required line prefix in the + * structure file. + */ + if(strcmp(struct_fname,tfsscriptname()) == 0) { + struct_scriptisstructfile = 1; + } else { + struct_scriptisstructfile = 0; + } + + /* Assume each command line argument is some "struct=val" statement, + * and process each one... + */ + for(i=optind; i<argc; i++) { + equation = argv[i]; + + /* Make a copy of the argument so we can modify it. + * (no need to check length because sizeof(copy) is CMDLINESIZE). + */ + strcpy(copy,equation); + + /* Check for equal sign... + */ + if((eq = strchr(copy,'='))) { + *eq = 0; + } + + /* Start parsing and processing the structure request... + */ + offset = mbrtype = 0; + dot = strchr(copy,'.'); + if(!dot) { + size = structsize(copy); + } else { + while(dot) { + *dot++ = 0; + mbr = dot; + str = dot-2; + while((*str != 0) && (str != copy) && (*str != '.')) { + str--; + } + if(str != copy) { + str++; + } + while((dot != 0) && (*dot != '.')) { + dot++; + } + *dot = 0; + + if(mbrtype == 3) { + str = type; + } + + if((rc = memberoffset(str,mbr,&size)) < 0) { + goto done; + } + + if((mbrtype = membertype(str,mbr,type)) < 0) { + goto done; + } + + offset += rc; + *dot = '.'; + dot = strchr(mbr,'.'); + } + } + + shell_sprintf("STRUCTOFFSET","0x%lx",offset); + shell_sprintf("STRUCTSIZE","0x%lx",size); + + /* If there is no "right half" of the equation, then just + * continue here... + */ + if(!eq) { + continue; + } + + /* At this point we have the size of the member and its offset + * from the base, so now we parse the "val" side of the + * equation... + */ + + /* Check for functions (sizeof, strcpy, enet, ip, etc...). + * If found, then something other than just normal lval processing + * is done... + */ + eq++; + lval = processlval = 0; + dest = struct_base + offset; + if(!strncmp(eq,"sizeof(",7)) { + char *cp; + + eq += 7; + cp = eq; + if((cp = strchr(cp,')')) == 0) { + goto paramerr; + } + *cp=0; + lval = structsize(eq); + processlval = 1; + } else if(!strncmp(eq,"i2l(",4)) { + char *cp, *cp1; + + eq += 4; + cp = cp1 = eq; + if((cp1 = strchr(cp,')')) == 0) { + goto paramerr; + } + *cp1 = 0; + if(struct_verbose & 1) { + } + struct_printf(3,"i2l(0x%lx,%s)\n", dest, cp); + + if(IpToBin(cp,(uchar *)dest) < 0) { + goto paramerr; + } + } else if(!strncmp(eq,"e2b(",4)) { + char *cp, *cp1; + + cp = cp1 = eq+4; + if((cp1 = strchr(cp,')')) == 0) { + goto paramerr; + } + *cp1 = 0; + struct_printf(3,"e2b(0x%lx,%s)\n", dest, cp); + + if(EtherToBin(cp,(uchar *)dest) < 0) { + goto paramerr; + } + } else if(!strncmp(eq,"tagsiz(",7)) { + char *comma, *paren; + int siz1, siz2; + + eq += 7; + comma = eq; + if((comma = strchr(comma,',')) == 0) { + goto paramerr; + } + *comma++ = 0; + if((paren = strrchr(comma,')')) == 0) { + goto paramerr; + } + *paren = 0; + if((siz1=structsize(eq)) < 0) { + goto paramerr; + } + if((siz2=structsize(comma)) < 0) { + goto paramerr; + } + lval = (siz1+siz2)/4; + processlval = 1; + } else if(!strncmp(eq,"memcpy(",7)) { + int len; + char *comma, *cp; + + eq += 7; + comma = eq; + if((comma = strchr(comma,',')) == 0) { + goto paramerr; + } + *comma++ = 0; + cp = comma; + cp = (char *)strtoul(eq,0,0); + len = (int)strtoul(comma,0,0); + struct_printf(3,"memcpy(0x%lx,0x%lx,%d)\n",dest,(long)cp,len); + memcpy((void *)dest,(void *)cp,len); + } else if(!strncmp(eq,"strcpy(",7)) { + char *cp, *cp1; + + eq += 7; + cp = cp1 = eq; + if((cp1 = strrchr(cp,')')) == 0) { + goto paramerr; + } + *cp1 = 0; + + + if(!strncmp(cp,"0x",2)) { + cp = (char *)strtoul(eq,0,0); + struct_printf(3,"strcpy(0x%lx,0x%lx)\n",dest,(long)cp); + } else { + struct_prleft(1,equation," = \"%s\"\n",cp); + struct_printf(2,"strcpy(0x%lx,%s)\n", dest,cp); + } + strcpy((char *)dest,cp); + } else if(!strncmp(eq,"strcat(",7)) { + char *cp, *cp1; + + eq += 7; + cp = cp1 = eq; + if((cp1 = strrchr(cp,')')) == 0) { + goto paramerr; + } + *cp1 = 0; + + if(!strncmp(cp,"0x",2)) { + cp = (char *)strtoul(eq,0,0); + struct_printf(3,"strcat(0x%lx,0x%lx)\n",dest,(long)cp); + } else { + struct_prleft(1,equation," += \"%s\"\n",cp); + struct_printf(2,"strcat(0x%lx,%s)\n", dest,cp); + } + strcat((char *)dest,cp); + } else { + lval = strtoul(eq,0,0); + processlval = 1; + } + + if(processlval) { + switch(size) { + case 1: + struct_prleft(1,equation," = %d (0x%x)\n", + (uchar)lval,(uchar)lval); + struct_printf(2,"*(uchar *)0x%lx = %d (0x%x)\n", + dest,(uchar)lval,(uchar)lval); + *(uchar *)(dest) = (uchar)lval; + break; + case 2: + struct_prleft(1,equation," = %d (0x%x)\n", + (ushort)lval,(ushort)lval); + struct_printf(2,"*(ushort *)0x%lx = %d (0x%x)\n", + dest,(ushort)lval,(ushort)lval); + *(ushort *)dest = (ushort)lval; + break; + case 4: + struct_prleft(1,equation," = %ld (0x%lx)\n", + (ulong)lval,(ulong)lval); + struct_printf(2,"*(ulong *)0x%lx = %d (0x%x)\n", + dest,lval,lval); + *(ulong *)dest = lval; + break; + default: + struct_printf(3,"memset(0x%lx,0x%x,%d)\n", + dest,(uchar)lval,size); + memset((void *)dest,lval,size); + break; + } + } + } done: - tfsclose(struct_sfd,0); - return(CMD_SUCCESS); + tfsclose(struct_sfd,0); + return(CMD_SUCCESS); paramerr: - tfsclose(struct_sfd,0); - return(CMD_PARAM_ERROR); + tfsclose(struct_sfd,0); + return(CMD_PARAM_ERROR); } #endif |