15797Srrh /*
2*19828Sdist * Copyright (c) 1982 Regents of the University of California.
3*19828Sdist * All rights reserved. The Berkeley software License Agreement
4*19828Sdist * specifies the terms and conditions for redistribution.
55797Srrh */
6*19828Sdist
75797Srrh #ifndef lint
8*19828Sdist static char sccsid[] = "@(#)asscan1.c 5.1 (Berkeley) 04/30/85";
95797Srrh #endif not lint
105797Srrh
115797Srrh #include "asscanl.h"
125797Srrh
inittokfile()1313515Srrh inittokfile()
145797Srrh {
155797Srrh if (passno == 1){
165797Srrh if (useVM){
175797Srrh bufstart = &tokbuf[0];
185797Srrh buftail = &tokbuf[1];
195797Srrh bufstart->tok_next = buftail;
205797Srrh buftail->tok_next = 0;
215797Srrh }
225797Srrh tokbuf[0].tok_count = -1;
235797Srrh tokbuf[1].tok_count = -1;
245797Srrh }
255797Srrh tok_temp = 0;
265797Srrh tok_free = 0;
275797Srrh bufno = 0;
285797Srrh emptybuf = &tokbuf[bufno];
295797Srrh tokptr = 0;
305797Srrh tokub = 0;
315797Srrh }
325797Srrh
closetokfile()3313515Srrh closetokfile()
345797Srrh {
355797Srrh if (passno == 1){
365797Srrh if (useVM){
375797Srrh emptybuf->toks[emptybuf->tok_count++] = PARSEEOF;
385797Srrh } else {
395797Srrh /*
405797Srrh * Clean up the buffers that haven't been
415797Srrh * written out yet
425797Srrh */
435797Srrh if (tokbuf[bufno ^ 1].tok_count >= 0){
4413515Srrh if (writeTEST((char *)&tokbuf[bufno ^ 1], sizeof *emptybuf, 1, tokfile)){
455797Srrh badwrite:
465797Srrh yyerror("Unexpected end of file writing the interpass tmp file");
475797Srrh exit(2);
485797Srrh }
495797Srrh }
505797Srrh /*
515797Srrh * Ensure that we will read an End of file,
525797Srrh * if there are more than one file names
535797Srrh * in the argument list
545797Srrh */
555797Srrh tokbuf[bufno].toks[tokbuf[bufno].tok_count++] = PARSEEOF;
5613515Srrh if (writeTEST((char *)&tokbuf[bufno], sizeof *emptybuf, 1, tokfile))
575797Srrh goto badwrite;
585797Srrh }
595797Srrh } /*end of being pass 1*/
605797Srrh }
615797Srrh
yylex()625797Srrh inttoktype yylex()
635797Srrh {
645797Srrh register ptrall bufptr;
655797Srrh register inttoktype val;
665797Srrh register struct exp *locxp;
675797Srrh /*
685797Srrh * No local variables to be allocated; this saves
695797Srrh * one piddling instruction..
705797Srrh */
715797Srrh static int Lastjxxx;
725797Srrh
735797Srrh bufptr = tokptr; /*copy in the global value*/
745797Srrh top:
755797Srrh if (bufptr < tokub){
765797Srrh gtoken(val, bufptr);
775797Srrh switch(yylval = val){
785797Srrh case PARSEEOF:
795797Srrh yylval = val = PARSEEOF;
805797Srrh break;
815797Srrh case BFINT:
825797Srrh case INT:
835797Srrh if (xp >= &explist[NEXP])
845797Srrh yyerror("Too many expressions; try simplyfing");
855797Srrh else
865797Srrh locxp = xp++;
875797Srrh locxp->e_number = Znumber;
885797Srrh locxp->e_number.num_tag = TYPL;
895797Srrh glong(locxp->e_xvalue, bufptr);
905797Srrh makevalue:
915797Srrh locxp->e_xtype = XABS;
925797Srrh locxp->e_xloc = 0;
935797Srrh locxp->e_xname = NULL;
945797Srrh yylval = (int)locxp;
955797Srrh break;
965797Srrh case BIGNUM:
975797Srrh if (xp >= &explist[NEXP])
985797Srrh yyerror("Too many expressions; try simplyfing");
995797Srrh else
1005797Srrh locxp = xp++;
1015797Srrh gnumber(locxp->e_number, bufptr);
1025797Srrh goto makevalue;
1035797Srrh case NAME:
1045797Srrh gptr(yylval, bufptr);
1055797Srrh lastnam = (struct symtab *)yylval;
1065797Srrh break;
1075797Srrh case SIZESPEC:
1085797Srrh case REG:
1095797Srrh gchar(yylval, bufptr);
1105797Srrh break;
1115797Srrh case INSTn:
1125797Srrh case INST0:
1135797Srrh gopcode(yyopcode, bufptr);
1145797Srrh break;
1155797Srrh case IJXXX:
1165797Srrh gopcode(yyopcode, bufptr);
1175797Srrh /* We can't cast Lastjxxx into (int *) here.. */
1185797Srrh gptr(Lastjxxx, bufptr);
1195797Srrh lastjxxx = (struct symtab *)Lastjxxx;
1205797Srrh break;
1215797Srrh case ILINESKIP:
1225797Srrh gint(yylval, bufptr);
1235797Srrh lineno += yylval;
1245797Srrh goto top;
1255797Srrh case SKIP:
1265797Srrh eatskiplg(bufptr);
1275797Srrh goto top;
1285797Srrh case VOID:
1295797Srrh goto top;
1305797Srrh case STRING:
1315797Srrh case ISTAB:
1325797Srrh case ISTABSTR:
1335797Srrh case ISTABNONE:
1345797Srrh case ISTABDOT:
1355797Srrh case IALIGN:
1365797Srrh gptr(yylval, bufptr);
1375797Srrh break;
1385797Srrh }
1395797Srrh #ifdef DEBUG
1405797Srrh if (toktrace){
1415797Srrh char *tok_to_name();
1425797Srrh printf("P: %d T#: %4d, %s ",
1435797Srrh passno, bufptr - firsttoken, tok_to_name(val));
1445797Srrh switch(val){
1455797Srrh case INT: printf("val %d",
1465797Srrh ((struct exp *)yylval)->e_xvalue);
1475797Srrh break;
1485797Srrh case BFINT: printf("val %d",
1495797Srrh ((struct exp *)yylval)->e_xvalue);
1505797Srrh break;
1515797Srrh case BIGNUM: bignumprint(((struct exp*)yylval)->e_number);
1525797Srrh break;
1535797Srrh case NAME: printf("\"%.8s\"",
15413515Srrh FETCHNAME((struct symtab *)yylval));
1555797Srrh break;
1565797Srrh case REG: printf(" r%d",
1575797Srrh yylval);
1585797Srrh break;
1595797Srrh case IJXXX:
1605797Srrh case INST0:
1615797Srrh case INSTn: if (ITABCHECK(yyopcode))
16213515Srrh printf("%.8s",
16313515Srrh FETCHNAME(ITABFETCH(yyopcode)));
1645797Srrh else
1655797Srrh printf("IJXXX or INST0 or INSTn can't get into the itab\n");
1665797Srrh break;
16713807Srrh case STRING:
16813807Srrh printf("length %d, seekoffset %d, place 0%o ",
16913807Srrh ((struct strdesc *)yylval)->sd_strlen,
17013807Srrh ((struct strdesc *)yylval)->sd_stroff,
17113807Srrh ((struct strdesc *)yylval)->sd_place
17213807Srrh );
17313807Srrh if (((struct strdesc *)yylval)->sd_place & STR_CORE)
17413448Srrh printf("value\"%*s\"",
17513807Srrh ((struct strdesc *)yylval)->sd_strlen,
17613807Srrh ((struct strdesc *)yylval)->sd_string);
17713807Srrh break;
1785797Srrh } /*end of the debug switch*/
1795797Srrh printf("\n");
1805797Srrh }
1815797Srrh #endif DEBUG
1825797Srrh
1835797Srrh } else { /* start a new buffer */
1845797Srrh if (useVM){
1855797Srrh if (passno == 2){
1865797Srrh tok_temp = emptybuf->tok_next;
1875797Srrh emptybuf->tok_next = tok_free;
1885797Srrh tok_free = emptybuf;
1895797Srrh emptybuf = tok_temp;
1905797Srrh } else {
1915797Srrh emptybuf = emptybuf->tok_next;
1925797Srrh }
1935797Srrh bufno += 1;
1945797Srrh if (emptybuf == 0){
1955797Srrh struct tokbufdesc *newdallop;
1965797Srrh int i;
1975797Srrh if (passno == 2)
1985797Srrh goto badread;
1995797Srrh emptybuf = newdallop = (struct tokbufdesc *)
2005797Srrh Calloc(TOKDALLOP, sizeof (struct tokbufdesc));
2015797Srrh for (i=0; i < TOKDALLOP; i++){
2025797Srrh buftail->tok_next = newdallop;
2035797Srrh buftail = newdallop;
2045797Srrh newdallop += 1;
2055797Srrh }
2065797Srrh buftail->tok_next = 0;
2075797Srrh } /*end of need to get more buffers*/
2085797Srrh (bytetoktype *)bufptr = &(emptybuf->toks[0]);
2095797Srrh if (passno == 1)
2105797Srrh scan_dot_s(emptybuf);
2115797Srrh } else { /*don't use VM*/
2125797Srrh bufno ^= 1;
2135797Srrh emptybuf = &tokbuf[bufno];
2145797Srrh ((bytetoktype *)bufptr) = &(emptybuf->toks[0]);
2155797Srrh if (passno == 1){
2165797Srrh /*
2175797Srrh * First check if there are things to write
2185797Srrh * out at all
2195797Srrh */
2205797Srrh if (emptybuf->tok_count >= 0){
22113515Srrh if (writeTEST((char *)emptybuf, sizeof *emptybuf, 1, tokfile)){
2225797Srrh yyerror("Unexpected end of file writing the interpass tmp file");
2235797Srrh exit(2);
2245797Srrh }
2255797Srrh }
2265797Srrh scan_dot_s(emptybuf);
2275797Srrh } else { /*pass 2*/
22813515Srrh if (readTEST((char *)emptybuf, sizeof *emptybuf, 1, tokfile)){
2295797Srrh badread:
2305797Srrh yyerror("Unexpected end of file while reading the interpass tmp file");
2315797Srrh exit(1);
2325797Srrh }
2335797Srrh }
2345797Srrh } /*end of using a real live file*/
2355797Srrh (char *)tokub = (char *)bufptr + emptybuf->tok_count;
2365797Srrh #ifdef DEBUG
2375797Srrh firsttoken = bufptr;
2385797Srrh if (debug)
2395797Srrh printf("created buffernumber %d with %d tokens\n",
2405797Srrh bufno, emptybuf->tok_count);
2415797Srrh #endif DEBUG
2425797Srrh goto top;
2435797Srrh } /*end of reading/creating a new buffer*/
2445797Srrh tokptr = bufptr; /*copy back the global value*/
2455797Srrh return(val);
2465797Srrh } /*end of yylex*/
2475797Srrh
2485797Srrh
buildskip(from,to)2495797Srrh buildskip(from, to)
2505797Srrh register ptrall from, to;
2515797Srrh {
2525797Srrh int diff;
2535797Srrh register struct tokbufdesc *middlebuf;
2545797Srrh /*
2555797Srrh * check if from and to are in the same buffer
2565797Srrh * from and to DIFFER BY AT MOST 1 buffer and to is
2575797Srrh * always ahead of from, with to being in the buffer emptybuf
2585797Srrh * points to.
2595797Srrh * The hard part here is accounting for the case where the
2605797Srrh * skip is to cross a buffer boundary; we must construct
2615797Srrh * two skips.
2625797Srrh *
2635797Srrh * Figure out where the buffer boundary between from and to is
2645797Srrh * It's easy in VM, as buffers increase to high memory, but
2655797Srrh * w/o VM, we alternate between two buffers, and want
2665797Srrh * to look at the exact middle of the contiguous buffer region.
2675797Srrh */
2685797Srrh middlebuf = useVM ? emptybuf : &tokbuf[1];
2695797Srrh if ( ( (bytetoktype *)from > (bytetoktype *)middlebuf)
2705797Srrh ^ ( (bytetoktype *)to > (bytetoktype *)middlebuf)
2715797Srrh ){ /*split across a buffer boundary*/
2725797Srrh ptoken(from, SKIP);
2735797Srrh /*
2745797Srrh * Set the skip so it lands someplace beyond
2755797Srrh * the end of this buffer.
2765797Srrh * When we pull this skip out in the second pass,
2775797Srrh * we will temporarily move the current pointer
2785797Srrh * out beyond the end of the buffer, but immediately
2795797Srrh * do a compare and fail the compare, and then reset
2805797Srrh * all the pointers correctly to point into the next buffer.
2815797Srrh */
2825797Srrh bskiplg(from, TOKBUFLG + 1);
2835797Srrh /*
2845797Srrh * Now, force from to be in the same buffer as to
2855797Srrh */
2865797Srrh (bytetoktype *)from = (bytetoktype *)&(emptybuf->toks[0]);
2875797Srrh }
2885797Srrh /*
2895797Srrh * Now, to and from are in the same buffer
2905797Srrh */
2915797Srrh if (from > to)
2925797Srrh yyerror("Internal error: bad skip construction");
2935797Srrh else {
2945797Srrh if ( (diff = (bytetoktype *)to - (bytetoktype *)from) >=
2955797Srrh (sizeof(bytetoktype) + sizeof(lgtype) + 1)) {
2965797Srrh ptoken(from, SKIP);
2975797Srrh bskipfromto(from, to);
2985797Srrh } else {
2995797Srrh for ( ; diff > 0; --diff)
3005797Srrh ptoken(from, VOID);
3015797Srrh }
3025797Srrh }
3035797Srrh }
3045797Srrh
movestr(to,from,lg)3055797Srrh movestr(to, from, lg)
30613448Srrh char *to; /* 4(ap) */
30713448Srrh char *from; /* 8(ap) */
30813448Srrh int lg; /* 12(ap) */
3095797Srrh {
31013448Srrh if (lg <= 0)
31113448Srrh return;
31213448Srrh ;
31313448Srrh asm("movc3 12(ap),*8(ap),*4(ap)");
31413448Srrh ;
3155797Srrh }
3165797Srrh
new_dot_s(namep)3175797Srrh new_dot_s(namep)
3185797Srrh char *namep;
3195797Srrh {
3205797Srrh newfflag = 1;
3215797Srrh newfname = namep;
3225797Srrh dotsname = namep;
3235797Srrh lineno = 1;
3245797Srrh scanlineno = 1;
3255797Srrh }
32613448Srrh
min(a,b)32713448Srrh min(a, b)
32813448Srrh {
32913448Srrh return(a < b ? a : b);
33013448Srrh }
331