Annotation of 43BSDReno/pgrm/pascal/src/savenl.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 1980 Regents of the University of California.
                      3:  * All rights reserved.  The Berkeley software License Agreement
                      4:  * specifies the terms and conditions for redistribution.
                      5:  */
                      6: 
                      7: #ifndef lint
                      8: static char sccsid[] = "@(#)savenl.c   5.2 (Berkeley) 1/9/89";
                      9: #endif not lint
                     10: 
                     11: /*
                     12:  * savenl - routines for saving namelist and line number information
                     13:  *
                     14:  * This module contains the routines that make pi dump a namelist
                     15:  * at the end of the object file.  We do this by first creating
                     16:  * four temporary files in "startnlfile".  One temp file contains
                     17:  * the string table, one the symbol table, one the file name
                     18:  * information and one the line number information.
                     19:  *
                     20:  * Prior to generation of the code for a statement the "lineno"
                     21:  * routine is called to dump the line number and current object
                     22:  * address.  At the end of each block "savenl" is called to dump
                     23:  * the strings and symbol structures.
                     24:  *
                     25:  * At the end of execution "copynlfile" is called and it copies
                     26:  * the temp files onto the end of the obj file.
                     27:  *
                     28:  * In case of error, "removenlfile" is called to destroy the temp files.
                     29:  *
                     30:  * The only other changes to pi are in calling these routines from
                     31:  *
                     32:  *     "main"          (main.c)
                     33:  *     "yymain"        (yymain.c)
                     34:  *     "funcend"       (fend.c)
                     35:  *     "yyget"         (yyget.c)
                     36:  *     "putline"       (stat.c)
                     37:  */
                     38: 
                     39: #include "whoami.h"
                     40: #ifdef OBJ
                     41:         /*
                     42:         *      and the rest of the file
                     43:         */
                     44: #include "0.h"
                     45: #include "objfmt.h"
                     46: 
                     47: #undef NIL
                     48: 
                     49: /*
                     50:  * pdx header files
                     51:  */
                     52: 
                     53: #include "../pdx/defs.h"
                     54: #include "../pdx/object.h"
                     55: #include "../pdx/object/objsym.rep"
                     56: #include "../pdx/mappings.h"
                     57: #include "../pdx/mappings/filetab.h"
                     58: 
                     59: LOCAL char symname[] = "/tmp/obj.symXXXXXX";
                     60: LOCAL char strname[] = "/tmp/obj.strXXXXXX";
                     61: LOCAL char filesname[] = "/tmp/obj.filesXXXXXX";
                     62: LOCAL char linesname[] = "/tmp/obj.linesXXXXXX";
                     63: 
                     64: LOCAL FILE *symfp;
                     65: LOCAL FILE *strfp;
                     66: LOCAL FILE *filesfp;
                     67: LOCAL FILE *linesfp;
                     68: 
                     69: LOCAL long nlsize;
                     70: 
                     71: extern FILE *fopen();
                     72: 
                     73: LOCAL putblock();
                     74: LOCAL putstring();
                     75: 
                     76: /*
                     77:  * create temporary files for the namelist info
                     78:  */
                     79: 
                     80: startnlfile()
                     81: {
                     82:        nlsize = 0;
                     83:        (void) mktemp(symname);
                     84:        (void) mktemp(strname);
                     85:        (void) mktemp(filesname);
                     86:        (void) mktemp(linesname);
                     87:        symfp = fopen(symname, "w");
                     88:        strfp = fopen(strname, "w");
                     89:        filesfp = fopen(filesname, "w");
                     90:        linesfp = fopen(linesname, "w");
                     91:        if (symfp==NULL || strfp==NULL || filesfp==NULL || linesfp==NULL) {
                     92:                fprintf(stderr, "can't create /tmp/obj");
                     93:                pexit(NOSTART);
                     94:        }
                     95:        newfile(filename, 1);
                     96: }
                     97: 
                     98: /*
                     99:  * now copy the temp files back to obj; strings, symbols, file names, and lines
                    100:  *
                    101:  * There's some efficiency garbage here that uses straight system
                    102:  * calls rather than standard I/O library calls.
                    103:  */
                    104: 
                    105: copynlfile()
                    106: {
                    107:        register int n;
                    108:        extern long lseek();
                    109:        int symfd, strfd, filesfd, linesfd;
                    110:        char buff[BUFSIZ];
                    111: 
                    112:        (void) fclose((FILE *) symfp);
                    113:        (void) fclose((FILE *) strfp);
                    114:        (void) fclose((FILE *) filesfp);
                    115:        (void) fclose((FILE *) linesfp);
                    116:        if (!opt('g')) {
                    117:                removenlfile();
                    118:                return;
                    119:        }
                    120:        symfd = open(symname, 0);
                    121:        strfd = open(strname, 0);
                    122:        filesfd = open(filesname, 0);
                    123:        linesfd = open(linesname, 0);
                    124:        if (symfd < 0 || strfd < 0 || filesfd < 0 || linesfd < 0) {
                    125:                fprintf(stderr, "sync error on /tmp/obj");
                    126:                pexit(ERRS);
                    127:        }
                    128:        (void) lseek(ofil, 0L, 2);
                    129:        write(ofil, (char *) (&nlhdr), sizeof(nlhdr));
                    130:        n = read(strfd, buff, BUFSIZ - sizeof(nlhdr));
                    131:        write(ofil, buff, n);
                    132:        cat(strfd);
                    133:        cat(symfd);
                    134:        cat(filesfd);
                    135:        cat(linesfd);
                    136:        removenlfile();
                    137: }
                    138: 
                    139: cat(fd)
                    140: int fd;
                    141: {
                    142:        register int n;
                    143:        char buff[BUFSIZ];
                    144: 
                    145:        while ((n = read(fd, buff, BUFSIZ)) > 0) {
                    146:                write(ofil, buff, n);
                    147:        }
                    148:        (void) close(fd);
                    149: }
                    150: 
                    151: removenlfile()
                    152: {
                    153:        unlink(symname);
                    154:        unlink(strname);
                    155:        unlink(filesname);
                    156:        unlink(linesname);
                    157: }
                    158: 
                    159: nlhdrsize()
                    160: {
                    161:        int r;
                    162: 
                    163:        if (!opt('g')) {
                    164:                r = 0;
                    165:        } else {
                    166:                r = nlsize + sizeof(nlhdr);
                    167:        }
                    168:        return r;
                    169: }
                    170: 
                    171: #define isblock(s)     (s->class == FUNC || s->class == PROC)
                    172: #define isbuiltin(s)   ((s->nl_block&037) == 0 && isblock(s))
                    173: #define symno(p)       (p==NULL ? 0 : nloff(p))
                    174: 
                    175: struct nls {
                    176:        struct nl *nls_low;
                    177:        struct nl *nls_high;
                    178: };
                    179: 
                    180: struct nl nl[], *nlp, ntab[], *nlact;
                    181: 
                    182: /*VARARGS*/
                    183: savenl(to, rout)
                    184: struct nl *to;
                    185: {
                    186:        register struct nl *p;
                    187:        register OBJSYM *s;
                    188:        OBJSYM tmpsym;
                    189:        struct nls *nlsp;
                    190: 
                    191:        if (to != NIL) {
                    192:                putblock((char *) rout);
                    193:        } else {
                    194:                putblock("main program");
                    195:        }
                    196:        nlsp = (struct nls *) nlact;
                    197:        s = &tmpsym;
                    198:        for (p = nlp; p != to;) {
                    199:                if (p == nlsp->nls_low) {
                    200:                        if (nlsp == ((struct nls *) &ntab[0]))
                    201:                                break;
                    202:                        nlsp--;
                    203:                        p = nlsp->nls_high;
                    204:                }
                    205:                p--;
                    206:                if (isbuiltin(p) || symno(p) == 0) {
                    207:                        continue;
                    208:                }
                    209:                nlhdr.nsyms++;
                    210:                nlsize += sizeof(OBJSYM) + sizeof(int);
                    211:                (void) putw(symno(p), symfp);
                    212:                if (p->symbol != NULL) {
                    213:                        s->strindex = nlhdr.stringsize;
                    214:                        putstring(p->symbol);
                    215:                } else {
                    216:                        s->strindex = 0;
                    217:                }
                    218:                s->oclass = p->class;
                    219:                s->oblkno = (p->nl_block&037);
                    220:                s->typno = symno(p->type);
                    221:                s->chno = symno(p->chain);
                    222:                s->osymvalue.orangev.lower = p->range[0];
                    223:                s->osymvalue.orangev.upper = p->range[1];
                    224:                if (isblock(p)) {
                    225:                        s->osymvalue.ofuncv.codeloc = p->value[NL_ENTLOC];
                    226:                } else if (p->class == RECORD || p->class == VARNT) {
                    227:                        s->osymvalue.ovarnt.vtorecno = symno(p->ptr[2]);
                    228:                        s->osymvalue.ovarnt.vtagno = symno(p->ptr[3]);
                    229:                }
                    230:                fwrite((char *) s, sizeof(*s), 1, symfp);
                    231:        }
                    232: }
                    233: 
                    234: /*
                    235:  * Dump a line number and the current object location counter.
                    236:  *
                    237:  * To save space the difference from the previous line number and offset
                    238:  * (one byte each) is dumped.
                    239:  */
                    240: 
                    241: LOCAL int oline = 0;
                    242: LOCAL int olc = HEADER_BYTES;
                    243: 
                    244: lineno(line)
                    245: int line;
                    246: {
                    247:        OBJLINE info;
                    248: 
                    249:        if (line != oline) {
                    250:                nlhdr.nlines++;
                    251:                nlsize += sizeof(OBJLINE);
                    252:                info.separate.lineincr = line - oline;
                    253:                info.separate.addrincr = ((unsigned short) (lc - olc));
                    254:                (void) putw((int) info.together, linesfp);
                    255:                oline = line;
                    256:                olc = (int) lc;
                    257:        }
                    258: }
                    259: 
                    260: /*
                    261:  * put out a file name entry, including:
                    262:  *
                    263:  *     the current line number for the new file
                    264:  *     the current location counter
                    265:  *     the string table address of the file name
                    266:  *     an index into the current line number information
                    267:  */
                    268: 
                    269: newfile(s, line)
                    270: char *s;
                    271: int line;
                    272: {
                    273:        FILETAB ft;
                    274: 
                    275:        nlhdr.nfiles++;
                    276:        nlsize += sizeof(FILETAB);
                    277:        ft.line = line;
                    278:        oline = line;
                    279:        if (lc == 0) {
                    280:                ft.addr = 0;
                    281:        } else {
                    282:                ft.addr = ((LINENO) lc - HEADER_BYTES );
                    283:        }
                    284:        ft.filename = (char *) nlhdr.stringsize;
                    285:        putstring(s);
                    286:        ft.lineindex = nlhdr.nlines;
                    287:        fwrite((char *) (&ft), sizeof(ft), 1, filesfp);
                    288: }
                    289: 
                    290: /*
                    291:  * put out a dummy symbol at the beginning of a block
                    292:  */
                    293: 
                    294: LOCAL putblock(s)
                    295: char *s;
                    296: {
                    297:        static OBJSYM zerosym;
                    298: 
                    299:        nlhdr.nsyms++;
                    300:        nlsize += sizeof(OBJSYM) + sizeof(int);
                    301:        (void) putw(0, symfp);
                    302:        zerosym.strindex = nlhdr.stringsize;
                    303:        putstring(s);
                    304:        fwrite((char *) (&zerosym), sizeof(zerosym), 1, symfp);
                    305: }
                    306: 
                    307: /*
                    308:  * put out a string to the string table file
                    309:  */
                    310: 
                    311: LOCAL putstring(s)
                    312: char *s;
                    313: {
                    314:        register char *p;
                    315: 
                    316:        for (p = s; *p != '\0'; p++) {
                    317:                putc(*p, strfp);
                    318:        }
                    319:        nlhdr.stringsize += (p - s + 1);
                    320:        nlsize += (p - s + 1);
                    321:        putc('\0', strfp);
                    322: }
                    323: #endif OBJ

unix.superglobalmegacorp.com

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