Annotation of coherent/d/bin/strings.c, revision 1.1

1.1     ! root        1: /**
        !             2:  *     strings -- prints out all the character strings in an executable file.
        !             3:  *
        !             4:  *     Usage: strings [-xaop] [-nnn] [file ...]
        !             5:  *
        !             6:  *     Options:
        !             7:  *              -x     print offset of each string in the file in hex
        !             8:  *              -a     print offset of each string in the file in ASCII
        !             9:  *              -o     print offset of each string in the file in octal
        !            10:  *              -p     mask out the parity bit
        !            11:  */
        !            12: 
        !            13: #include       <sys/stat.h>
        !            14: #include       <l.out.h>
        !            15: #include       <stdio.h>
        !            16: #include       <canon.h>
        !            17: #include       <ctype.h>
        !            18: 
        !            19: /* The lamentable <rico.h>... */
        !            20: #define        bool    char
        !            21: #define        TRUE    (0 == 0)
        !            22: #define        FALSE   (!TRUE)
        !            23: 
        !            24: int    nchars  = 4;    /* minimum character string length */
        !            25: 
        !            26: bool   flag;           /* input condition: FALSE for redirection, else TRUE */
        !            27: bool   aflag;          /* option flags:        ascii line numbering */
        !            28: bool   xflag;          /*                      hex   line numbering */
        !            29: bool   oflag;          /*                      octal line numbering */
        !            30: 
        !            31: int    pbit;           /* parity bit mask */
        !            32: long   addr;           /* current seek position in data space segment */
        !            33: long   count;          /* size of data space segment */
        !            34: char  * buff;          /* string to store beginning NCHARS
        !            35:                                        characters in character string */
        !            36: bool   printstr();
        !            37: bool   lookfor();
        !            38: 
        !            39: extern FILE    * freopen();
        !            40: extern char    * malloc();
        !            41: 
        !            42: 
        !            43: main( argc, argv )
        !            44: 
        !            45: int    argc;
        !            46: char  * argv[];
        !            47: 
        !            48: {
        !            49:        char    * malloc();
        !            50:        char    * s;
        !            51: 
        !            52:        while( (--argc > 0) && ((*++argv)[0] == '-') ) {
        !            53: 
        !            54:                /*
        !            55:                 * Read options declared.
        !            56:                 */
        !            57:                for( s = argv[0] + 1 ; *s != '\0'; s++ ) {
        !            58: 
        !            59:                        /*
        !            60:                         * Set minimum string length for recognizing
        !            61:                         * character strings.
        !            62:                         */
        !            63:                        if( isdigit( *s ) ) {
        !            64:                                if( (nchars = atoi( s )) <= 0 )
        !            65:                                        fatal( "string length must be greater than 0" );
        !            66: 
        !            67:                                break;
        !            68:                        }
        !            69: 
        !            70:                        /*
        !            71:                         * Set appropriate flags or bit mask according to
        !            72:                         * option declared.
        !            73:                         */
        !            74:                        switch( *s ) {
        !            75: 
        !            76:                        case 'x':
        !            77:                                if( aflag | oflag | xflag )
        !            78:                                        usage();
        !            79: 
        !            80:                                xflag = TRUE;
        !            81:                                break;
        !            82: 
        !            83:                        case 'a':
        !            84:                                if( aflag | oflag | xflag )
        !            85:                                        usage();
        !            86: 
        !            87:                                aflag = TRUE;
        !            88:                                break;
        !            89: 
        !            90:                        case 'o':
        !            91:                                if( aflag | oflag | xflag )
        !            92:                                        usage();
        !            93: 
        !            94:                                oflag = TRUE;
        !            95:                                break;
        !            96: 
        !            97:                        case 'p':
        !            98:                                pbit = 0200;
        !            99:                                break;
        !           100: 
        !           101:                        default:
        !           102:                                usage();
        !           103:                        }
        !           104:                }
        !           105:        }
        !           106: 
        !           107:        /*
        !           108:         * Get memory for string buffer.
        !           109:         */
        !           110:        if( (buff = malloc( nchars )) == NULL )
        !           111:                fatal( "not enough memory" );
        !           112: 
        !           113:        /*
        !           114:         * Set input condition:
        !           115:         *      FALSE if input is through indirection, else TRUE.
        !           116:         */
        !           117:        if( argc > 0 )
        !           118:                flag = TRUE;
        !           119:        else {
        !           120:                argc++;
        !           121:                flag = FALSE;
        !           122:        }
        !           123: 
        !           124:        /*
        !           125:         * Examine each file for strings of the required length.
        !           126:         */
        !           127:        while( argc-- ) {
        !           128: 
        !           129:                /*
        !           130:                 * Test for read permission in file.
        !           131:                 */
        !           132:                if( flag  &&  freopen( *argv, "r", stdin ) == NULL )
        !           133:                        fatal( "can't open %s", argv[0] );
        !           134: 
        !           135:                /*
        !           136:                 * Test if file is an executable file.
        !           137:                 */
        !           138:                if( checklout( stdin ) < 0 ) {
        !           139:                        if( flag ) {
        !           140:                                fprintf( stderr, "strings: '%s' not executable\n", *argv);
        !           141:                                ++argv;
        !           142:                                continue;
        !           143:                        }
        !           144:                        else {
        !           145:                                fprintf( stderr, "strings: not executable\n" );
        !           146:                                exit( 1 );
        !           147:                        }
        !           148:                }
        !           149: 
        !           150:                /*
        !           151:                 * Display file name if available.
        !           152:                 */
        !           153:                if( flag )
        !           154:                        fprintf( stderr, "%s:\n", *argv );
        !           155: 
        !           156:                /*
        !           157:                 * Display all character strings in file.
        !           158:                 */
        !           159:                while( printstr() )
        !           160:                        ;
        !           161: 
        !           162:                ++argv;
        !           163:        }
        !           164: 
        !           165:        free( buff );
        !           166:        exit( 0 );
        !           167: }
        !           168: 
        !           169: /**
        !           170:  * bool
        !           171:  * printstr()
        !           172:  *
        !           173:  *     Input:  None.
        !           174:  *
        !           175:  *     Action: Display character strings in file.
        !           176:  *
        !           177:  *     Return: FALSE on error or no character strings available,
        !           178:  *             otherwise TRUE.
        !           179:  *
        !           180:  *     Note:   None.
        !           181:  *
        !           182:  */
        !           183: 
        !           184: bool
        !           185: printstr()
        !           186: 
        !           187: {
        !           188:        char    c;
        !           189:        char  * p;
        !           190:        char  * q;
        !           191: 
        !           192:        p = buff;
        !           193:        q = p + nchars;
        !           194: 
        !           195:        /*
        !           196:         * Check if character strings are available in file.
        !           197:         */
        !           198:        if( ! lookfor() )
        !           199:                return( FALSE );
        !           200: 
        !           201:        /*
        !           202:         * Display line number according to the format option specified.
        !           203:         * Ignore if no format option is set.
        !           204:         */
        !           205:        if( aflag )
        !           206:                printf( "%-6D: ", addr-nchars );
        !           207: 
        !           208:        else if( oflag )
        !           209:                printf( "0%-6O: ", addr-nchars );
        !           210: 
        !           211:        else if( xflag )
        !           212:                printf( "0x%-6X: ", addr-nchars );
        !           213: 
        !           214:        /*
        !           215:         * Display printable characters found.
        !           216:         */
        !           217:        do {
        !           218:                putchar( *p++ );
        !           219:        } while( p < q );
        !           220: 
        !           221:        /*
        !           222:         * Display remaining printable characters in file.
        !           223:         */
        !           224:        for ( ;; ) {
        !           225:                if( --count <= 0L )
        !           226:                        return( FALSE );
        !           227: 
        !           228:                ++addr;
        !           229:                c = getchar();
        !           230: 
        !           231:                if( c == EOF )
        !           232:                        return( FALSE );
        !           233: 
        !           234:                if( ! (isascii( (c) & ~pbit ) &&  isprint( (c) & ~pbit )) )
        !           235:                        break;
        !           236: 
        !           237:                putchar( c );
        !           238:        }
        !           239: 
        !           240:        putchar( '\n' );
        !           241:        return( TRUE );
        !           242: }
        !           243: 
        !           244: /**
        !           245:  * bool
        !           246:  * lookfor()
        !           247:  *
        !           248:  *     Input:  None.
        !           249:  *
        !           250:  *     Action: Look for the first character string in file.
        !           251:  *
        !           252:  *     Return: TRUE if a character string is found, else FALSE.
        !           253:  *
        !           254:  *     Note:   None.
        !           255:  *
        !           256:  */
        !           257: 
        !           258: bool
        !           259: lookfor()
        !           260: 
        !           261: {
        !           262:        char    c;
        !           263:        char  * p;
        !           264:        char  * q;
        !           265: 
        !           266:        q = buff + nchars;
        !           267: 
        !           268:        for( ;; ) {
        !           269: 
        !           270:                /*
        !           271:                 * Seek in data space segment of file until a printable
        !           272:                 * character is encountered.
        !           273:                 */
        !           274:                do {
        !           275:                        if( --count <= 0L )
        !           276:                                return( FALSE );
        !           277: 
        !           278:                        ++addr;
        !           279:                        c = getchar();
        !           280: 
        !           281:                        if( c == EOF )
        !           282:                                return( FALSE );
        !           283: 
        !           284:                } while( ! (isascii( (c) & ~pbit ) && isprint( (c) & ~pbit )) );
        !           285: 
        !           286:                p = buff;
        !           287: 
        !           288:                /*
        !           289:                 * Check for valid character string.
        !           290:                 */
        !           291:                do {
        !           292:                        *p++ = c;
        !           293: 
        !           294:                        if( p >= q )
        !           295:                                return( TRUE );
        !           296: 
        !           297:                        if( --count <= 0L )
        !           298:                                return( FALSE );
        !           299: 
        !           300:                        ++addr;
        !           301:                        c = getchar();
        !           302: 
        !           303:                        if( c == EOF )
        !           304:                                return( FALSE );
        !           305: 
        !           306:                } while( isascii( (c) & ~pbit ) && isprint( (c) & ~pbit ) );
        !           307:        }
        !           308: }
        !           309: 
        !           310: 
        !           311: /**
        !           312:  * int
        !           313:  * checklout( f )
        !           314:  *
        !           315:  * register FILE * f;
        !           316:  *
        !           317:  *     Input:  f       - file pointer to stdin.
        !           318:  *
        !           319:  *     Action: Check if executable (l.out) file.
        !           320:  *
        !           321:  *     Return: Returns -1 on error or file is not executable, otherwise 0.
        !           322:  *
        !           323:  *     Note:   None.
        !           324:  *
        !           325:  */
        !           326: 
        !           327: int
        !           328: checklout( f )
        !           329: 
        !           330: register FILE  * f;
        !           331: 
        !           332: {
        !           333:        register int      i;            /* counter variable */
        !           334:        int               ret = -1;     /* returning error value */
        !           335:        struct   stat     s;            /* file attributes */
        !           336:        struct   ldheader l;            /* file header information */
        !           337: 
        !           338:        if( fstat( fileno( f ), &s ) == -1 )
        !           339:                return( ret );
        !           340: 
        !           341:        /*
        !           342:         * File type check. Return unless regular file.
        !           343:         */
        !           344:        if( (s.st_mode & S_IFMT) != S_IFREG )
        !           345:                return( ret );
        !           346: 
        !           347:        /*
        !           348:         * Get file header information.
        !           349:         */
        !           350:        if( fread( &l, sizeof( l ), 1, f ) != 1 ) {
        !           351:                rewind( f );
        !           352:                return( ret );
        !           353:        }
        !           354: 
        !           355:        rewind( f );
        !           356: 
        !           357:        if( l.l_magic != L_MAGIC )
        !           358:                return( ret );
        !           359: 
        !           360:        /*
        !           361:         * Correct canonical effect on file format information.
        !           362:         */
        !           363:        for( i = 0 ; i < NLSEG ; ++i )
        !           364:                canlong(l.l_ssize[i]);
        !           365: 
        !           366:        /*
        !           367:         * Get seek position to the beginning memory location of the
        !           368:         * data space segment in the executable file.
        !           369:         */
        !           370:        fseek( f, (long)sizeof(l) + l.l_ssize[L_SHRI] + l.l_ssize[L_PRVI], 0 );
        !           371:        addr = ftell( f );
        !           372: 
        !           373:        /*
        !           374:         * Get size of data space segment of file.
        !           375:         */
        !           376:        count = l.l_ssize[L_SHRD] + l.l_ssize[L_PRVD];
        !           377: 
        !           378:        if( count == 0L ) {
        !           379:                fatal( "zero-length data segments" );
        !           380:                /* NOTREACHED */
        !           381:        }
        !           382: 
        !           383:        ++count;
        !           384:        return( 0 );
        !           385: }
        !           386: 
        !           387: /**
        !           388:  * void
        !           389:  * fatal( arg0 )
        !           390:  *
        !           391:  * char        * arg0;
        !           392:  *
        !           393:  *     Input:  arg0    - pointer to string containing the error message.
        !           394:  *
        !           395:  *     Action: Display fatal error message and exit.
        !           396:  *
        !           397:  *     Return: Never return, always exit.
        !           398:  *
        !           399:  *     Note:   None.
        !           400:  *
        !           401:  */
        !           402: 
        !           403: fatal( arg0 )
        !           404: 
        !           405: char   * arg0;
        !           406: 
        !           407: {
        !           408:        fflush( stdout );
        !           409:        fprintf( stderr, "strings: %r\n", &arg0 );
        !           410:        exit( 1 );
        !           411: }
        !           412: 
        !           413: /**
        !           414:  * void
        !           415:  * usage()
        !           416:  *
        !           417:  *     Input:  None.
        !           418:  *
        !           419:  *     Action: Display command usage format.
        !           420:  *
        !           421:  *     Return: Never return, always exit.
        !           422:  *
        !           423:  *     Note:   None.
        !           424:  *
        !           425:  */
        !           426: 
        !           427: usage()
        !           428: 
        !           429: {
        !           430:        fprintf( stderr, "Usage: strings [-xaop] [-nnn] [file ...]\n" );
        !           431:        exit( 1 );
        !           432: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.