Annotation of 42BSD/ucb/finger.c, revision 1.1.1.1

1.1       root        1: #ifndef lint
                      2: static char *sccsid = "@(#)finger.c    4.5 (Berkeley) 9/16/83";
                      3: #endif
                      4: 
                      5: /*  This is a finger program.  It prints out useful information about users
                      6:  *  by digging it up from various system files.  It is not very portable
                      7:  *  because the most useful parts of the information (the full user name,
                      8:  *  office, and phone numbers) are all stored in the VAX-unused gecos field
                      9:  *  of /etc/passwd, which, unfortunately, other UNIXes use for other things.
                     10:  *
                     11:  *  There are three output formats, all of which give login name, teletype
                     12:  *  line number, and login time.  The short output format is reminiscent
                     13:  *  of finger on ITS, and gives one line of information per user containing
                     14:  *  in addition to the minimum basic requirements (MBR), the full name of
                     15:  *  the user, his idle time and office location and phone number.  The
                     16:  *  quick style output is UNIX who-like, giving only name, teletype and
                     17:  *  login time.  Finally, the long style output give the same information
                     18:  *  as the short (in more legible format), the home directory and shell
                     19:  *  of the user, and, if it exits, a copy of the file .plan in the users
                     20:  *  home directory.  Finger may be called with or without a list of people
                     21:  *  to finger -- if no list is given, all the people currently logged in
                     22:  *  are fingered.
                     23:  *
                     24:  *  The program is validly called by one of the following:
                     25:  *
                     26:  *     finger                  {short form list of users}
                     27:  *     finger -l               {long form list of users}
                     28:  *     finger -b               {briefer long form list of users}
                     29:  *     finger -q               {quick list of users}
                     30:  *     finger -i               {quick list of users with idle times}
                     31:  *     finger namelist         {long format list of specified users}
                     32:  *     finger -s namelist      {short format list of specified users}
                     33:  *     finger -w namelist      {narrow short format list of specified users}
                     34:  *
                     35:  *  where 'namelist' is a list of users login names.
                     36:  *  The other options can all be given after one '-', or each can have its
                     37:  *  own '-'.  The -f option disables the printing of headers for short and
                     38:  *  quick outputs.  The -b option briefens long format outputs.  The -p
                     39:  *  option turns off plans for long format outputs.
                     40:  */
                     41: 
                     42: #include       <sys/types.h>
                     43: #include       <sys/stat.h>
                     44: #include       <sgtty.h>
                     45: #include       <utmp.h>
                     46: #include       <signal.h>
                     47: #include       <pwd.h>
                     48: #include       <stdio.h>
                     49: #include       <lastlog.h>
                     50: #include       <sys/time.h>
                     51: 
                     52: struct utmp    utmp;   /* for sizeof */
                     53: #define NMAX sizeof(utmp.ut_name)
                     54: #define LMAX sizeof(utmp.ut_line)
                     55: 
                     56: #define                ASTERISK        '*'     /* ignore this in real name */
                     57: #define                BLANK           ' '     /* blank character (i.e. space) */
                     58: #define                CAPITALIZE      0137&   /* capitalize character macro */
                     59: #define                COMMA           ','     /* separator in pw_gecos field */
                     60: #define                COMMAND         '-'     /* command line flag char */
                     61: #define                CORY            'C'     /* cory hall office */
                     62: #define                EVANS           'E'     /* evans hall office */
                     63: #define                LINEBREAK       012     /* line feed */
                     64: #define                NULLSTR         ""      /* the null string, opposed to NULL */
                     65: #define                SAMENAME        '&'     /* repeat login name in real name */
                     66: #define                TALKABLE        0222    /* tty is writeable if 222 mode */
                     67: 
                     68: struct  person  {                      /* one for each person fingered */
                     69:        char            name[NMAX+1];   /* login name */
                     70:        char            tty[LMAX+1];    /* NULL terminated tty line */
                     71:        long            loginat;        /* time of login (possibly last) */
                     72:        long            idletime;       /* how long idle (if logged in) */
                     73:        short int       loggedin;       /* flag for being logged in */
                     74:        short int       writeable;      /* flag for tty being writeable */
                     75:        char            *realname;      /* pointer to full name */
                     76:        char            *office;        /* pointer to office name */
                     77:        char            *officephone;   /* pointer to office phone no. */
                     78:        char            *homephone;     /* pointer to home phone no. */
                     79:        char            *random;        /* for any random stuff in pw_gecos */
                     80:        struct  passwd  *pwd;           /* structure of /etc/passwd stuff */
                     81:        struct  person  *link;          /* link to next person */
                     82: };
                     83: 
                     84: struct  passwd                 *NILPWD = 0;
                     85: struct  person                 *NILPERS = 0;
                     86: 
                     87: int            persize         = sizeof( struct person );
                     88: int            pwdsize         = sizeof( struct passwd );
                     89: 
                     90: char           LASTLOG[]       = "/usr/adm/lastlog";   /* last login info */
                     91: char           USERLOG[]       = "/etc/utmp";          /* who is logged in */
                     92: char           outbuf[BUFSIZ];                         /* output buffer */
                     93: char           *ctime();
                     94: 
                     95: int            unbrief         = 1;            /* -b option default */
                     96: int            header          = 1;            /* -f option default */
                     97: int            hack            = 1;            /* -h option default */
                     98: int            idle            = 0;            /* -i option default */
                     99: int            large           = 0;            /* -l option default */
                    100: int            match           = 1;            /* -m option default */
                    101: int            plan            = 1;            /* -p option default */
                    102: int            unquick         = 1;            /* -q option default */
                    103: int            small           = 0;            /* -s option default */
                    104: int            wide            = 1;            /* -w option default */
                    105: 
                    106: int            lf;
                    107: int            llopenerr;
                    108: 
                    109: long           tloc;                           /* current time */
                    110: 
                    111: 
                    112: 
                    113: main( argc, argv )
                    114: 
                    115:     int                argc;
                    116:     char       *argv[];
                    117: 
                    118: {
                    119:        FILE                    *fp,  *fopen();         /* for plans */
                    120:        struct  passwd          *getpwent();            /* read /etc/passwd */
                    121:        struct  person          *person1,  *p,  *pend;  /* people */
                    122:        struct  passwd          *pw;                    /* temporary */
                    123:        struct  utmp            user;                   /*   ditto   */
                    124:        char                    *malloc();
                    125:        char                    *s,  *pn,  *ln;
                    126:        char                    c;
                    127:        char                    *PLAN = "/.plan";       /* what plan file is */
                    128:        char                    *PROJ = "/.project";    /* what project file */
                    129:        int                     PLANLEN = strlen( PLAN );
                    130:        int                     PROJLEN = strlen( PROJ );
                    131:        int                     numnames = 0;
                    132:        int                     orgnumnames;
                    133:        int                     uf;
                    134:        int                     usize = sizeof user;
                    135:        int                     unshort;
                    136:        int                     i, j;
                    137:        int                     fngrlogin;
                    138: 
                    139:        setbuf( stdout, outbuf );                       /* buffer output */
                    140: 
                    141:     /*  parse command line for (optional) arguments */
                    142: 
                    143:        i = 1;
                    144:        if(  strcmp( *argv, "sh" )  )  {
                    145:            fngrlogin = 0;
                    146:            while( i++ < argc  &&  (*++argv)[0] == COMMAND )  {
                    147:                for( s = argv[0] + 1; *s != NULL; s++ )  {
                    148:                        switch  (*s)  {
                    149: 
                    150:                            case 'b':
                    151:                                    unbrief = 0;
                    152:                                    break;
                    153: 
                    154:                            case 'f':
                    155:                                    header = 0;
                    156:                                    break;
                    157: 
                    158:                            case 'h':
                    159:                                    hack = 0;
                    160:                                    break;
                    161: 
                    162:                            case 'i':
                    163:                                    idle = 1;
                    164:                                    unquick = 0;
                    165:                                    break;
                    166: 
                    167:                            case 'l':
                    168:                                    large = 1;
                    169:                                    break;
                    170: 
                    171:                            case 'm':
                    172:                                    match = 0;
                    173:                                    break;
                    174: 
                    175:                            case 'p':
                    176:                                    plan = 0;
                    177:                                    break;
                    178: 
                    179:                            case 'q':
                    180:                                    unquick = 0;
                    181:                                    break;
                    182: 
                    183:                            case 's':
                    184:                                    small = 1;
                    185:                                    break;
                    186: 
                    187:                            case 'w':
                    188:                                    wide = 0;
                    189:                                    break;
                    190: 
                    191:                            default:
                    192:                                fprintf( stderr, "finger: Usage -- 'finger [-bfhilmpqsw] [login1 [login2 ...] ]'\n" );
                    193:                                exit( 1 );
                    194:                        }
                    195:                }
                    196:            }
                    197:        }
                    198:        else  {
                    199:            fngrlogin = 1;
                    200:        }
                    201:        if( unquick )  {
                    202:            time( &tloc );
                    203:        }
                    204:        else  {
                    205:            if( idle )  {
                    206:                time( &tloc );
                    207:            }
                    208:        }
                    209: 
                    210:     /*  i > argc means no login names given so get them by reading USERLOG */
                    211: 
                    212:        if(  (i > argc)  ||  fngrlogin  )  {
                    213:            unshort = large;
                    214:            if(  ( uf = open(USERLOG, 0) ) >= 0  )  {
                    215:                user.ut_name[0] = NULL;
                    216:                while( user.ut_name[0] == NULL )  {
                    217:                    if( read( uf, (char *) &user, usize ) != usize )  {
                    218:                        printf( "\nNo one logged on\n" );
                    219:                        exit( 0 );
                    220:                    }
                    221:                }
                    222:                person1 = (struct person  *) malloc( persize );
                    223:                for( j = 0; j < NMAX; j++ )  {
                    224:                    person1->tty[j] = user.ut_line[j];
                    225:                    person1->name[j] = user.ut_name[j];
                    226:                }
                    227:                person1->name[NMAX] = NULL;
                    228:                person1->tty[NMAX] = NULL;
                    229:                person1->loginat = user.ut_time;
                    230:                person1->pwd = NILPWD;
                    231:                person1->loggedin = 1;
                    232:                numnames++;
                    233:                p = person1;
                    234:                while( read( uf, (char *) &user, usize ) == usize )  {
                    235:                    if( user.ut_name[0] == NULL )  continue;
                    236:                    p->link = (struct person  *) malloc( persize );
                    237:                    p = p->link;
                    238:                    for( j = 0; j < NMAX; j++ )  {
                    239:                        p->tty[j] = user.ut_line[j];
                    240:                        p->name[j] = user.ut_name[j];
                    241:                    }
                    242:                    p->name[NMAX] = NULL;
                    243:                    p->tty[NMAX] = NULL;
                    244:                    p->loginat = user.ut_time;
                    245:                    p->pwd = NILPWD;
                    246:                    p->loggedin = 1;
                    247:                    numnames++;
                    248:                }
                    249:                p->link = NILPERS;
                    250:                close( uf );
                    251:            }
                    252:            else  {
                    253:                fprintf( stderr, "finger: error opening %s\n", USERLOG );
                    254:                exit( 2 );
                    255:            }
                    256: 
                    257:                /*  if we are doing it, read /etc/passwd for the useful info */
                    258: 
                    259:            if( unquick )  {
                    260:                setpwent();
                    261:                fwopen();
                    262:                i = numnames;
                    263:                while(  ( (pw = getpwent()) != NILPWD )  &&  ( i > 0 )  )  {
                    264:                    p = person1;
                    265:                    do  {
                    266:                        if( p->pwd == NILPWD )  {
                    267:                            if(  strcmp( p->name, pw->pw_name ) == 0  )  {
                    268:                                p->pwd = (struct passwd  *) malloc( pwdsize );
                    269:                                pwdcopy( p->pwd, pw );
                    270:                                decode( p );
                    271:                                i--;
                    272:                            }
                    273:                        }
                    274:                        p = p->link;
                    275:                    }  while( p != NILPERS );
                    276:                }
                    277:                fwclose();
                    278:                endpwent();
                    279:            }
                    280:        }
                    281: 
                    282:     /* get names from command line and check to see if they're  logged in */
                    283: 
                    284:        else  {
                    285:            unshort = ( small == 1 ? 0 : 1 );
                    286:            i++;
                    287:            person1 = (struct person  *) malloc( persize );
                    288:            strcpy(  person1->name, (argv++)[ 0 ]  );
                    289:            person1->loggedin = 0;
                    290:            person1->pwd = NILPWD;
                    291:            numnames++;
                    292:            p = person1;
                    293:            while( i++ <= argc )  {
                    294:                p->link = (struct person  *) malloc( persize );
                    295:                p = p->link;
                    296:                strcpy(  p->name, (argv++)[ 0 ]  );
                    297:                p->loggedin = 0;
                    298:                p->pwd = NILPWD;
                    299:                numnames++;
                    300:            }
                    301:            p->link = NILPERS;
                    302:            pend = p;
                    303: 
                    304:                /*  if we are doing it, read /etc/passwd for the useful info */
                    305: 
                    306:            orgnumnames = numnames;
                    307:            if( unquick )  {
                    308:                setpwent();
                    309:                while(  ( pw = getpwent() ) != NILPWD  )  {
                    310:                    p = person1;
                    311:                    i = 0;
                    312:                    do  {
                    313:                        if( strcmp( p->name, pw->pw_name ) == 0    ||
                    314:                            matchcmp( pw->pw_gecos, pw->pw_name, p->name ) )  {
                    315:                            if( p->pwd == NILPWD )  {
                    316:                                p->pwd = (struct passwd  *) malloc( pwdsize );
                    317:                                pwdcopy( p->pwd, pw );
                    318:                            }
                    319:                            else  {     /* handle multiple logins -- append new
                    320:                                           "duplicate" entry to end of list */
                    321:                                pend->link = (struct person  *) malloc(persize);
                    322:                                pend = pend->link;
                    323:                                pend->link = NILPERS;
                    324:                                strcpy( pend->name, p->name );
                    325:                                pend->pwd = (struct passwd  *) malloc(pwdsize);
                    326:                                pwdcopy( pend->pwd, pw );
                    327:                                numnames++;
                    328:                            }
                    329:                        }
                    330:                        p = p->link;
                    331:                    }  while( ++i < orgnumnames );
                    332:                }
                    333:                endpwent();
                    334:            }
                    335: 
                    336:                /*  Now get login information */
                    337: 
                    338:            if(  ( uf = open(USERLOG, 0) ) >= 0  )  {
                    339:                while( read( uf, (char *) &user, usize ) == usize )  {
                    340:                    if( user.ut_name[0] == NULL )  continue;
                    341:                    p = person1;
                    342:                    do  {
                    343:                        pw = p->pwd;
                    344:                        if( pw == NILPWD )  {
                    345:                            i = ( strcmp( p->name, user.ut_name ) ? 0 : NMAX );
                    346:                        }
                    347:                        else  {
                    348:                            i = 0;
                    349:                            while(  (i < NMAX)  &&
                    350:                                    ( pw->pw_name[i] == user.ut_name[i])  )  {
                    351:                                if( pw->pw_name[i] == NULL )  {
                    352:                                    i = NMAX;
                    353:                                    break;
                    354:                                }
                    355:                                i++;
                    356:                            }
                    357:                        }
                    358:                        if( i == NMAX )  {
                    359:                            if( p->loggedin == 1 )  {
                    360:                                pend->link = (struct person  *) malloc(persize);
                    361:                                pend = pend->link;
                    362:                                pend->link = NILPERS;
                    363:                                strcpy( pend->name, p->name );
                    364:                                for( j = 0; j < NMAX; j++ )  {
                    365:                                    pend->tty[j] = user.ut_line[j];
                    366:                                }
                    367:                                pend->tty[ NMAX ] = NULL;
                    368:                                pend->loginat = user.ut_time;
                    369:                                pend->loggedin = 2;
                    370:                                if(  pw == NILPWD  )  {
                    371:                                    pend ->pwd = NILPWD;
                    372:                                }
                    373:                                else  {
                    374:                                    pend->pwd = (struct passwd  *) malloc(pwdsize);
                    375:                                    pwdcopy( pend->pwd, pw );
                    376:                                }
                    377:                                numnames++;
                    378:                            }
                    379:                            else  {
                    380:                                if( p->loggedin != 2 )  {
                    381:                                    for( j = 0; j < NMAX; j++ )  {
                    382:                                        p->tty[j] = user.ut_line[j];
                    383:                                    }
                    384:                                    p->tty[ NMAX ] = NULL;
                    385:                                    p->loginat = user.ut_time;
                    386:                                    p->loggedin = 1;
                    387:                                }
                    388:                            }
                    389:                        }
                    390:                        p = p->link;
                    391:                    }  while( p != NILPERS );
                    392:                }
                    393:                fwopen();
                    394:                p = person1;
                    395:                while( p != NILPERS )  {
                    396:                    if( p->loggedin == 2 )  {
                    397:                        p->loggedin = 1;
                    398:                    }
                    399:                    decode( p );
                    400:                    p = p->link;
                    401:                }
                    402:                fwclose();
                    403:                close( uf );
                    404:            }
                    405:            else  {
                    406:                fprintf( stderr, "finger: error opening %s\n", USERLOG );
                    407:                exit( 2 );
                    408:            }
                    409:        }
                    410: 
                    411:     /* print out what we got */
                    412: 
                    413:        if( header )  {
                    414:            if( unquick )  {
                    415:                if( !unshort )  {
                    416:                    if( wide )  {
                    417:                        printf(
                    418: "Login       Name              TTY Idle    When            Office\n" );
                    419:                    }
                    420:                    else  {
                    421:                        printf(
                    422: "Login    TTY Idle    When            Office\n" );
                    423:                    }
                    424:                }
                    425:            }
                    426:            else  {
                    427:                printf( "Login      TTY            When" );
                    428:                if( idle )  {
                    429:                    printf( "             Idle" );
                    430:                }
                    431:                printf( "\n" );
                    432:            }
                    433:        }
                    434:        p = person1;
                    435:        do  {
                    436:            if( unquick )  {
                    437:                if( unshort )  {
                    438:                    personprint( p );
                    439:                    if( p->pwd != NILPWD )  {
                    440:                        if( hack )  {
                    441:                            s = malloc(strlen((p->pwd)->pw_dir) + PROJLEN + 1 );
                    442:                            strcpy(  s, (p->pwd)->pw_dir  );
                    443:                            strcat( s, PROJ );
                    444:                            if(  ( fp = fopen( s, "r") )  != NULL  )  {
                    445:                                printf( "Project: " );
                    446:                                while(  ( c = getc(fp) )  !=  EOF  )  {
                    447:                                    if( c == LINEBREAK )  {
                    448:                                        break;
                    449:                                    }
                    450:                                    putc( c, stdout );
                    451:                                }
                    452:                                fclose( fp );
                    453:                                printf( "\n" );
                    454:                            }
                    455:                        }
                    456:                        if( plan )  {
                    457:                            s = malloc( strlen( (p->pwd)->pw_dir ) + PLANLEN + 1 );
                    458:                            strcpy(  s, (p->pwd)->pw_dir  );
                    459:                            strcat( s, PLAN );
                    460:                            if(  ( fp = fopen( s, "r") )  == NULL  )  {
                    461:                                printf( "No Plan.\n" );
                    462:                            }
                    463:                            else  {
                    464:                                printf( "Plan:\n" );
                    465:                                while(  ( c = getc(fp) )  !=  EOF  )  {
                    466:                                    putc( c, stdout );
                    467:                                }
                    468:                                fclose( fp );
                    469:                            }
                    470:                        }
                    471:                    }
                    472:                    if( p->link != NILPERS )  {
                    473:                        printf( "\n" );
                    474:                    }
                    475:                }
                    476:                else  {
                    477:                    shortprint( p );
                    478:                }
                    479:            }
                    480:            else  {
                    481:                quickprint( p );
                    482:            }
                    483:            p = p->link;
                    484:        }  while( p != NILPERS );
                    485:        exit(0);
                    486: }
                    487: 
                    488: 
                    489: /*  given a pointer to a pwd (pfrom) copy it to another one, allocating
                    490:  *  space for all the stuff in it.  Note: Only the useful (what the
                    491:  *  program currently uses) things are copied.
                    492:  */
                    493: 
                    494: pwdcopy( pto, pfrom )          /* copy relevant fields only */
                    495: 
                    496:     struct  passwd             *pto,  *pfrom;
                    497: {
                    498:        pto->pw_name = malloc(  strlen( pfrom->pw_name ) + 1  );
                    499:        strcpy( pto->pw_name, pfrom->pw_name );
                    500:        pto->pw_uid = pfrom->pw_uid;
                    501:        pto->pw_gecos = malloc(  strlen( pfrom->pw_gecos ) + 1  );
                    502:        strcpy( pto->pw_gecos, pfrom->pw_gecos );
                    503:        pto->pw_dir = malloc(  strlen( pfrom->pw_dir ) + 1  );
                    504:        strcpy( pto->pw_dir, pfrom->pw_dir );
                    505:        pto->pw_shell = malloc(  strlen( pfrom->pw_shell ) + 1  );
                    506:        strcpy( pto->pw_shell, pfrom->pw_shell );
                    507: }
                    508: 
                    509: 
                    510: /*  print out information on quick format giving just name, tty, login time
                    511:  *  and idle time if idle is set.
                    512:  */
                    513: 
                    514: quickprint( pers )
                    515: 
                    516:     struct  person             *pers;
                    517: {
                    518:        int                     idleprinted;
                    519: 
                    520:        printf( "%-*.*s", NMAX, NMAX, pers->name );
                    521:        printf( "  " );
                    522:        if( pers->loggedin )  {
                    523:            if( idle )  {
                    524:                findidle( pers );
                    525:                if( pers->writeable )  {
                    526:                    printf(  " %-*.*s %-16.16s", LMAX, LMAX, 
                    527:                        pers->tty, ctime( &pers->loginat )  );
                    528:                }
                    529:                else  {
                    530:                    printf(  "*%-*.*s %-16.16s", LMAX, LMAX, 
                    531:                        pers->tty, ctime( &pers->loginat )  );
                    532:                }
                    533:                printf( "   " );
                    534:                idleprinted = ltimeprint( &pers->idletime );
                    535:            }
                    536:            else  {
                    537:                printf(  " %-*.*s %-16.16s", LMAX, LMAX, 
                    538:                    pers->tty, ctime( &pers->loginat )  );
                    539:            }
                    540:        }
                    541:        else  {
                    542:            printf( "          Not Logged In" );
                    543:        }
                    544:        printf( "\n" );
                    545: }
                    546: 
                    547: 
                    548: /*  print out information in short format, giving login name, full name,
                    549:  *  tty, idle time, login time, office location and phone.
                    550:  */
                    551: 
                    552: shortprint( pers )
                    553: 
                    554:     struct  person     *pers;
                    555: 
                    556: {
                    557:        struct  passwd          *pwdt = pers->pwd;
                    558:        char                    buf[ 26 ];
                    559:        int                     i,  len,  offset,  dialup;
                    560: 
                    561:        if( pwdt == NILPWD )  {
                    562:            printf( "%-*.*s", NMAX, NMAX,  pers->name );
                    563:            printf( "       ???\n" );
                    564:            return;
                    565:        }
                    566:        printf( "%-*.*s", NMAX, NMAX,  pwdt->pw_name );
                    567:        dialup = 0;
                    568:        if( wide )  {
                    569:            if(  strlen( pers->realname ) > 0  )  {
                    570:                printf( " %-20.20s", pers->realname );
                    571:            }
                    572:            else  {
                    573:                printf( "        ???          " );
                    574:            }
                    575:        }
                    576:        if( pers->loggedin )  {
                    577:            if( pers->writeable )  {
                    578:                printf( "  " );
                    579:            }
                    580:            else  {
                    581:                printf( " *" );
                    582:            }
                    583:        }
                    584:        else  {
                    585:            printf( "  " );
                    586:        }
                    587:        if(  strlen( pers->tty ) > 0  )  {
                    588:            strcpy( buf, pers->tty );
                    589:            if(  (buf[0] == 't')  &&  (buf[1] == 't')  &&  (buf[2] == 'y')  )  {
                    590:                offset = 3;
                    591:                for( i = 0; i < 2; i++ )  {
                    592:                    buf[i] = buf[i + offset];
                    593:                }
                    594:            }
                    595:            if(  (buf[0] == 'd')  &&  pers->loggedin  )  {
                    596:                dialup = 1;
                    597:            }
                    598:            printf( "%-2.2s ", buf );
                    599:        }
                    600:        else  {
                    601:            printf( "   " );
                    602:        }
                    603:        strcpy(buf, ctime(&pers->loginat));
                    604:        if( pers->loggedin )  {
                    605:            stimeprint( &pers->idletime );
                    606:            offset = 7;
                    607:            for( i = 4; i < 19; i++ )  {
                    608:                buf[i] = buf[i + offset];
                    609:            }
                    610:            printf( " %-9.9s ", buf );
                    611:        }
                    612:        else if (pers->loginat == 0)
                    613:            printf(" < .  .  .  . >");
                    614:        else if (tloc - pers->loginat >= 180 * 24 * 60 * 60)
                    615:            printf( " <%-6.6s, %-4.4s>", buf+4, buf+20 );
                    616:        else
                    617:            printf(" <%-12.12s>", buf+4);
                    618:        len = strlen( pers->homephone );
                    619:        if(  dialup  &&  (len > 0)  )  {
                    620:            if( len == 8 )  {
                    621:                printf( "             " );
                    622:            }
                    623:            else  {
                    624:                if( len == 12 )  {
                    625:                    printf( "         " );
                    626:                }
                    627:                else {
                    628:                    for( i = 1; i <= 21 - len; i++ )  {
                    629:                        printf( " " );
                    630:                    }
                    631:                }
                    632:            }
                    633:            printf( "%s", pers->homephone );
                    634:        }
                    635:        else  {
                    636:            if(  strlen( pers->office ) > 0  )  {
                    637:                printf( " %-11.11s", pers->office );
                    638:                if(  strlen( pers->officephone ) > 0  )  {
                    639:                    printf( " %8.8s", pers->officephone );
                    640:                }
                    641:                else  {
                    642:                    if( len == 8 )  {
                    643:                        printf( " %8.8s", pers->homephone );
                    644:                    }
                    645:                }
                    646:            }
                    647:            else  {
                    648:                if(  strlen( pers->officephone ) > 0  )  {
                    649:                    printf( "             %8.8s", pers->officephone );
                    650:                }
                    651:                else  {
                    652:                    if( len == 8 )  {
                    653:                        printf( "             %8.8s", pers->homephone );
                    654:                    }
                    655:                    else  {
                    656:                        if( len == 12 )  {
                    657:                            printf( "         %12.12s", pers->homephone );
                    658:                        }
                    659:                    }
                    660:                }
                    661:            }
                    662:        }
                    663:        printf( "\n" );
                    664: }
                    665: 
                    666: 
                    667: /*  print out a person in long format giving all possible information.
                    668:  *  directory and shell are inhibited if unbrief is clear.
                    669:  */
                    670: 
                    671: personprint( pers )
                    672: 
                    673:     struct  person     *pers;
                    674: {
                    675:        struct  passwd          *pwdt = pers->pwd;
                    676:        int                     idleprinted;
                    677: 
                    678:        if( pwdt == NILPWD )  {
                    679:            printf( "Login name: %-10s", pers->name );
                    680:            printf( "                   " );
                    681:            printf( "In real life: ???\n");
                    682:            return;
                    683:        }
                    684:        printf( "Login name: %-10s", pwdt->pw_name );
                    685:        if( pers->loggedin )  {
                    686:            if( pers->writeable )  {
                    687:                printf( "                       " );
                    688:            }
                    689:            else  {
                    690:                printf( "       (messages off)  " );
                    691:            }
                    692:        }
                    693:        else  {
                    694:            printf( "                   " );
                    695:        }
                    696:        if(  strlen( pers->realname ) > 0  )  {
                    697:            printf( "In real life: %-s", pers->realname );
                    698:        }
                    699:        if(  strlen( pers->office ) > 0  )  {
                    700:            printf( "\nOffice: %-.11s", pers->office );
                    701:            if(  strlen( pers->officephone ) > 0  )  {
                    702:                printf( ", %s", pers->officephone );
                    703:                if(  strlen( pers->homephone ) > 0  )  {
                    704:                    printf( "           Home phone: %s", pers->homephone );
                    705:                }
                    706:                else  {
                    707:                    if(  strlen( pers->random ) > 0  )  {
                    708:                        printf( "       %s", pers->random );
                    709:                    }
                    710:                }
                    711:            }
                    712:            else  {
                    713:                if(  strlen( pers->homephone ) > 0  )  {
                    714:                    printf("                    Home phone: %s",pers->homephone);
                    715:                }
                    716:                if(  strlen( pers->random ) > 0  )  {
                    717:                    printf( "                   %s", pers->random );
                    718:                }
                    719:            }
                    720:        }
                    721:        else  {
                    722:            if(  strlen( pers->officephone ) > 0  )  {
                    723:                printf( "\nPhone: %s", pers->officephone );
                    724:                if(  strlen( pers->homephone ) > 0  )  {
                    725:                    printf( "\n, %s", pers->homephone );
                    726:                    if(  strlen( pers->random ) > 0  )  {
                    727:                        printf( ", %s", pers->random );
                    728:                    }
                    729:                }
                    730:                else  {
                    731:                    if(  strlen( pers->random ) > 0  )  {
                    732:                        printf( "\n, %s", pers->random );
                    733:                    }
                    734:                }
                    735:            }
                    736:            else  {
                    737:                if(  strlen( pers->homephone ) > 0  )  {
                    738:                    printf( "\nPhone: %s", pers->homephone );
                    739:                    if(  strlen( pers->random ) > 0  )  {
                    740:                        printf( ", %s", pers->random );
                    741:                    }
                    742:                }
                    743:                else  {
                    744:                    if(  strlen( pers->random ) > 0  )  {
                    745:                        printf( "\n%s", pers->random );
                    746:                    }
                    747:                }
                    748:            }
                    749:        }
                    750:        if( unbrief )  {
                    751:            printf( "\n" );
                    752:            printf( "Directory: %-25s", pwdt->pw_dir );
                    753:            if(  strlen( pwdt->pw_shell ) > 0  )  {
                    754:                printf( "       Shell: %-s", pwdt->pw_shell );
                    755:            }
                    756:        }
                    757:        if( pers->loggedin )  {
                    758:            register char *ep = ctime( &pers->loginat );
                    759:            printf("\nOn since %15.15s on %-*.*s        ", &ep[4], LMAX, LMAX, pers->tty );
                    760:            idleprinted = ltimeprint( &pers->idletime );
                    761:            if( idleprinted )  {
                    762:                printf( " Idle Time" );
                    763:            }
                    764:        }
                    765:        else if (pers->loginat == 0)
                    766:            printf("\nNever logged in.");
                    767:        else if (tloc - pers->loginat > 180 * 24 * 60 * 60) {
                    768:            register char *ep = ctime( &pers->loginat );
                    769:            printf("\nLast login %10.10s, %4.4s on %.*s", ep, ep+20, LMAX, pers->tty);
                    770:        }
                    771:        else  {
                    772:            register char *ep = ctime( &pers->loginat );
                    773:            printf("\nLast login %16.16s on %.*s", ep, LMAX, pers->tty );
                    774:        }
                    775:        printf( "\n" );
                    776: }
                    777: 
                    778: 
                    779: /*
                    780:  *  very hacky section of code to format phone numbers.  filled with
                    781:  *  magic constants like 4, 7 and 10.
                    782:  */
                    783: 
                    784: char  *phone( s, len )
                    785: 
                    786:     char               *s;
                    787:     int                        len;
                    788: {
                    789:        char            *strsave();
                    790:        char            fonebuf[ 15 ];
                    791:        int             i;
                    792: 
                    793:        switch(  len  )  {
                    794: 
                    795:            case  4:
                    796:                fonebuf[ 0 ] = ' ';
                    797:                fonebuf[ 1 ] = 'x';
                    798:                fonebuf[ 2 ] = '2';
                    799:                fonebuf[ 3 ] = '-';
                    800:                for( i = 0; i <= 3; i++ )  {
                    801:                    fonebuf[ 4 + i ] = *s++;
                    802:                }
                    803:                fonebuf[ 8 ] = NULL;
                    804:                return( strsave( &fonebuf[0] ) );
                    805:                break;
                    806: 
                    807:            case  7:
                    808:                for( i = 0; i <= 2; i++ )  {
                    809:                    fonebuf[ i ] = *s++;
                    810:                }
                    811:                fonebuf[ 3 ] = '-';
                    812:                for( i = 0; i <= 3; i++ )  {
                    813:                    fonebuf[ 4 + i ] = *s++;
                    814:                }
                    815:                fonebuf[ 8 ] = NULL;
                    816:                return( strsave( &fonebuf[0] ) );
                    817:                break;
                    818: 
                    819:            case 10:
                    820:                for( i = 0; i <= 2; i++ )  {
                    821:                    fonebuf[ i ] = *s++;
                    822:                }
                    823:                fonebuf[ 3 ] = '-';
                    824:                for( i = 0; i <= 2; i++ )  {
                    825:                    fonebuf[ 4 + i ] = *s++;
                    826:                }
                    827:                fonebuf[ 7 ] = '-';
                    828:                for( i = 0; i <= 3; i++ )  {
                    829:                    fonebuf[ 8 + i ] = *s++;
                    830:                }
                    831:                fonebuf[ 12 ] = NULL;
                    832:                return( strsave( &fonebuf[0] ) );
                    833:                break;
                    834: 
                    835:            default:
                    836:                fprintf( stderr, "finger: error in phone numbering\n" );
                    837:                return( strsave(s) );
                    838:                break;
                    839:        }
                    840: }
                    841: 
                    842: 
                    843: /*  decode the information in the gecos field of /etc/passwd
                    844:  *  another hacky section of code, but given the format the stuff is in...
                    845:  */
                    846: 
                    847: decode( pers )
                    848: 
                    849:     struct  person     *pers;
                    850: 
                    851: {
                    852:        struct  passwd          *pwdt = pers->pwd;
                    853:        char                    buffer[ 256 ],  *bp,  *gp,  *lp;
                    854:        char                    *phone();
                    855:        int                     alldigits;
                    856:        int                     len;
                    857:        int                     i;
                    858: 
                    859:        pers->realname = NULLSTR;
                    860:        pers->office = NULLSTR;
                    861:        pers->officephone = NULLSTR;
                    862:        pers->homephone = NULLSTR;
                    863:        pers->random = NULLSTR;
                    864:        if(  pwdt != NILPWD )  {
                    865:            gp = pwdt->pw_gecos;
                    866:            bp = &buffer[ 0 ];
                    867:            if( *gp == ASTERISK )  {
                    868:                gp++;
                    869:            }
                    870:            while(  (*gp != NULL)  &&  (*gp != COMMA)  )  {     /* name */
                    871:                if( *gp == SAMENAME )  {
                    872:                    lp = pwdt->pw_name;
                    873:                    *bp++ = CAPITALIZE(*lp++);
                    874:                    while( *lp != NULL )  {
                    875:                        *bp++ = *lp++;
                    876:                    }
                    877:                }
                    878:                else  {
                    879:                    *bp++ = *gp;
                    880:                }
                    881:                gp++;
                    882:            }
                    883:            *bp = NULL;
                    884:            pers->realname = malloc( strlen( &buffer[0] ) + 1 );
                    885:            strcpy( pers->realname, &buffer[0] );
                    886:            if( *gp++ == COMMA )  {                     /* office, supposedly */
                    887:                alldigits = 1;
                    888:                bp = &buffer[ 0 ];
                    889:                while(  (*gp != NULL)  &&  (*gp != COMMA)  )  {
                    890:                    *bp = *gp++;
                    891:                    alldigits = alldigits && ('0' <= *bp) && (*bp <= '9');
                    892:                    bp++;
                    893:                }
                    894:                *bp = NULL;
                    895:                len = strlen( &buffer[0] );
                    896:                if( buffer[ len - 1 ]  ==  CORY )  {
                    897:                    strcpy( &buffer[ len - 1 ], " Cory" );
                    898:                    pers->office = malloc( len + 5 );
                    899:                    strcpy( pers->office, &buffer[0] );
                    900:                }
                    901:                else  {
                    902:                    if( buffer[ len - 1 ] == EVANS )  {
                    903:                        strcpy( &buffer[ len - 1 ], " Evans" );
                    904:                        pers->office = malloc( len + 6 );
                    905:                        strcpy( pers->office, &buffer[0] );
                    906:                    }
                    907:                    else  {
                    908:                        if( buffer[ len - 1 ] == 'L' )  {
                    909:                            strcpy( &buffer[ len - 1 ], " LBL" );
                    910:                            pers->office = malloc( len + 4 );
                    911:                            strcpy( pers->office, &buffer[0] );
                    912:                        }
                    913:                        else  {
                    914:                            if( alldigits )  {
                    915:                                if( len == 4 )  {
                    916:                                    pers->officephone = phone(&buffer[0], len);
                    917:                                }
                    918:                                else  {
                    919:                                    if(  (len == 7) || (len == 10)  )  {
                    920:                                        pers->homephone = phone(&buffer[0],len);
                    921:                                    }
                    922:                                }
                    923:                            }
                    924:                            else  {
                    925:                                pers->random = malloc( len + 1 );
                    926:                                strcpy( pers->random, &buffer[0] );
                    927:                            }
                    928:                        }
                    929:                    }
                    930:                }
                    931:                if( *gp++ == COMMA )  {     /* office phone, theoretically */
                    932:                    bp = &buffer[ 0 ];
                    933:                    alldigits = 1;
                    934:                    while(  (*gp != NULL)  &&  (*gp != COMMA)  )  {
                    935:                        *bp = *gp++;
                    936:                        alldigits = alldigits && ('0' <= *bp) && (*bp <= '9');
                    937:                        bp++;
                    938:                    }
                    939:                    *bp = NULL;
                    940:                    len = strlen( &buffer[0] );
                    941:                    if( alldigits )  {
                    942:                        if(  len != 4  )  {
                    943:                            if(  (len == 7) || (len == 10)  )  {
                    944:                                pers->homephone = phone( &buffer[0], len );
                    945:                            }
                    946:                            else  {
                    947:                                pers->random = malloc( len + 1 );
                    948:                                strcpy( pers->random, &buffer[0] );
                    949:                            }
                    950:                        }
                    951:                        else  {
                    952:                                pers->officephone = phone( &buffer[0], len );
                    953:                        }
                    954:                    }
                    955:                    else  {
                    956:                        pers->random = malloc( len + 1 );
                    957:                        strcpy( pers->random, &buffer[0] );
                    958:                    }
                    959:                    if( *gp++ == COMMA )  {             /* home phone?? */
                    960:                        bp = &buffer[ 0 ];
                    961:                        alldigits = 1;
                    962:                            while(  (*gp != NULL)  &&  (*gp != COMMA)  )  {
                    963:                                *bp = *gp++;
                    964:                                alldigits = alldigits && ('0' <= *bp) &&
                    965:                                                        (*bp <= '9');
                    966:                                bp++;
                    967:                            }
                    968:                        *bp = NULL;
                    969:                        len = strlen( &buffer[0] );
                    970:                        if( alldigits  &&  ( (len == 7) || (len == 10) )  )  {
                    971:                            if( *pers->homephone != NULL )  {
                    972:                                pers->officephone = pers->homephone;
                    973:                            }
                    974:                            pers->homephone = phone( &buffer[0], len );
                    975:                        }
                    976:                        else  {
                    977:                            pers->random = malloc( strlen( &buffer[0] ) + 1 );
                    978:                            strcpy( pers->random, &buffer[0] );
                    979:                        }
                    980:                    }
                    981:                }
                    982:            }
                    983:            if( pers->loggedin == 0 )  {
                    984:                findwhen( pers );
                    985:            }
                    986:            else  {
                    987:                findidle( pers );
                    988:            }
                    989:        }
                    990: }
                    991: 
                    992: 
                    993: /*  find the last log in of a user by checking the LASTLOG file.
                    994:  *  the entry is indexed by the uid, so this can only be done if
                    995:  *  the uid is known (which it isn't in quick mode)
                    996:  */
                    997: 
                    998: fwopen()
                    999: {
                   1000:        if(  ( lf = open(LASTLOG, 0) ) >= 0  )  {
                   1001:            llopenerr = 0;
                   1002:        }
                   1003:        else  {
                   1004:            fprintf( stderr, "finger: lastlog open error\n" );
                   1005:            llopenerr = 1;
                   1006:        }
                   1007: }
                   1008: 
                   1009: 
                   1010: findwhen( pers )
                   1011: 
                   1012:     struct  person     *pers;
                   1013: {
                   1014:        struct  passwd          *pwdt = pers->pwd;
                   1015:        struct  lastlog         ll;
                   1016:        int                     llsize = sizeof ll;
                   1017:        int                     i;
                   1018: 
                   1019:        if( !llopenerr )  {
                   1020:            lseek( lf, pwdt->pw_uid*llsize, 0 );
                   1021:            if ((i = read( lf, (char *) &ll, llsize )) == llsize) {
                   1022:                    for( i = 0; i < LMAX; i++ )  {
                   1023:                        pers->tty[ i ] = ll.ll_line[ i ];
                   1024:                    }
                   1025:                    pers->tty[ LMAX ] = NULL;
                   1026:                    pers->loginat = ll.ll_time;
                   1027:            }
                   1028:            else  {
                   1029:                if (i != 0)
                   1030:                        fprintf(stderr, "finger: lastlog read error\n");
                   1031:                pers->tty[ 0 ] = NULL;
                   1032:                pers->loginat = 0L;
                   1033:            }
                   1034:        }
                   1035:        else  {
                   1036:            pers->tty[ 0 ] = NULL;
                   1037:            pers->loginat = 0L;
                   1038:        }
                   1039: }
                   1040: 
                   1041: 
                   1042: fwclose()
                   1043: {
                   1044:        if( !llopenerr )  {
                   1045:            close( lf );
                   1046:        }
                   1047: }
                   1048: 
                   1049: 
                   1050: /*  find the idle time of a user by doing a stat on /dev/histty,
                   1051:  *  where histty has been gotten from USERLOG, supposedly.
                   1052:  */
                   1053: 
                   1054: findidle( pers )
                   1055: 
                   1056:     struct  person     *pers;
                   1057: {
                   1058:        struct  stat            ttystatus;
                   1059:        struct  passwd          *pwdt = pers->pwd;
                   1060:        char                    buffer[ 20 ];
                   1061:        char                    *TTY = "/dev/";
                   1062:        int                     TTYLEN = strlen( TTY );
                   1063:        int                     i;
                   1064: 
                   1065:        strcpy( &buffer[0], TTY );
                   1066:        i = 0;
                   1067:        do  {
                   1068:            buffer[ TTYLEN + i ] = pers->tty[ i ];
                   1069:        }  while( ++i <= LMAX );
                   1070:        if(  stat( &buffer[0], &ttystatus ) >= 0  )  {
                   1071:            time( &tloc );
                   1072:            if( tloc < ttystatus.st_atime )  {
                   1073:                pers->idletime = 0L;
                   1074:            }
                   1075:            else  {
                   1076:                pers->idletime = tloc - ttystatus.st_atime;
                   1077:            }
                   1078:            if(  (ttystatus.st_mode & TALKABLE) == TALKABLE  )  {
                   1079:                pers->writeable = 1;
                   1080:            }
                   1081:            else  {
                   1082:                pers->writeable = 0;
                   1083:            }
                   1084:        }
                   1085:        else  {
                   1086:            fprintf( stderr, "finger: error STATing %s\n", &buffer[0] );
                   1087:            exit( 4 );
                   1088:        }
                   1089: }
                   1090: 
                   1091: 
                   1092: /*  print idle time in short format; this program always prints 4 characters;
                   1093:  *  if the idle time is zero, it prints 4 blanks.
                   1094:  */
                   1095: 
                   1096: stimeprint( dt )
                   1097: 
                   1098:     long       *dt;
                   1099: {
                   1100:        struct  tm              *gmtime();
                   1101:        struct  tm              *delta;
                   1102: 
                   1103:        delta = gmtime( dt );
                   1104:        if( delta->tm_yday == 0 )  {
                   1105:            if( delta->tm_hour == 0 )  {
                   1106:                if( delta->tm_min >= 10 )  {
                   1107:                    printf( " %2.2d ", delta->tm_min );
                   1108:                }
                   1109:                else  {
                   1110:                    if( delta->tm_min == 0 )  {
                   1111:                        printf( "    " );
                   1112:                    }
                   1113:                    else  {
                   1114:                        printf( "  %1.1d ", delta->tm_min );
                   1115:                    }
                   1116:                }
                   1117:            }
                   1118:            else  {
                   1119:                if( delta->tm_hour >= 10 )  {
                   1120:                    printf( "%3.3d:", delta->tm_hour );
                   1121:                }
                   1122:                else  {
                   1123:                    printf( "%1.1d:%02.2d", delta->tm_hour, delta->tm_min );
                   1124:                }
                   1125:            }
                   1126:        }
                   1127:        else  {
                   1128:            printf( "%3dd", delta->tm_yday );
                   1129:        }
                   1130: }
                   1131: 
                   1132: 
                   1133: /*  print idle time in long format with care being taken not to pluralize
                   1134:  *  1 minutes or 1 hours or 1 days.
                   1135:  */
                   1136: 
                   1137: ltimeprint( dt )
                   1138: 
                   1139:     long       *dt;
                   1140: {
                   1141:        struct  tm              *gmtime();
                   1142:        struct  tm              *delta;
                   1143:        int                     printed = 1;
                   1144: 
                   1145:        delta = gmtime( dt );
                   1146:        if( delta->tm_yday == 0 )  {
                   1147:            if( delta->tm_hour == 0 )  {
                   1148:                if( delta->tm_min >= 10 )  {
                   1149:                    printf( "%2d minutes", delta->tm_min );
                   1150:                }
                   1151:                else  {
                   1152:                    if( delta->tm_min == 0 )  {
                   1153:                        if( delta->tm_sec > 10 )  {
                   1154:                            printf( "%2d seconds", delta->tm_sec );
                   1155:                        }
                   1156:                        else  {
                   1157:                            printed = 0;
                   1158:                        }
                   1159:                    }
                   1160:                    else  {
                   1161:                        if( delta->tm_min == 1 )  {
                   1162:                            if( delta->tm_sec == 1 )  {
                   1163:                                printf( "%1d minute %1d second",
                   1164:                                    delta->tm_min, delta->tm_sec );
                   1165:                            }
                   1166:                            else  {
                   1167:                                printf( "%1d minute %d seconds",
                   1168:                                    delta->tm_min, delta->tm_sec );
                   1169:                            }
                   1170:                        }
                   1171:                        else  {
                   1172:                            if( delta->tm_sec == 1 )  {
                   1173:                                printf( "%1d minutes %1d second",
                   1174:                                    delta->tm_min, delta->tm_sec );
                   1175:                            }
                   1176:                            else  {
                   1177:                                printf( "%1d minutes %d seconds",
                   1178:                                    delta->tm_min, delta->tm_sec );
                   1179:                            }
                   1180:                        }
                   1181:                    }
                   1182:                }
                   1183:            }
                   1184:            else  {
                   1185:                if( delta->tm_hour >= 10 )  {
                   1186:                    printf( "%2d hours", delta->tm_hour );
                   1187:                }
                   1188:                else  {
                   1189:                    if( delta->tm_hour == 1 )  {
                   1190:                        if( delta->tm_min == 1 )  {
                   1191:                            printf( "%1d hour %1d minute",
                   1192:                                delta->tm_hour, delta->tm_min );
                   1193:                        }
                   1194:                        else  {
                   1195:                            printf( "%1d hour %2d minutes",
                   1196:                                delta->tm_hour, delta->tm_min );
                   1197:                        }
                   1198:                    }
                   1199:                    else  {
                   1200:                        if( delta->tm_min == 1 )  {
                   1201:                            printf( "%1d hours %1d minute",
                   1202:                                delta->tm_hour, delta->tm_min );
                   1203:                        }
                   1204:                        else  {
                   1205:                            printf( "%1d hours %2d minutes",
                   1206:                                delta->tm_hour, delta->tm_min );
                   1207:                        }
                   1208:                    }
                   1209:                }
                   1210:            }
                   1211:        }
                   1212:        else  {
                   1213:                if( delta->tm_yday >= 10 )  {
                   1214:                    printf( "%2d days", delta->tm_yday );
                   1215:                }
                   1216:                else  {
                   1217:                    if( delta->tm_yday == 1 )  {
                   1218:                        if( delta->tm_hour == 1 )  {
                   1219:                            printf( "%1d day %1d hour",
                   1220:                                delta->tm_yday, delta->tm_hour );
                   1221:                        }
                   1222:                        else  {
                   1223:                            printf( "%1d day %2d hours",
                   1224:                                delta->tm_yday, delta->tm_hour );
                   1225:                        }
                   1226:                    }
                   1227:                    else  {
                   1228:                        if( delta->tm_hour == 1 )  {
                   1229:                            printf( "%1d days %1d hour",
                   1230:                                delta->tm_yday, delta->tm_hour );
                   1231:                        }
                   1232:                        else  {
                   1233:                            printf( "%1d days %2d hours",
                   1234:                                delta->tm_yday, delta->tm_hour );
                   1235:                        }
                   1236:                    }
                   1237:                }
                   1238:        }
                   1239:        return( printed );
                   1240: }
                   1241: 
                   1242: 
                   1243: matchcmp( gname, login, given )
                   1244: 
                   1245:     char               *gname;
                   1246:     char               *login;
                   1247:     char               *given;
                   1248: {
                   1249:        char            buffer[ 20 ];
                   1250:        char            c;
                   1251:        int             flag,  i,  unfound;
                   1252: 
                   1253:        if( !match )  {
                   1254:            return( 0 );
                   1255:        }
                   1256:        else  {
                   1257:            if(  namecmp( login, given )  )  {
                   1258:                return( 1 );
                   1259:            }
                   1260:            else if (*gname == '\0')
                   1261:                return (0);
                   1262:            else  {
                   1263:                if( *gname == ASTERISK )  {
                   1264:                    gname++;
                   1265:                }
                   1266:                flag = 1;
                   1267:                i = 0;
                   1268:                unfound = 1;
                   1269:                while(  unfound  )  {
                   1270:                    if( flag )  {
                   1271:                        c = *gname++;
                   1272:                        if( c == SAMENAME )  {
                   1273:                            flag = 0;
                   1274:                            c = *login++;
                   1275:                        }
                   1276:                        else  {
                   1277:                            unfound = (*gname != COMMA)  &&  (*gname != NULL);
                   1278:                        }
                   1279:                    }
                   1280:                    else {
                   1281:                        c = *login++;
                   1282:                        if( c == NULL )  {
                   1283:                            if(  (*gname == COMMA)  ||  (*gname == NULL)  )  {
                   1284:                                break;
                   1285:                            }
                   1286:                            else  {
                   1287:                                flag = 1;
                   1288:                                continue;
                   1289:                            }
                   1290:                        }
                   1291:                    }
                   1292:                    if( c == BLANK )  {
                   1293:                        buffer[i++] = NULL;
                   1294:                        if(  namecmp( buffer, given )  )  {
                   1295:                            return( 1 );
                   1296:                        }
                   1297:                        i = 0;
                   1298:                        flag = 1;
                   1299:                    }
                   1300:                    else  {
                   1301:                        buffer[ i++ ] = c;
                   1302:                    }
                   1303:                }
                   1304:                buffer[i++] = NULL;
                   1305:                if(  namecmp( buffer, given )  )  {
                   1306:                    return( 1 );
                   1307:                }
                   1308:                else  {
                   1309:                    return( 0 );
                   1310:                }
                   1311:            }
                   1312:        }
                   1313: }
                   1314: 
                   1315: 
                   1316: namecmp( name1, name2 )
                   1317: 
                   1318:     char               *name1;
                   1319:     char               *name2;
                   1320: {
                   1321:        char            c1,  c2;
                   1322: 
                   1323:        c1 = *name1;
                   1324:        if( (('A' <= c1) && (c1 <= 'Z')) || (('a' <= c1) && (c1 <= 'z')) )  {
                   1325:            c1 = CAPITALIZE( c1 );
                   1326:        }
                   1327:        c2 = *name2;
                   1328:        if( (('A' <= c2) && (c2 <= 'Z')) || (('a' <= c2) && (c2 <= 'z')) )  {
                   1329:            c2 = CAPITALIZE( c2 );
                   1330:        }
                   1331:        while( c1 == c2 )  {
                   1332:            if( c1 == NULL )  {
                   1333:                return( 1 );
                   1334:            }
                   1335:            c1 = *++name1;
                   1336:            if( (('A'<=c1) && (c1<='Z')) || (('a'<=c1) && (c1<='z')) )  {
                   1337:                c1 = CAPITALIZE( c1 );
                   1338:            }
                   1339:            c2 = *++name2;
                   1340:            if( (('A'<=c2) && (c2<='Z')) || (('a'<=c2) && (c2<='z')) )  {
                   1341:                c2 = CAPITALIZE( c2 );
                   1342:            }
                   1343:        }
                   1344:        if( *name1 == NULL )  {
                   1345:            while(  ('0' <= *name2)  &&  (*name2 <= '9')  )  {
                   1346:                name2++;
                   1347:            }
                   1348:            if( *name2 == NULL )  {
                   1349:                return( 1 );
                   1350:            }
                   1351:        }
                   1352:        else  {
                   1353:            if( *name2 == NULL )  {
                   1354:                while(  ('0' <= *name1)  &&  (*name1 <= '9')  )  {
                   1355:                    name1++;
                   1356:                }
                   1357:                if( *name1 == NULL )  {
                   1358:                    return( 1 );
                   1359:                }
                   1360:            }
                   1361:        }
                   1362:        return( 0 );
                   1363: }
                   1364: 
                   1365: 
                   1366: char  *strsave( s )
                   1367: 
                   1368:     char               *s;
                   1369: {
                   1370:        char            *malloc();
                   1371:        char            *p;
                   1372: 
                   1373:        p = malloc( strlen( s ) + 1 );
                   1374:        strcpy( p, s );
                   1375: }

unix.superglobalmegacorp.com

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