Annotation of 3BSD/cmd/as/asmain.c, revision 1.1

1.1     ! root        1: /* Copyright (c) 1979 Regents of the University of California */
        !             2: #include <stdio.h>
        !             3: #include <signal.h>
        !             4: 
        !             5: #include "as.h"
        !             6: #include "assyms.h"
        !             7: #include "asexpr.h"
        !             8: #include "asscan.h"
        !             9: 
        !            10: int    curlen;
        !            11: /*
        !            12:  *     variables to manage the assembly input
        !            13:  */
        !            14: char   *dotsname;      /*the current file name; managed by the parser*/
        !            15: int    lineno;         /*current line number; managed by the parser*/
        !            16: int    silent;         /*don't complain about any errors*/
        !            17: int    savelabels;     /*write the labels to the a.out file*/
        !            18: 
        !            19: #ifdef DEBUG
        !            20: int    debug;
        !            21: int    toktrace;
        !            22: #endif
        !            23: 
        !            24: long   datbase;
        !            25: 
        !            26: char   *endcore;               /*where to get more symbol space*/
        !            27: 
        !            28: struct hdr hdr = {
        !            29:        0410, 0, 0, 0, 0, 0, 0, 0,
        !            30: };
        !            31: 
        !            32: #ifndef vax
        !            33: struct {short hiword; short loword;}; /* stupid fp-11 */
        !            34: #else
        !            35: #define writel(p,n,f) fwrite( (long) p, sizeof (long), n, f)
        !            36: #endif
        !            37: 
        !            38: char           *tmpn1;
        !            39: char           *tmpn2;
        !            40: char           *tmpn3;
        !            41: 
        !            42: struct exp     usedot[NLOC+NLOC];
        !            43: 
        !            44: FILE           *usefile[NLOC+NLOC];
        !            45: FILE           *rusefile[NLOC+NLOC];
        !            46: char           sibuf[TOKBUFLG];                /*buffer used for all input*/
        !            47: char           sobuf[TOKBUFLG];                /*buffer used for all output*/
        !            48:                                                /*except stdout and relfil*/
        !            49: char           stdoutbuf[BUFSIZ];              /*stdout buffer*/
        !            50: 
        !            51: extern int     njxxx;          /*number of jumpxxx  instructs*/
        !            52: extern int     d124;           /*allocate 1,2 or 4 bytes for unknowns*/
        !            53: 
        !            54: int delexit();
        !            55: 
        !            56: char           *innames[32];   /*names of the files being assembled*/
        !            57: int            ninfiles;       /*how many interesting files there are*/
        !            58: 
        !            59: main(argc, argv)
        !            60:        int     argc;
        !            61:        char    **argv;
        !            62: {
        !            63:        int             locindex;
        !            64:        long            v;
        !            65:        char            *outfile = "a.out";
        !            66:        int             filestep;
        !            67:        char            *cp;
        !            68: 
        !            69:        setbuf(stdout, stdoutbuf);
        !            70:        ninfiles = 0;
        !            71:        silent = 0;
        !            72:        useVM = 0;
        !            73: #ifdef DEBUG
        !            74:        debug = 0;
        !            75: #endif
        !            76:        /*
        !            77:         *      Give the error processor something to complain about
        !            78:         *      if there is an error processing an argument
        !            79:         */
        !            80:        dotsname = "<argv error>";
        !            81:        while (argc > 1) {
        !            82:                if (argv[1][0] == '-'){
        !            83:                        cp = argv[1] + 1;
        !            84:                        /*
        !            85:                         *      We can throw away single minus signs, so
        !            86:                         *      that make scripts for the PDP 11 assembler work
        !            87:                         *      on this assembler too
        !            88:                         */
        !            89:                        while (*cp){    
        !            90:                                switch(*cp++){
        !            91:                                 default:
        !            92:                                        yyerror("Unknown flag: %c", *--cp);
        !            93:                                        cp++;
        !            94:                                        break;
        !            95:                                 case 'd':
        !            96:                                        d124 = *cp++ - '0';
        !            97:                                        if ( (d124 != 1) && (d124 != 2) && 
        !            98:                                             (d124 != 4)){
        !            99:                                                yyerror("-d[124] only");
        !           100:                                                exit(1);
        !           101:                                        }
        !           102:                                        break;
        !           103:                                 case 'o':
        !           104:                                        if (argc < 3){
        !           105:                                                yyerror("-o what???");
        !           106:                                                exit(1);
        !           107:                                        }
        !           108:                                        outfile = argv[2];
        !           109:                                        argc -= 2;
        !           110:                                        argv += 2;
        !           111:                                        goto nextarg;
        !           112: 
        !           113:                                 case 'V':
        !           114:                                        useVM = 1;
        !           115:                                        break;
        !           116: #ifdef fooiearg
        !           117:                                 case 'M':
        !           118:                                        if (argc < 3){
        !           119:                                                yyerror("Mode what?");
        !           120:                                                exit(1);
        !           121:                                        }
        !           122:                                        hdr.magic = 0;
        !           123:                                        cp = argv[2];
        !           124:                                        while (*cp && ('0' <= *cp) && (*cp <= '7'))
        !           125:                                                hdr.magic = hdr.magic<<3 + *cp++ - '0';
        !           126:                                        argc -= 2;
        !           127:                                        argv += 2;
        !           128:                                        goto nextarg;
        !           129:                                 case 'W':      silent = 1;
        !           130:                                        break;
        !           131: #endif
        !           132: 
        !           133: #ifdef DEBUG
        !           134:                                 case 'D':      debug = 1;
        !           135:                                        break;
        !           136:                                 case 'T':      toktrace = 1;
        !           137:                                        break;
        !           138: #endif
        !           139: #ifdef METRIC
        !           140:                                 case 'C':      outcounters = 1;
        !           141:                                        break;
        !           142: #endif
        !           143:                                 case 'L':      savelabels = 1;
        !           144:                                        break;
        !           145:                                }       /*end of the switch*/
        !           146:                        }       /*end of pulling out all arguments*/
        !           147:                }       /*end of a flag argument*/
        !           148:                else {  /*file name*/
        !           149:                        if (ninfiles > 32){
        !           150:                                yyerror("More than 32 file names");
        !           151:                                exit(3);
        !           152:                        }
        !           153:                        innames[ninfiles++] = argv[1];
        !           154:                }
        !           155:                --argc; ++argv;
        !           156:           nextarg:;
        !           157:        }       /*end of looking at all of the arguments*/
        !           158:                                 
        !           159:        if (anyerrs)
        !           160:                exit(1);
        !           161: 
        !           162:        endcore = (char *)sbrk(0);
        !           163: 
        !           164:        /*
        !           165:         *      Install symbols in the table
        !           166:         */
        !           167:        symtabinit();
        !           168:        syminstall();
        !           169:        /*
        !           170:         *      mark usedot: first NLOC slots for named text segments,
        !           171:         *      the next for named data segments.
        !           172:         */
        !           173:        for (locindex=0; locindex<NLOC; locindex++) {
        !           174:                usedot[locindex].xtype = XTEXT;
        !           175:                usedot[locindex+NLOC].xtype = XDATA;
        !           176:        }
        !           177: 
        !           178:        if (signal(SIGINT, SIG_IGN) != SIG_IGN)
        !           179:                signal(SIGINT, delexit);
        !           180: 
        !           181:        tmpn1 = (char *)mktemp("/tmp/asXXXXX");
        !           182:        tmpfil = fopen(tmpn1, "w");
        !           183:        if (tmpfil==NULL) {
        !           184:                yyerror("Bad pass 1 temporary file for writing %s", tmpn1);
        !           185:                delexit();
        !           186:        }
        !           187:        setbuf(tmpfil,sobuf);
        !           188: 
        !           189:        inittmpfile();
        !           190:        buildtokensets();               /*sets to implement expression lookahead*/
        !           191: 
        !           192:        if (ninfiles == 0){             /*take the input from stdin directly*/
        !           193:                setbuf(stdin, sibuf);
        !           194:                lineno = 1;
        !           195:                dotsname = "<stdin>";
        !           196: 
        !           197:                yyparse();
        !           198:        } else {                /*we have the names tanked*/
        !           199:                for (filestep = 0; filestep < ninfiles; filestep++){
        !           200:                        new_dot_s(innames[filestep]);
        !           201:                        if (freopen(innames[filestep], "r", stdin) == NULL) {
        !           202:                                yyerror( "Can't open source file %s\n",
        !           203:                                        innames[filestep]);
        !           204:                                exit(2);
        !           205:                        }
        !           206:                        setbuf(stdin,sibuf);
        !           207: 
        !           208:                        yyparse();
        !           209:                }
        !           210:        }
        !           211: 
        !           212:        closetmpfile();         /*kick out the last buffered intermediate text*/
        !           213: 
        !           214:        if (anyerrs)
        !           215:                delexit();
        !           216: 
        !           217:        /*
        !           218:         *      Pass 1.5
        !           219:         */
        !           220:        sortsymtab();
        !           221: 
        !           222: #ifdef DEBUG
        !           223:        if (debug)
        !           224:                dumpsymtab();
        !           225: #endif
        !           226: 
        !           227:        jxxxfix();
        !           228: 
        !           229: #ifdef DEBUG
        !           230:        if (debug)
        !           231:                dumpsymtab();
        !           232: #endif
        !           233: 
        !           234: #ifdef METRIC
        !           235:        lgtmpfile = ftell(tmpfil);
        !           236: #endif
        !           237: 
        !           238:        fclose(tmpfil);
        !           239:        tmpfil = fopen(tmpn1, "r");
        !           240:        if (tmpfil==NULL) {
        !           241:                yyerror("Bad pass 2 temporary file for reading %s", tmpn1);
        !           242:                delexit();
        !           243:        }
        !           244:        setbuf(tmpfil,sibuf);
        !           245: 
        !           246:        /*
        !           247:         *      round and assign text segment origins 
        !           248:         */
        !           249:        tsize = 0;
        !           250:        for (locindex=0; locindex<NLOC; locindex++) {
        !           251:                v = round(usedot[locindex].xvalue, FW);
        !           252:                usedot[locindex].xvalue = tsize;
        !           253:                tsize += v;
        !           254:        }
        !           255:        /*
        !           256:         *      round and assign data segment origins 
        !           257:         */
        !           258:        datbase = round(tsize, PAGRND);
        !           259:        for (locindex=0; locindex<NLOC; locindex++) {
        !           260:                v = round(usedot[NLOC+locindex].xvalue, FW);
        !           261:                usedot[NLOC+locindex].xvalue = datbase+dsize;
        !           262:                dsize += v;
        !           263:        }
        !           264: 
        !           265:        hdr.bsize = dsize;
        !           266: 
        !           267:        /*
        !           268:         *      Assign final values to symbols
        !           269:         */
        !           270:        freezesymtab();
        !           271:        stabfix();
        !           272: 
        !           273:        hdr.bsize -= dsize;
        !           274: 
        !           275:        txtfil = fopen(outfile, "w");
        !           276:        if (txtfil==NULL) {
        !           277:                yyerror("Cannot create %s", outfile);
        !           278:                delexit();
        !           279:        }
        !           280:        setbuf(txtfil,sobuf);
        !           281: 
        !           282:        usefile[0] = txtfil;
        !           283: 
        !           284:        tmpn2 = (char *)mktemp("/tmp/aaatXXXXX");
        !           285:        tmpn3 = (char *)mktemp("/tmp/abatXXXXX");
        !           286: 
        !           287:        relfil = fopen(tmpn3, "w");
        !           288:        if (relfil==NULL) {
        !           289:                yyerror("Bad temp file for writing extra text segments %s", tmpn3);
        !           290:                delexit();
        !           291:        }
        !           292:        rusefile[0] = relfil;
        !           293: 
        !           294:        hdr.tsize = tsize;
        !           295:        hdr.dsize = dsize;
        !           296:        hdr.ssize = sizesymtab();
        !           297:        /*
        !           298:         *      hdr.trsize, hdr.drsize set by outrel 
        !           299:         */
        !           300: 
        !           301:        /* *************** PASS 2 **************** */
        !           302: 
        !           303:        writel(&hdr,8,txtfil);
        !           304:        tsize = 0;
        !           305:        dsize = 0;
        !           306:        lineno = 1;
        !           307:        dotp = &usedot[0];
        !           308: #ifdef DEBUG
        !           309:        if (debug)
        !           310:                printf("\n\n\n\t\tPASS 2\n\n\n\n");
        !           311: #endif
        !           312:        passno = 2;
        !           313:        inittmpfile();
        !           314: 
        !           315:        yyparse();
        !           316: 
        !           317:        closetmpfile();
        !           318: 
        !           319:        /*
        !           320:         *      round csects to FW 
        !           321:         */
        !           322:        for (locindex=0; locindex<NLOC; locindex++) {
        !           323:                if (usefile[locindex]) {
        !           324:                        txtfil=usefile[locindex];
        !           325:                        dotp= &usedot[locindex];
        !           326:                        while (usedot[locindex].xvalue & FW)
        !           327:                                outb(0);
        !           328:                        if (locindex>0)
        !           329:                                fclose(usefile[locindex]);
        !           330:                        fclose(rusefile[locindex]);
        !           331:                }
        !           332:                if (usefile[NLOC+locindex]) {
        !           333:                        txtfil = usefile[NLOC+locindex]; 
        !           334:                        dotp= &usedot[locindex+NLOC];
        !           335:                        relfil = rusefile[NLOC+locindex];
        !           336:                        while (usedot[locindex+NLOC].xvalue & FW)
        !           337:                                outb(0);
        !           338:                        fclose(txtfil);
        !           339:                        fclose(relfil);
        !           340:                }
        !           341:        }
        !           342: 
        !           343:        txtfil = usefile[0];
        !           344:        /*
        !           345:         *      append csect text onto text for csect 0 
        !           346:         */
        !           347:        for (locindex=1; locindex<NLOC+NLOC; locindex++) {
        !           348:                char    buffer[BUFSIZ];
        !           349:                if (usefile[locindex]) {
        !           350:                        tmpn2[TMPC] = locindex+'a';
        !           351:                        relfil = fopen(tmpn2, "r");
        !           352:                        if (relfil==NULL) {
        !           353:                                yyerror("cannot reopen temp");
        !           354:                                continue;
        !           355:                        }
        !           356:                        while (!feof(relfil))
        !           357:                                fwrite(buffer, 1,
        !           358:                                        fread(buffer, 1, BUFSIZ, relfil),
        !           359:                                        txtfil);
        !           360:                        fclose(relfil);
        !           361:                }
        !           362:        }
        !           363:        /*
        !           364:         *      append relocation info onto text 
        !           365:         */
        !           366:        for (locindex=0; locindex<NLOC+NLOC; locindex++) {
        !           367:                char    buffer[BUFSIZ];
        !           368:                if (rusefile[locindex]) {
        !           369:                        tmpn3[TMPC] = locindex+'a';
        !           370:                        relfil = fopen(tmpn3, "r");
        !           371:                        if (relfil==NULL) {
        !           372:                                yyerror("cannot reopen temp");
        !           373:                                continue;
        !           374:                        }
        !           375:                        while (!feof(relfil))
        !           376:                                fwrite(buffer, 1, 
        !           377:                                       fread(buffer, 1, BUFSIZ, relfil),
        !           378:                                       txtfil);
        !           379:                        fclose(relfil);
        !           380:                }
        !           381:        }
        !           382: 
        !           383:        symwrite(txtfil);
        !           384:        /*
        !           385:         *      Go back and patch up rsize
        !           386:         */
        !           387:        fseek(txtfil,0L,0);
        !           388:        writel(&hdr,8,txtfil);
        !           389: 
        !           390:        delete();
        !           391: 
        !           392:        if (anyerrs==0 && orgwarn)
        !           393:                yyerror("Caution: absolute origins.\n");
        !           394: #ifdef METRIC
        !           395:        pcounters();
        !           396: #endif
        !           397:        exit(anyerrs!=0);
        !           398: }      /*end of main*/
        !           399: 
        !           400: 
        !           401: delexit()
        !           402: {
        !           403:        delete();
        !           404: #ifdef METRIC
        !           405:        pcounters();
        !           406: #endif
        !           407:        exit(1);
        !           408: }
        !           409: 
        !           410: sawabort()
        !           411: {
        !           412:        char    buffer[BUFSIZ];
        !           413: #ifdef METRIC
        !           414:        pcounters();
        !           415: #endif
        !           416:        while (!feof(stdin))
        !           417:                fread(buffer, 1, BUFSIZ, stdin);
        !           418:        delete();
        !           419:        exit(1);        /*although the previous pass will also exit non zero*/
        !           420: }
        !           421: 
        !           422: delete()
        !           423: {
        !           424:        register locindex;
        !           425: 
        !           426:        if (tmpn1)
        !           427:                unlink(tmpn1);
        !           428:        for (locindex=0; locindex<NLOC+NLOC; locindex++) {
        !           429:                if (tmpn2) {
        !           430:                        tmpn2[TMPC] = locindex+'a';
        !           431:                        unlink(tmpn2);
        !           432:                }
        !           433:                if (tmpn3) {
        !           434:                        tmpn3[TMPC] = locindex+'a';
        !           435:                        unlink(tmpn3);
        !           436:                }
        !           437:        }
        !           438: }
        !           439: #ifdef METRIC
        !           440: pcounters()
        !           441: {
        !           442:        int     i;
        !           443:        struct {
        !           444:                long    p_user;
        !           445:                long    p_sys;
        !           446:                long    c_user;
        !           447:                long    c_sys;
        !           448:        } tbuffer;
        !           449: 
        !           450:        if (!outcounters) return;
        !           451:        printf("Assembly of files: ");
        !           452:        if (innames[0] == 0)
        !           453:                printf("<Standard Input.>\n");
        !           454:        else {
        !           455:                for (i = 0; i<ninfiles; i++)
        !           456:                        printf("%s ", innames[i]);
        !           457:                printf("\n");
        !           458:        }
        !           459:        if (useVM)
        !           460:                printf("Using ");
        !           461:        else
        !           462:                printf("NOT using ");
        !           463:        printf("Virtual Memory for the interpass temporary file.\n");
        !           464:        printf("%d hashing collsions\n", nhcollisions);
        !           465:        printf("%d hash table accesses\n", nhashed);
        !           466:        printf("%d values entered in the hash table\n", nentered);
        !           467:        printf("%d byte length of the temporary file\n", lgtmpfile);
        !           468:        printf("%d symbols in the symbol table\n", nsyms);
        !           469:        printf("%d labels in the symbol table\n", nlabels);
        !           470:        printf("%d forgotten symbols\n", nforgotten);
        !           471:        printf("%d iterations through all symbols to remove jxxxes\n",
        !           472:                        jxxxiterate);
        !           473:        printf("%d jumps resolved via tunnelling\n", jxxxtunnel);
        !           474:        if (jxdeadlock)
        !           475:                printf("%d DEADLOCKED JXXXentries: Resolved by %s jumping\n",
        !           476:                        jxdeadlock, nbadjxsegs == 0 ? "short" : "long");
        !           477:        if (nbadjxsegs)
        !           478:                printf("%d Segments with jxxx over aligns.\n",
        !           479:                        nbadjxsegs);
        !           480:        times(&tbuffer);
        !           481:        printf("%1.2fu 1.2fs\n",
        !           482:                ((float)tbuffer.p_user)/60.0,
        !           483:                ((float)tbuffer.p_sys)/60.0);
        !           484: }
        !           485: #endif

unix.superglobalmegacorp.com

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