#include #include #include #define BUFLEN 16384 char buf[BUFLEN+2]; char rcl[4]; char rc2[4]; unsigned long packit( char x[4] ) { return (x[0] & 0x00ff) | ((x[1] << 8) & 0xff00) | ((x[2] << 16) & 0xff0000) | ((x[3] << 24) & 0xff000000); } int read_record( char buf[], unsigned int buf_size, FILE *fd ) { int n; char tbuf1[4]; char tbuf2[4]; int reclen1; int reclen2; n = fread( tbuf1, sizeof(char), 4, fd ); if( n == 0 ) { return -1; } if( n < 4 ) { fprintf( stderr, "Bad read length %d\n", n ); exit(1); } reclen1 = packit( tbuf1 ); if( reclen1 == 0 ) { return 0; } if( reclen1 > buf_size) { fprintf( stderr, "ERROR: tape record too big: %d max is %s\n", reclen1, buf_size ); exit(1); } n = fread( buf, sizeof(char), reclen1, fd ); if( n != reclen1 ) { fprintf( stderr, "ERROR: short read\n" ); exit(1); } /* ** check end count */ n = fread( tbuf2, sizeof(char), 4, fd ); if( n != 4 ) { fprintf( stderr, "ERROR: end length missing\n" ); exit(1); } reclen2 = packit( tbuf2 ); if( reclen1 != reclen2 ) { fprintf( stderr, "ERROR: record lengths do not match [%d,%d]\n", reclen1, reclen2 ); exit(1); } return reclen1; } void dump_buf( char buf[], int buf_len ) { int i,j; for( i = 0; i < buf_len; i += 16 ) { printf( " " ); for( j = 0; j < 16; j++ ) { if( (i+j) >= buf_len ) printf( "-- " ); else printf( "%02x ", (buf[i+j] & 0xff) ); } printf( " [" ); for( j = 0; j < 16; j++ ) { if( (i + j) >= buf_len ) printf( " " ); else if( (buf[i+j] < 32) || ((buf[i+j] & 0xff) >= 127) ) printf( " " ); else printf( "%c", buf[i+j] ); } printf( "]\n" ); } } int main( int argc, char *argv[] ) { unsigned int reclen; unsigned int reccnt; unsigned long byte_cnt; FILE *tp; reccnt = 0; byte_cnt = 0; if( argc < 2 ) { fprintf( stderr, "Usage: dumpit tape\n" ); exit(1); } if( (tp = fopen(argv[1],"r")) == NULL ) { fprintf( stderr, "FATAL: Can't open %s\n", argv[1] ); exit(1); } while( 1 ) { reclen = read_record( buf, BUFLEN, tp ); if( reclen < 0 ) { printf( "**** End of Tape\n" ); break; } else if( reclen == 0 ) { printf( "**** File Mark\n" ); continue; } byte_cnt += reclen; reccnt++; printf( "**** record %d size %d total size %ld\n", reccnt+1, reclen, byte_cnt ); dump_buf( buf, reclen ); } fclose(tp); return 0; }