void OutputData( unsigned_32 offset, unsigned_32 len ) /****************************************************/ { int i; char *j; char ch; char ascbuf[80]; if( no_disp ) return; if( len == 0 ) { len = RecLen - RecOffset(); /* FIXME - kind of a kludge */ } Output( INDENT "%8", offset ); offset += 16; i = 0; j = ascbuf; for(;;) { if( len == 0 ) break; if( i > 0xf ) { *j = 0; Output( " <%s>" CRLF INDENT "%8", ascbuf, offset ); offset += 16; i = 0; j = ascbuf; } ch = GetByte(); --len; *j++ = isprint( ch ) ? ch : '.'; Output( "%c%2", ( i & 1 ) ? '|' : ' ', ch ); i++; } *j = 0; Output( "%> <%s>" CRLF, 3 * ( 0x10 - i ), ascbuf ); }
void ProcFile( FILE *fp, bool is_intel ) /**************************************/ { byte cksum; byte hdr[ 3 ]; unsigned_16 page_len; unsigned_32 offset; const char *recname; unsigned_32 total_padding; int raw_dump; int i; int first; IsPharLap = FALSE; IsMS386 = FALSE; IsIntel = is_intel; RecNum = 0; page_len = 0; RecBuff = NULL; RecMaxLen = 0; total_padding = 0; Lnames = NULL; Xnames = NULL; Segdefs = NULL; Grpdefs = NULL; first = 1; for(;;) { raw_dump = DumpRaw; offset = ftell( fp ); if( fread( hdr, 1, 3, fp ) != 3 ) break; cksum = hdr[ 0 ]; cksum += hdr[ 1 ]; cksum += hdr[ 2 ]; RecLen = hdr[ 1 ] | ( hdr[ 2 ] << 8 ); ResizeBuff( RecLen ); RecPtr = RecBuff; if( fread( RecBuff, RecLen, 1, fp ) == 0 ) { break; } cksum += checkSumBuff(); IsMS386 = hdr[ 0 ] & 1; if( IsMS386 ) { IsIntel = FALSE; } no_disp = ( rec_count == 0 ) ? FALSE : TRUE; for( i = 0; i < rec_count; i++ ) { if( rec_type[ i ] == ( hdr[ 0 ] & ~1 )) { no_disp = FALSE; break; } } recname = RecNumberToName( hdr[ 0 ] ); cksum = -( cksum - RecBuff[ RecLen - 1 ] ); Output( CRLF "%s%s(%2) recnum:%u, offset:%X, len:%x, chksum:%b(%2)" CRLF, recname, IsMS386 ? "386" : "", hdr[ 0 ], ++RecNum, offset, RecLen, RecBuff[ RecLen - 1 ], cksum ); RecLen--; if( setjmp( BailOutJmp ) == 0 ) { switch( hdr[ 0 ] & ~1 ) { case CMD_RHEADR: ProcRHeadr(); break; case CMD_ENDREC: ProcEndRec(); break; case CMD_THEADR: ProcTHeadr( first ); first = 0; break; case CMD_LHEADR: ProcLHeadr(); break; case CMD_COMENT: ProcComent(); break; case CMD_MODEND: ProcModEnd(); if( page_len != 0 ) { offset = ftell( fp ); offset = page_len - offset % page_len; if( offset != page_len ) { total_padding += offset; fseek( fp, offset, SEEK_CUR ); } } first = 1; break; case CMD_STATIC_EXTDEF: /* fall through */ case CMD_EXTDEF: ProcExtNames(); break; case CMD_STATIC_PUBDEF: /* fall through */ case CMD_PUBDEF: ProcPubDefs(); break; case CMD_LOCSYM: ProcLocSyms(); break; case CMD_LINNUM: ProcLinNums(); break; case CMD_LLNAME: /* fall through */ case CMD_LNAMES: ProcLNames( &Nameindex ); break; case CMD_SEGDEF: ProcSegDefs(); break; case CMD_GRPDEF: ProcGrpDef(); break; case CMD_FIXUP: ProcFixup(); break; case CMD_LEDATA: ProcLedata(); break; case CMD_LIDATA: ProcLidata(); break; case CMD_LIBNAM: ProcNames( &Libindex ); break; case CMD_STATIC_COMDEF: /* fall through */ case CMD_COMDEF: ProcComDef(); break; case CMD_BAKPAT: ProcBackPat(); break; case CMD_CEXTDF: ProcComExtDef(); break; case CMD_COMDAT: ProcComDat(); break; case CMD_LINSYM: ProcLineSym(); break; case CMD_ALIAS: ProcAlias(); break; case CMD_NBKPAT: ProcNameBackPat(); break; case CMD_VERNUM: ProcVerNum(); break; case CMD_VENDEXT: ProcVendExt(); break; case LIB_HEADER_REC: if( hdr[ 0 ] & 1 ) { /* LIB_TRAILER_REC */ ProcLibTrailer( fp ); fseek( fp, 0L, SEEK_END ); page_len = 0; } else { page_len = RecLen + 4; ProcLibHeader(); } break; default: if( !raw_dump ) { OutputData( 0L, 0L ); } break; } } else { /* something bailed out... */ if( raw_dump ) { Output( INDENT "Error at offset %x" CRLF, (unsigned_32)(pointer_int)RecOffset ); } else if( !EndRec() ) { Output( INDENT "Remainder of record follows:" CRLF ); OutputData( (unsigned_32)RecOffset(), 0L ); } else { Output( INDENT "End of record" CRLF ); } } if( raw_dump ) { RecPtr = RecBuff; Output( "====================RAW DUMP===============================================" CRLF ); OutputData( 0L, 0L ); Output( "====================RAW DUMP===============================================" CRLF ); } } if( total_padding > 0 ) { Output( CRLF "total padding=%X" CRLF, total_padding ); } if( TranslateIndex) { PrintNames(); } FreeGrpdefs(); FreeSegdefs(); FreeLnames(); FreeXnames(); free( RecBuff ); }
/* Output is a customized printf with the following format options: %c same as printf %c %s same as printf %s (string must be less than OUT_BUFF_WRITE) %R print remainder of RecBuff starting at RecPtr %N print NameLen chars from NamePtr (implicit arguments) %b same as printf %2.2xh %2 same as printf %2.2x %x same as printf %4.4xh %X same as printf %8.8xh %8 same as printf %8.8x %u same as printf %u %5 same as printf %5u %> arg is number of spaces to print, truncates to 80 spaces %< arg is minimum width of print up to this point (pads with spaces) %% print a % Output makes the assumption that % is not followed by the null- terminator. */ size_t Output( const char *fmt, ... ) { va_list args; char *p; const char *probe; const char *str; size_t len; char *pcrlf; if( no_disp ) return( 0 ); va_start( args, fmt ); p = outBuffPtr; for(;;) { probe = strchr( fmt, '%' ); if( probe == NULL ) { len = strlen( fmt ); memcpy( p, fmt, len ); p += len; break; } len = probe - fmt; if( len > 0 ) { memcpy( p, fmt, len ); p += len; } fmt = probe + 1; switch( *fmt ) { case 'c': *p++ = va_arg( args, int ); break; case 's': str = va_arg( args, const char * ); len = strlen( str ); memcpy( p, str, len ); p += len; break; case 'R': len = RecLen - RecOffset(); if( len > OUT_BUFF_WRITE ) { len = OUT_BUFF_WRITE; } memcpy( p, RecPtr, len ); p += len; break; case 'N': *p++ = '\''; memcpy( p, NamePtr, NameLen ); p += NameLen; *p++ = '\''; break; case 'b': p = toHex2( p, va_arg( args, unsigned ) ); *p++ = 'h'; break; case '2': p = toHex2( p, va_arg( args, unsigned ) ); break; case 'x': p = toHex4( p, va_arg( args, unsigned ) ); *p++ = 'h'; break; case 'X': p = toHex8( p, va_arg( args, unsigned_32 ) ); *p++ = 'h'; break; case '8': p = toHex8( p, va_arg( args, unsigned_32 ) ); break; case 'u': p = toDec16( p, va_arg( args, unsigned ) ); break; case '5': p = to5Dec16( p, va_arg( args, unsigned ) ); break; case '<': len = va_arg( args, unsigned ); while( p - outBuffPtr < len ) { *p++ = ' '; } break; case '>': len = va_arg( args, unsigned ); if( len > 80 ) { len = 80; } memset( p, ' ', len ); p += len; break; default: *p++ = *fmt; break; } ++fmt; } va_end( args ); outBuffPtr = p; len = p - outBuff; *p = '\0'; /* for following str.. function */ pcrlf = strrchr( outBuff, '\n' ); /* need CRLF as char not string */ if( pcrlf != NULL ) { col = p - pcrlf; } else { col += len; } if( len > OUT_BUFF_WRITE ) flush(); return( col ); }