1 /* 2 * Copyright (c) 1982 Regents of the University of California 3 */ 4 #ifndef lint 5 static char sccsid[] = "@(#)asscan1.c 4.6 07/06/83"; 6 #endif not lint 7 8 #include "asscanl.h" 9 10 inittokfile() 11 { 12 if (passno == 1){ 13 if (useVM){ 14 bufstart = &tokbuf[0]; 15 buftail = &tokbuf[1]; 16 bufstart->tok_next = buftail; 17 buftail->tok_next = 0; 18 } 19 tokbuf[0].tok_count = -1; 20 tokbuf[1].tok_count = -1; 21 } 22 tok_temp = 0; 23 tok_free = 0; 24 bufno = 0; 25 emptybuf = &tokbuf[bufno]; 26 tokptr = 0; 27 tokub = 0; 28 } 29 30 closetokfile() 31 { 32 if (passno == 1){ 33 if (useVM){ 34 emptybuf->toks[emptybuf->tok_count++] = PARSEEOF; 35 } else { 36 /* 37 * Clean up the buffers that haven't been 38 * written out yet 39 */ 40 if (tokbuf[bufno ^ 1].tok_count >= 0){ 41 if (writeTEST((char *)&tokbuf[bufno ^ 1], sizeof *emptybuf, 1, tokfile)){ 42 badwrite: 43 yyerror("Unexpected end of file writing the interpass tmp file"); 44 exit(2); 45 } 46 } 47 /* 48 * Ensure that we will read an End of file, 49 * if there are more than one file names 50 * in the argument list 51 */ 52 tokbuf[bufno].toks[tokbuf[bufno].tok_count++] = PARSEEOF; 53 if (writeTEST((char *)&tokbuf[bufno], sizeof *emptybuf, 1, tokfile)) 54 goto badwrite; 55 } 56 } /*end of being pass 1*/ 57 } 58 59 inttoktype yylex() 60 { 61 register ptrall bufptr; 62 register inttoktype val; 63 register struct exp *locxp; 64 /* 65 * No local variables to be allocated; this saves 66 * one piddling instruction.. 67 */ 68 static int Lastjxxx; 69 70 bufptr = tokptr; /*copy in the global value*/ 71 top: 72 if (bufptr < tokub){ 73 gtoken(val, bufptr); 74 switch(yylval = val){ 75 case PARSEEOF: 76 yylval = val = PARSEEOF; 77 break; 78 case BFINT: 79 case INT: 80 if (xp >= &explist[NEXP]) 81 yyerror("Too many expressions; try simplyfing"); 82 else 83 locxp = xp++; 84 locxp->e_number = Znumber; 85 locxp->e_number.num_tag = TYPL; 86 glong(locxp->e_xvalue, bufptr); 87 makevalue: 88 locxp->e_xtype = XABS; 89 locxp->e_xloc = 0; 90 locxp->e_xname = NULL; 91 yylval = (int)locxp; 92 break; 93 case BIGNUM: 94 if (xp >= &explist[NEXP]) 95 yyerror("Too many expressions; try simplyfing"); 96 else 97 locxp = xp++; 98 gnumber(locxp->e_number, bufptr); 99 goto makevalue; 100 case NAME: 101 gptr(yylval, bufptr); 102 lastnam = (struct symtab *)yylval; 103 break; 104 case SIZESPEC: 105 case REG: 106 gchar(yylval, bufptr); 107 break; 108 case INSTn: 109 case INST0: 110 gopcode(yyopcode, bufptr); 111 break; 112 case IJXXX: 113 gopcode(yyopcode, bufptr); 114 /* We can't cast Lastjxxx into (int *) here.. */ 115 gptr(Lastjxxx, bufptr); 116 lastjxxx = (struct symtab *)Lastjxxx; 117 break; 118 case ILINESKIP: 119 gint(yylval, bufptr); 120 lineno += yylval; 121 goto top; 122 case SKIP: 123 eatskiplg(bufptr); 124 goto top; 125 case VOID: 126 goto top; 127 case STRING: 128 case ISTAB: 129 case ISTABSTR: 130 case ISTABNONE: 131 case ISTABDOT: 132 case IALIGN: 133 gptr(yylval, bufptr); 134 break; 135 } 136 #ifdef DEBUG 137 if (toktrace){ 138 char *tok_to_name(); 139 printf("P: %d T#: %4d, %s ", 140 passno, bufptr - firsttoken, tok_to_name(val)); 141 switch(val){ 142 case INT: printf("val %d", 143 ((struct exp *)yylval)->e_xvalue); 144 break; 145 case BFINT: printf("val %d", 146 ((struct exp *)yylval)->e_xvalue); 147 break; 148 case BIGNUM: bignumprint(((struct exp*)yylval)->e_number); 149 break; 150 case NAME: printf("\"%.8s\"", 151 FETCHNAME((struct symtab *)yylval)); 152 break; 153 case REG: printf(" r%d", 154 yylval); 155 break; 156 case IJXXX: 157 case INST0: 158 case INSTn: if (ITABCHECK(yyopcode)) 159 printf("%.8s", 160 FETCHNAME(ITABFETCH(yyopcode))); 161 else 162 printf("IJXXX or INST0 or INSTn can't get into the itab\n"); 163 break; 164 case STRING: 165 printf("length %d, seekoffset %d, place 0%o ", 166 ((struct strdesc *)yylval)->sd_strlen, 167 ((struct strdesc *)yylval)->sd_stroff, 168 ((struct strdesc *)yylval)->sd_place 169 ); 170 if (((struct strdesc *)yylval)->sd_place & STR_CORE) 171 printf("value\"%*s\"", 172 ((struct strdesc *)yylval)->sd_strlen, 173 ((struct strdesc *)yylval)->sd_string); 174 break; 175 } /*end of the debug switch*/ 176 printf("\n"); 177 } 178 #endif DEBUG 179 180 } else { /* start a new buffer */ 181 if (useVM){ 182 if (passno == 2){ 183 tok_temp = emptybuf->tok_next; 184 emptybuf->tok_next = tok_free; 185 tok_free = emptybuf; 186 emptybuf = tok_temp; 187 } else { 188 emptybuf = emptybuf->tok_next; 189 } 190 bufno += 1; 191 if (emptybuf == 0){ 192 struct tokbufdesc *newdallop; 193 int i; 194 if (passno == 2) 195 goto badread; 196 emptybuf = newdallop = (struct tokbufdesc *) 197 Calloc(TOKDALLOP, sizeof (struct tokbufdesc)); 198 for (i=0; i < TOKDALLOP; i++){ 199 buftail->tok_next = newdallop; 200 buftail = newdallop; 201 newdallop += 1; 202 } 203 buftail->tok_next = 0; 204 } /*end of need to get more buffers*/ 205 (bytetoktype *)bufptr = &(emptybuf->toks[0]); 206 if (passno == 1) 207 scan_dot_s(emptybuf); 208 } else { /*don't use VM*/ 209 bufno ^= 1; 210 emptybuf = &tokbuf[bufno]; 211 ((bytetoktype *)bufptr) = &(emptybuf->toks[0]); 212 if (passno == 1){ 213 /* 214 * First check if there are things to write 215 * out at all 216 */ 217 if (emptybuf->tok_count >= 0){ 218 if (writeTEST((char *)emptybuf, sizeof *emptybuf, 1, tokfile)){ 219 yyerror("Unexpected end of file writing the interpass tmp file"); 220 exit(2); 221 } 222 } 223 scan_dot_s(emptybuf); 224 } else { /*pass 2*/ 225 if (readTEST((char *)emptybuf, sizeof *emptybuf, 1, tokfile)){ 226 badread: 227 yyerror("Unexpected end of file while reading the interpass tmp file"); 228 exit(1); 229 } 230 } 231 } /*end of using a real live file*/ 232 (char *)tokub = (char *)bufptr + emptybuf->tok_count; 233 #ifdef DEBUG 234 firsttoken = bufptr; 235 if (debug) 236 printf("created buffernumber %d with %d tokens\n", 237 bufno, emptybuf->tok_count); 238 #endif DEBUG 239 goto top; 240 } /*end of reading/creating a new buffer*/ 241 tokptr = bufptr; /*copy back the global value*/ 242 return(val); 243 } /*end of yylex*/ 244 245 246 buildskip(from, to) 247 register ptrall from, to; 248 { 249 int diff; 250 register struct tokbufdesc *middlebuf; 251 /* 252 * check if from and to are in the same buffer 253 * from and to DIFFER BY AT MOST 1 buffer and to is 254 * always ahead of from, with to being in the buffer emptybuf 255 * points to. 256 * The hard part here is accounting for the case where the 257 * skip is to cross a buffer boundary; we must construct 258 * two skips. 259 * 260 * Figure out where the buffer boundary between from and to is 261 * It's easy in VM, as buffers increase to high memory, but 262 * w/o VM, we alternate between two buffers, and want 263 * to look at the exact middle of the contiguous buffer region. 264 */ 265 middlebuf = useVM ? emptybuf : &tokbuf[1]; 266 if ( ( (bytetoktype *)from > (bytetoktype *)middlebuf) 267 ^ ( (bytetoktype *)to > (bytetoktype *)middlebuf) 268 ){ /*split across a buffer boundary*/ 269 ptoken(from, SKIP); 270 /* 271 * Set the skip so it lands someplace beyond 272 * the end of this buffer. 273 * When we pull this skip out in the second pass, 274 * we will temporarily move the current pointer 275 * out beyond the end of the buffer, but immediately 276 * do a compare and fail the compare, and then reset 277 * all the pointers correctly to point into the next buffer. 278 */ 279 bskiplg(from, TOKBUFLG + 1); 280 /* 281 * Now, force from to be in the same buffer as to 282 */ 283 (bytetoktype *)from = (bytetoktype *)&(emptybuf->toks[0]); 284 } 285 /* 286 * Now, to and from are in the same buffer 287 */ 288 if (from > to) 289 yyerror("Internal error: bad skip construction"); 290 else { 291 if ( (diff = (bytetoktype *)to - (bytetoktype *)from) >= 292 (sizeof(bytetoktype) + sizeof(lgtype) + 1)) { 293 ptoken(from, SKIP); 294 bskipfromto(from, to); 295 } else { 296 for ( ; diff > 0; --diff) 297 ptoken(from, VOID); 298 } 299 } 300 } 301 302 movestr(to, from, lg) 303 char *to; /* 4(ap) */ 304 char *from; /* 8(ap) */ 305 int lg; /* 12(ap) */ 306 { 307 if (lg <= 0) 308 return; 309 ; 310 asm("movc3 12(ap),*8(ap),*4(ap)"); 311 ; 312 } 313 314 new_dot_s(namep) 315 char *namep; 316 { 317 newfflag = 1; 318 newfname = namep; 319 dotsname = namep; 320 lineno = 1; 321 scanlineno = 1; 322 } 323 324 min(a, b) 325 { 326 return(a < b ? a : b); 327 } 328