123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482 |
- /* Copyright 2009, UCAR/Unidata and OPeNDAP, Inc.
- See the COPYRIGHT file for more information.
- */
- #include "config.h"
- #include <sys/stat.h>
- #ifdef NETINET_IN_H
- #include <netinet/in.h>
- #endif
- #include "ocinternal.h"
- #include "ocdata.h"
- #include "ocdebug.h"
- #define MAXLEVEL 1
- /*Forward*/
- static void dumpocnode1(OCnode* node, int depth);
- static void dumpdimensions(OCnode* node);
- static void dumpattvalue(OCtype nctype, char** aset, int index);
- static char* sindent = NULL;
- static char*
- dent(int n)
- {
- if(sindent == NULL) {
- sindent = (char*)ocmalloc(102);
- MEMCHECK(sindent,NULL);
- memset((void*)sindent,(int)' ',(size_t)101);
- sindent[101] = '\0';
- }
- if(n > 100) n = 100;
- return sindent+(100-n);
- }
- /* support [dd] leader*/
- static char*
- dent2(int n) {return dent(n+4);}
- void
- ocdumpnode(OCnode* node)
- {
- if(node != NULL) {
- dumpocnode1(node,0);
- } else {
- fprintf(stdout,"<NULL>\n");
- }
- fflush(stdout);
- }
- static void
- dumpskip(OCnode* node)
- {
- char tmpc[64];
- char tmpi[64];
- char tmpt[64];
- char tmpo[64];
- if(node->skip.count == OCINDETERMINATE)
- strcpy(tmpc,"?");
- else
- snprintf(tmpc,sizeof(tmpc),"%lu",(unsigned long)node->skip.count);
- if(node->skip.instancesize == OCINDETERMINATE)
- strcpy(tmpi,"?");
- else
- snprintf(tmpi,sizeof(tmpi),"%lu",(unsigned long)node->skip.instancesize);
- if(node->skip.totalsize == OCINDETERMINATE)
- strcpy(tmpt,"?");
- else
- snprintf(tmpt,sizeof(tmpt),"%lu",(unsigned long)node->skip.totalsize);
- if(node->skip.offset == OCINDETERMINATE)
- strcpy(tmpo,"?");
- else
- snprintf(tmpo,sizeof(tmpo),"%lu",(unsigned long)node->skip.offset);
- fprintf(stdout," [(%s*%s)/%s@%s]",tmpi,tmpc,tmpt,tmpo);
- }
- static void
- dumpocnode1(OCnode* node, int depth)
- {
- unsigned int n;
- switch (node->octype) {
- case OC_Primitive: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- if(node->name == NULL) OCPANIC("prim without name");
- fprintf(stdout,"%s %s",octypetostring(node->etype),node->name);
- dumpdimensions(node);
- #ifdef OCIGNORE
- if(node->cache.cacheable) fprintf(stdout," [cached]");
- #endif
- dumpskip(node);
- fprintf(stdout," &%lx",(unsigned long)node);
- fprintf(stdout,"\n");
- } break;
- case OC_Dataset: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- fprintf(stdout,"dataset %s\n",
- (node->name?node->name:""));
- for(n=0;n<oclistlength(node->subnodes);n++) {
- dumpocnode1((OCnode*)oclistget(node->subnodes,n),depth+1);
- }
- } break;
- case OC_Structure: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- fprintf(stdout,"struct %s",
- (node->name?node->name:""));
- dumpdimensions(node);
- dumpskip(node);
- fprintf(stdout," &%lx",(unsigned long)node);
- fprintf(stdout,"\n");
- for(n=0;n<oclistlength(node->subnodes);n++) {
- dumpocnode1((OCnode*)oclistget(node->subnodes,n),depth+1);
- }
- } break;
- case OC_Sequence: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- fprintf(stdout,"sequence %s",
- (node->name?node->name:""));
- dumpdimensions(node);
- dumpskip(node);
- fprintf(stdout," &%lx",(unsigned long)node);
- fprintf(stdout,"\n");
- for(n=0;n<oclistlength(node->subnodes);n++) {
- dumpocnode1((OCnode*)oclistget(node->subnodes,n),depth+1);
- }
- } break;
- case OC_Grid: {
- unsigned int i;
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- fprintf(stdout,"grid %s",
- (node->name?node->name:""));
- dumpdimensions(node);
- dumpskip(node);
- fprintf(stdout," &%lx",(unsigned long)node);
- fprintf(stdout,"\n");
- fprintf(stdout,"%sarray:\n",dent2(depth+1));
- dumpocnode1((OCnode*)oclistget(node->subnodes,0),depth+2);
- fprintf(stdout,"%smaps:\n",dent2(depth+1));
- for(i=1;i<oclistlength(node->subnodes);i++) {
- dumpocnode1((OCnode*)oclistget(node->subnodes,i),depth+2);
- }
- } break;
- case OC_Attribute: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- if(node->name == NULL) OCPANIC("Attribute without name");
- fprintf(stdout,"%s %s",octypetostring(node->etype),node->name);
- for(n=0;n<oclistlength(node->att.values);n++) {
- char* value = (char*)oclistget(node->att.values,n);
- if(n > 0) fprintf(stdout,",");
- fprintf(stdout," %s",value);
- }
- fprintf(stdout," &%lx",(unsigned long)node);
- fprintf(stdout,"\n");
- } break;
- case OC_Attributeset: {
- fprintf(stdout,"[%2d]%s ",depth,dent(depth));
- fprintf(stdout,"%s:\n",node->name?node->name:"Attributes");
- for(n=0;n<oclistlength(node->subnodes);n++) {
- dumpocnode1((OCnode*)oclistget(node->subnodes,n),depth+1);
- }
- } break;
- default:
- OCPANIC1("encountered unexpected node type: %x",node->octype);
- }
- if(node->attributes != NULL) {
- unsigned int i;
- for(i=0;i<oclistlength(node->attributes);i++) {
- OCattribute* att = (OCattribute*)oclistget(node->attributes,i);
- fprintf(stdout,"%s[%s=",dent2(depth+2),att->name);
- if(att->nvalues == 0)
- OCPANIC("Attribute.nvalues == 0");
- if(att->nvalues == 1) {
- dumpattvalue(att->etype,att->values,0);
- } else {
- unsigned int j;
- fprintf(stdout,"{");
- for(j=0;j<att->nvalues;j++) {
- if(j>0) fprintf(stdout,", ");
- dumpattvalue(att->etype,att->values,j);
- }
- fprintf(stdout,"}");
- }
- fprintf(stdout,"]\n");
- }
- }
- }
- static void
- dumpdimensions(OCnode* node)
- {
- unsigned int i;
- for(i=0;i<node->array.rank;i++) {
- OCnode* dim = (OCnode*)oclistget(node->array.dimensions,i);
- fprintf(stdout,"[%s=%lu]",
- (dim->name?dim->name:"?"),
- (unsigned long)dim->dim.declsize);
- }
- }
- static void
- dumpattvalue(OCtype nctype, char** strings, int index)
- {
- if(nctype == OC_String || nctype == OC_URL) {
- fprintf(stdout,"\"%s\"",strings[index]);
- } else {
- fprintf(stdout,"%s",strings[index]);
- }
- }
- void
- ocdumpslice(OCslice* slice)
- {
- fprintf(stdout,"[");
- fprintf(stdout,"%lu",(unsigned long)slice->first);
- if(slice->stride > 1) fprintf(stdout,":%lu",(unsigned long)slice->stride);
- fprintf(stdout,":%lu",(unsigned long)(slice->first+slice->count)-1);
- fprintf(stdout,"]");
- }
- void
- ocdumpclause(OCprojectionclause* ref)
- {
- unsigned int i;
- OClist* path = oclistnew();
- occollectpathtonode(ref->node,path);
- for(i=0;i<oclistlength(path);i++) {
- OClist* sliceset;
- OCnode* node = (OCnode*)oclistget(path,i);
- if(node->tree != NULL) continue; /* leave off the root node*/
- fprintf(stdout,"%s%s",(i>0?PATHSEPARATOR:""),node->name);
- sliceset = (OClist*)oclistget(ref->indexsets,i);
- if(sliceset != NULL) {
- unsigned int j;
- for(j=0;j<oclistlength(sliceset);j++) {
- OCslice* slice = (OCslice*)oclistget(sliceset,j);
- ocdumpslice(slice);
- }
- }
- }
- }
- static void
- addfield(char* field, char* line, int align)
- {
- int len,rem;
- strcat(line,"|");
- strcat(line,field);
- len = strlen(field);
- rem = (align - len);
- while(rem-- > 0) strcat(line," ");
- }
- static void
- dumpfield(int index, char* n8, int isxdr)
- {
- char line[1024];
- char tmp[32];
- union {
- unsigned int uv;
- int sv;
- char cv[4];
- float fv;
- } form;
- union {
- char cv[8];
- unsigned long long ll;
- double d;
- } dform;
- line[0] = '\0';
- /* offset */
- sprintf(tmp,"%6d",index);
- addfield(tmp,line,5);
- memcpy(form.cv,n8,4);
- /* straight hex*/
- sprintf(tmp,"%08x",form.uv);
- addfield(tmp,line,8);
- if(isxdr) {swapinline32(&form.uv);}
- /* unsigned integer */
- sprintf(tmp,"%12u",form.uv);
- addfield(tmp,line,12);
- /* signed integer */
- sprintf(tmp,"%12d",form.sv);
- addfield(tmp,line,12);
- /* float */
- sprintf(tmp,"%#g",form.fv);
- addfield(tmp,line,12);
- /* char[4] */
- {
- /* use raw form (i.e. n8)*/
- int i;
- tmp[0] = '\0';
- for(i=0;i<4;i++) {
- char stmp[64];
- unsigned int c = (n8[i] & 0xff);
- if(c < ' ' || c > 126)
- sprintf(stmp,"\\%02x",c);
- else
- sprintf(stmp,"%c",c);
- strcat(tmp,stmp);
- }
- }
- addfield(tmp,line,16);
- /* double */
- memcpy(dform.cv,n8,2*XDRUNIT);
- if(isxdr) xxdrntohdouble(dform.cv,&dform.d);
- sprintf(tmp,"%#g",dform.d);
- addfield(tmp,line,12);
- fprintf(stdout,"%s\n",line);
- }
- static void
- typedmemorydump(char* memory, size_t len, int fromxdr)
- {
- unsigned int i,count,rem;
- char line[1024];
- char* pmem;
- char mem[8];
- assert(memory[len] == 0);
- /* build the header*/
- line[0] = '\0';
- addfield("offset",line,6);
- addfield("hex",line,8);
- addfield("uint",line,12);
- addfield("int",line,12);
- addfield("float",line,12);
- addfield("char[4]",line,16);
- addfield("double",line,12);
- strcat(line,"\n");
- fprintf(stdout,"%s",line);
- count = (len / sizeof(int));
- rem = (len % sizeof(int));
- for(pmem=memory,i=0;i<count;i++,pmem+=4) {
- memset(mem,0,8);
- if(i<(count-1))
- memcpy(mem,pmem,8);
- else
- memcpy(mem,pmem,4);
- dumpfield(i*sizeof(unsigned int),mem,fromxdr);
- }
- if(rem > 0) {
- memset(mem,0,8);
- memcpy(mem,pmem,4);
- dumpfield(i*sizeof(unsigned int),mem,fromxdr);
- }
- fflush(stdout);
- }
- static void
- simplememorydump(char* memory, size_t len, int fromxdr)
- {
- unsigned int i,count,rem;
- int* imemory;
- char tmp[32];
- char line[1024];
- assert(memory[len] == 0);
- /* build the header*/
- line[0] = '\0';
- addfield("offset",line,6);
- addfield("XDR (hex)",line,9);
- addfield("!XDR (hex)",line,10);
- fprintf(stdout,"%s\n",line);
- count = (len / sizeof(int));
- rem = (len % sizeof(int));
- if(rem != 0)
- fprintf(stderr,"ocdump: |mem|%%4 != 0\n");
- imemory = (int*)memory;
- for(i=0;i<count;i++) {
- unsigned int vx = (unsigned int)imemory[i];
- unsigned int v = vx;
- if(!xxdr_network_order) swapinline32(&v);
- line[0] = '\0';
- sprintf(tmp,"%6d",i);
- addfield(tmp,line,6);
- sprintf(tmp,"%08x",vx);
- addfield(tmp,line,9);
- sprintf(tmp,"%08x",v);
- addfield(tmp,line,10);
- fprintf(stdout,"%s\n",line);
- }
- fflush(stdout);
- }
- void
- ocdumpmemory(char* memory, size_t len, int xdrencoded, int level)
- {
- if(level > MAXLEVEL) level = MAXLEVEL;
- switch (level) {
- case 1: /* Do a multi-type dump */
- typedmemorydump(memory,len,xdrencoded);
- break;
- case 0: /* Dump a simple linear list of the contents of the memory as 32-bit hex and decimal */
- default:
- simplememorydump(memory,len,xdrencoded);
- break;
- }
- }
- static int
- ocreadfile(FILE* file, int datastart, char** memp, size_t* lenp)
- {
- char* mem;
- size_t len;
- size_t pos;
- size_t red;
- struct stat stats;
- pos = ftell(file);
- fseek(file,0,SEEK_SET);
- fseek(file,datastart,SEEK_SET);
- fstat(fileno(file),&stats);
- len = stats.st_size;
- len -= datastart;
-
- mem = (char*)calloc(len+1,1);
- if(mem == NULL) return 0;
- /* Read only the data part */
- red = fread(mem,1,len,file);
- if(red < len) {
- fprintf(stderr,"ocreadfile: short file\n");
- return 0;
- }
- fseek(file,pos,SEEK_SET); /* leave it as we found it*/
- if(memp) *memp = mem;
- if(lenp) *lenp = len;
- return 1;
- }
- void
- ocdd(OCstate* state, OCnode* root, int xdrencoded, int level)
- {
- char* mem;
- size_t len;
- if(root->tree->data.file != NULL) {
- if(!ocreadfile(root->tree->data.file,root->tree->data.bod,&mem,&len)) {
- fprintf(stderr,"ocdd could not read data file\n");
- return;
- }
- ocdumpmemory(mem,len,xdrencoded,level);
- free(mem);
- } else {
- mem = root->tree->data.memory;
- mem += root->tree->data.bod;
- len = root->tree->data.datasize;
- len -= root->tree->data.bod;
- ocdumpmemory(mem,len,xdrencoded,level);
- }
- }
|