1769Speter /* Copyright (c) 1979 Regents of the University of California */ 2769Speter 3*10562Smckusick static char sccsid[] = "@(#)put.c 1.20 01/21/83"; 4769Speter 5769Speter #include "whoami.h" 6769Speter #include "opcode.h" 7769Speter #include "0.h" 8769Speter #include "objfmt.h" 9769Speter #ifdef PC 10769Speter # include "pc.h" 11769Speter #endif PC 12769Speter 13769Speter short *obufp = obuf; 14769Speter 15769Speter /* 16769Speter * If DEBUG is defined, include the table 17769Speter * of the printing opcode names. 18769Speter */ 19769Speter #ifdef DEBUG 20769Speter #include "OPnames.h" 21769Speter #endif 22769Speter 23769Speter #ifdef OBJ 24769Speter /* 25769Speter * Put is responsible for the interpreter equivalent of code 26769Speter * generation. Since the interpreter is specifically designed 27769Speter * for Pascal, little work is required here. 28769Speter */ 29769Speter put(a) 30769Speter { 31769Speter register int *p, i; 32769Speter register char *cp; 333077Smckusic register short *sp; 343077Smckusic register long *lp; 35769Speter int n, subop, suboppr, op, oldlc, w; 36769Speter char *string; 37769Speter static int casewrd; 38769Speter 39769Speter /* 40769Speter * It would be nice to do some more 41769Speter * optimizations here. The work 42769Speter * done to collapse offsets in lval 43769Speter * should be done here, the IFEQ etc 44769Speter * relational operators could be used 45769Speter * etc. 46769Speter */ 47769Speter oldlc = lc; 483317Speter if ( !CGENNING ) 49769Speter /* 50769Speter * code disabled - do nothing 51769Speter */ 52769Speter return (oldlc); 53769Speter p = &a; 54769Speter n = *p++; 553077Smckusic suboppr = subop = (*p >> 8) & 0377; 56769Speter op = *p & 0377; 57769Speter string = 0; 58769Speter #ifdef DEBUG 59769Speter if ((cp = otext[op]) == NIL) { 60769Speter printf("op= %o\n", op); 61769Speter panic("put"); 62769Speter } 63769Speter #endif 64769Speter switch (op) { 65769Speter case O_ABORT: 66769Speter cp = "*"; 67769Speter break; 682221Smckusic case O_AS: 692221Smckusic switch(p[1]) { 706594Smckusick case 0: 716594Smckusick break; 722221Smckusic case 2: 732221Smckusic op = O_AS2; 746594Smckusick n = 1; 752221Smckusic break; 762221Smckusic case 4: 772221Smckusic op = O_AS4; 786594Smckusick n = 1; 792221Smckusic break; 802221Smckusic case 8: 812221Smckusic op = O_AS8; 826594Smckusick n = 1; 832221Smckusic break; 842221Smckusic default: 852221Smckusic goto pack; 862221Smckusic } 873077Smckusic # ifdef DEBUG 883077Smckusic cp = otext[op]; 893077Smckusic # endif DEBUG 902221Smckusic break; 913077Smckusic case O_CONG: 923077Smckusic case O_LVCON: 933077Smckusic case O_CON: 94769Speter case O_LINO: 95769Speter case O_NEW: 96769Speter case O_DISPOSE: 977965Smckusick case O_DFDISP: 98769Speter case O_IND: 99769Speter case O_OFF: 100769Speter case O_INX2: 101769Speter case O_INX4: 102769Speter case O_CARD: 103769Speter case O_ADDT: 104769Speter case O_SUBT: 105769Speter case O_MULT: 106769Speter case O_IN: 107769Speter case O_CASE1OP: 108769Speter case O_CASE2OP: 109769Speter case O_CASE4OP: 1101199Speter case O_FRTN: 111769Speter case O_WRITES: 1123173Smckusic case O_WRITEC: 113769Speter case O_WRITEF: 114769Speter case O_MAX: 115769Speter case O_MIN: 116769Speter case O_ARGV: 117769Speter case O_CTTOT: 118769Speter case O_INCT: 119769Speter case O_RANG2: 120769Speter case O_RSNG2: 121769Speter case O_RANG42: 122769Speter case O_RSNG42: 1232105Smckusic case O_SUCC2: 1242105Smckusic case O_SUCC24: 1252105Smckusic case O_PRED2: 1262105Smckusic case O_PRED24: 127769Speter if (p[1] == 0) 128769Speter break; 129769Speter case O_CON2: 130769Speter case O_CON24: 1312221Smckusic pack: 132769Speter if (p[1] < 128 && p[1] >= -128) { 133769Speter suboppr = subop = p[1]; 134769Speter p++; 135769Speter n--; 136769Speter if (op == O_CON2) { 137769Speter op = O_CON1; 1383077Smckusic # ifdef DEBUG 1393077Smckusic cp = otext[O_CON1]; 1403077Smckusic # endif DEBUG 141769Speter } 142769Speter if (op == O_CON24) { 143769Speter op = O_CON14; 1443077Smckusic # ifdef DEBUG 1453077Smckusic cp = otext[O_CON14]; 1463077Smckusic # endif DEBUG 147769Speter } 148769Speter } 149769Speter break; 150769Speter case O_CON8: 151769Speter { 152769Speter short *sp = &p[1]; 153769Speter 154769Speter #ifdef DEBUG 155769Speter if ( opt( 'k' ) ) 1563317Speter printf ( "%5d\tCON8\t%22.14e\n" , 157769Speter lc - HEADER_BYTES , 158769Speter * ( ( double * ) &p[1] ) ); 159769Speter #endif 1603077Smckusic # ifdef DEC11 1613077Smckusic word(op); 1623077Smckusic # else 1633077Smckusic word(op << 8); 1643077Smckusic # endif DEC11 165769Speter for ( i = 1 ; i <= 4 ; i ++ ) 166769Speter word ( *sp ++ ); 167769Speter return ( oldlc ); 168769Speter } 169769Speter default: 170769Speter if (op >= O_REL2 && op <= O_REL84) { 1711883Smckusic if ((i = (subop >> INDX) * 5 ) >= 30) 172769Speter i -= 30; 173769Speter else 174769Speter i += 2; 175769Speter #ifdef DEBUG 176769Speter string = &"IFEQ\0IFNE\0IFLT\0IFGT\0IFLE\0IFGE"[i]; 177769Speter #endif 178769Speter suboppr = 0; 179769Speter } 180769Speter break; 181769Speter case O_IF: 182769Speter case O_TRA: 183769Speter /***** 184769Speter codeline = 0; 185769Speter *****/ 1862184Smckusic /* relative addressing */ 1872184Smckusic p[1] -= ( unsigned ) lc + sizeof(short); 1882184Smckusic break; 189769Speter case O_FOR1U: 190769Speter case O_FOR2U: 191769Speter case O_FOR1D: 192769Speter case O_FOR2D: 1934025Smckusic /* sub opcode optimization */ 1944025Smckusic if (p[1] < 128 && p[1] >= -128 && p[1] != 0) { 1954025Smckusic suboppr = subop = p[1]; 1964025Smckusic p++; 1974025Smckusic n--; 1984025Smckusic } 199769Speter /* relative addressing */ 2004025Smckusic p[n - 1] -= ( unsigned ) lc + (n - 1) * sizeof(short); 201769Speter break; 202769Speter case O_CONC: 203769Speter #ifdef DEBUG 204769Speter (string = "'x'")[1] = p[1]; 205769Speter #endif 206769Speter suboppr = 0; 207769Speter op = O_CON1; 2083077Smckusic # ifdef DEBUG 2093077Smckusic cp = otext[O_CON1]; 2103077Smckusic # endif DEBUG 211769Speter subop = p[1]; 212769Speter goto around; 213769Speter case O_CONC4: 214769Speter #ifdef DEBUG 215769Speter (string = "'x'")[1] = p[1]; 216769Speter #endif 217769Speter suboppr = 0; 218769Speter op = O_CON14; 219769Speter subop = p[1]; 220769Speter goto around; 221769Speter case O_CON1: 222769Speter case O_CON14: 223769Speter suboppr = subop = p[1]; 224769Speter around: 225769Speter n--; 226769Speter break; 227769Speter case O_CASEBEG: 228769Speter casewrd = 0; 229769Speter return (oldlc); 230769Speter case O_CASEEND: 231769Speter if ((unsigned) lc & 1) { 232769Speter lc--; 233769Speter word(casewrd); 234769Speter } 235769Speter return (oldlc); 236769Speter case O_CASE1: 237769Speter #ifdef DEBUG 238769Speter if (opt('k')) 2393317Speter printf("%5d\tCASE1\t%d\n" 2403077Smckusic , lc - HEADER_BYTES, p[1]); 241769Speter #endif 242769Speter /* 243769Speter * this to build a byte size case table 244769Speter * saving bytes across calls in casewrd 245769Speter * so they can be put out by word() 246769Speter */ 247769Speter lc++; 248769Speter if ((unsigned) lc & 1) 2493077Smckusic # ifdef DEC11 2503077Smckusic casewrd = p[1] & 0377; 2513077Smckusic # else 2523077Smckusic casewrd = (p[1] & 0377) << 8; 2533077Smckusic # endif DEC11 254769Speter else { 255769Speter lc -= 2; 2563077Smckusic # ifdef DEC11 2573077Smckusic word(((p[1] & 0377) << 8) | casewrd); 2583077Smckusic # else 2593077Smckusic word((p[1] & 0377) | casewrd); 2603077Smckusic # endif DEC11 261769Speter } 262769Speter return (oldlc); 263769Speter case O_CASE2: 264769Speter #ifdef DEBUG 265769Speter if (opt('k')) 2663317Speter printf("%5d\tCASE2\t%d\n" 2673077Smckusic , lc - HEADER_BYTES , p[1]); 268769Speter #endif 2693077Smckusic word(p[1]); 270769Speter return (oldlc); 2714025Smckusic case O_FOR4U: 2724025Smckusic case O_FOR4D: 2734025Smckusic /* sub opcode optimization */ 2744025Smckusic lp = (long *)&p[1]; 2754025Smckusic if (*lp < 128 && *lp >= -128 && *lp != 0) { 2764025Smckusic suboppr = subop = *lp; 2774025Smckusic p += (sizeof(long) / sizeof(int)); 2784025Smckusic n--; 2794025Smckusic } 2804025Smckusic /* relative addressing */ 2814025Smckusic p[1 + (n - 2) * (sizeof(long) / sizeof(int))] -= 2824025Smckusic (unsigned)lc + (sizeof(short) + 2834025Smckusic (n - 2) * sizeof(long)); 2844025Smckusic goto longgen; 285769Speter case O_PUSH: 2863077Smckusic lp = (long *)&p[1]; 2873077Smckusic if (*lp == 0) 288769Speter return (oldlc); 2894025Smckusic /* and fall through */ 2904025Smckusic case O_RANG4: 2914025Smckusic case O_RANG24: 2924025Smckusic case O_RSNG4: 2934025Smckusic case O_RSNG24: 2944025Smckusic case O_SUCC4: 2954025Smckusic case O_PRED4: 2964025Smckusic /* sub opcode optimization */ 2974025Smckusic lp = (long *)&p[1]; 2984025Smckusic if (*lp < 128 && *lp >= -128 && *lp != 0) { 2993077Smckusic suboppr = subop = *lp; 3004025Smckusic p += (sizeof(long) / sizeof(int)); 301769Speter n--; 302769Speter } 303769Speter goto longgen; 304769Speter case O_TRA4: 305769Speter case O_CALL: 3061199Speter case O_FSAV: 307769Speter case O_GOTO: 308769Speter case O_NAM: 309769Speter case O_READE: 310769Speter /* absolute long addressing */ 3113077Smckusic lp = (long *)&p[1]; 3123077Smckusic *lp -= HEADER_BYTES; 313769Speter goto longgen; 314769Speter case O_RV1: 315769Speter case O_RV14: 316769Speter case O_RV2: 317769Speter case O_RV24: 318769Speter case O_RV4: 319769Speter case O_RV8: 320769Speter case O_RV: 321769Speter case O_LV: 3222105Smckusic /* 3232105Smckusic * positive offsets represent arguments 3242105Smckusic * and must use "ap" display entry rather 3252105Smckusic * than the "fp" entry 3262105Smckusic */ 3272105Smckusic if (p[1] >= 0) { 3282105Smckusic subop++; 3292105Smckusic suboppr++; 3302105Smckusic } 3313077Smckusic # ifdef PDP11 3323077Smckusic break; 3333077Smckusic # else 3343077Smckusic /* 3353077Smckusic * offsets out of range of word addressing 3363077Smckusic * must use long offset opcodes 3373077Smckusic */ 3383077Smckusic if (p[1] < SHORTADDR && p[1] >= -SHORTADDR) 3393077Smckusic break; 3403077Smckusic else { 341769Speter op += O_LRV - O_RV; 3423077Smckusic # ifdef DEBUG 3433077Smckusic cp = otext[op]; 3443077Smckusic # endif DEBUG 3453077Smckusic } 3463077Smckusic /* and fall through */ 3473077Smckusic # endif PDP11 348769Speter case O_BEG: 349769Speter case O_NODUMP: 350769Speter case O_CON4: 351769Speter case O_CASE4: 352769Speter longgen: 353769Speter n = (n << 1) - 1; 354*10562Smckusick if ( op == O_LRV || op == O_FOR4U || op == O_FOR4D) { 355769Speter n--; 356*10562Smckusick # if defined(ADDR32) && !defined(DEC11) 357*10562Smckusick p[n / 2] <<= 16; 358*10562Smckusick # endif 359*10562Smckusick } 360769Speter #ifdef DEBUG 3613077Smckusic if (opt('k')) { 3623317Speter printf("%5d\t%s", lc - HEADER_BYTES, cp+1); 363769Speter if (suboppr) 3643077Smckusic printf(":%d", suboppr); 3653077Smckusic for ( i = 2, lp = (long *)&p[1]; i < n 366769Speter ; i += sizeof ( long )/sizeof ( short ) ) 367769Speter printf( "\t%D " , *lp ++ ); 3683377Speter if (i == n) { 3693377Speter sp = (short *)lp; 3703377Speter printf( "\t%d ", *sp ); 3713377Speter } 372769Speter pchr ( '\n' ); 3733077Smckusic } 374769Speter #endif 375769Speter if ( op != O_CASE4 ) 3763077Smckusic # ifdef DEC11 3773077Smckusic word((op & 0377) | subop << 8); 3783077Smckusic # else 3793077Smckusic word(op << 8 | (subop & 0377)); 3803077Smckusic # endif DEC11 3813077Smckusic for ( i = 1, sp = (short *)&p[1]; i < n; i++) 3823077Smckusic word ( *sp ++ ); 383769Speter return ( oldlc ); 384769Speter } 385769Speter #ifdef DEBUG 386769Speter if (opt('k')) { 3873317Speter printf("%5d\t%s", lc - HEADER_BYTES, cp+1); 388769Speter if (suboppr) 389769Speter printf(":%d", suboppr); 390769Speter if (string) 391769Speter printf("\t%s",string); 392769Speter if (n > 1) 393769Speter pchr('\t'); 394769Speter for (i=1; i<n; i++) 3953077Smckusic printf("%d ", p[i]); 396769Speter pchr('\n'); 397769Speter } 398769Speter #endif 399769Speter if (op != NIL) 4003077Smckusic # ifdef DEC11 4013077Smckusic word((op & 0377) | subop << 8); 4023077Smckusic # else 4033077Smckusic word(op << 8 | (subop & 0377)); 4043077Smckusic # endif DEC11 405769Speter for (i=1; i<n; i++) 406769Speter word(p[i]); 407769Speter return (oldlc); 408769Speter } 409769Speter #endif OBJ 410769Speter 411769Speter /* 412769Speter * listnames outputs a list of enumerated type names which 413769Speter * can then be selected from to output a TSCAL 414769Speter * a pointer to the address in the code of the namelist 415769Speter * is kept in value[ NL_ELABEL ]. 416769Speter */ 417769Speter listnames(ap) 418769Speter 419769Speter register struct nl *ap; 420769Speter { 421769Speter struct nl *next; 422769Speter register int oldlc, len; 423769Speter register unsigned w; 424769Speter register char *strptr; 425769Speter 4263317Speter if ( !CGENNING ) 427769Speter /* code is off - do nothing */ 428769Speter return(NIL); 429769Speter if (ap->class != TYPE) 430769Speter ap = ap->type; 431769Speter if (ap->value[ NL_ELABEL ] != 0) { 432769Speter /* the list already exists */ 433769Speter return( ap -> value[ NL_ELABEL ] ); 434769Speter } 435769Speter # ifdef OBJ 436769Speter oldlc = lc; 437769Speter put(2, O_TRA, lc); 438769Speter ap->value[ NL_ELABEL ] = lc; 439769Speter # endif OBJ 440769Speter # ifdef PC 44110254Speter # ifdef vax 44210254Speter putprintf(" .data", 0); 44310254Speter putprintf(" .align 1", 0); 44410254Speter # endif vax 44510254Speter # ifdef mc68000 44610254Speter putprintf(" .data", 0); 44710254Speter putprintf(" .even", 0); 44810254Speter # endif mc68000 449769Speter ap -> value[ NL_ELABEL ] = getlab(); 450769Speter putlab( ap -> value[ NL_ELABEL ] ); 451769Speter # endif PC 452769Speter /* number of scalars */ 453769Speter next = ap->type; 454769Speter len = next->range[1]-next->range[0]+1; 455769Speter # ifdef OBJ 456769Speter put(2, O_CASE2, len); 457769Speter # endif OBJ 458769Speter # ifdef PC 459769Speter putprintf( " .word %d" , 0 , len ); 460769Speter # endif PC 461769Speter /* offsets of each scalar name */ 462769Speter len = (len+1)*sizeof(short); 463769Speter # ifdef OBJ 464769Speter put(2, O_CASE2, len); 465769Speter # endif OBJ 466769Speter # ifdef PC 467769Speter putprintf( " .word %d" , 0 , len ); 468769Speter # endif PC 469769Speter next = ap->chain; 470769Speter do { 471769Speter for(strptr = next->symbol; *strptr++; len++) 472769Speter continue; 473769Speter len++; 474769Speter # ifdef OBJ 475769Speter put(2, O_CASE2, len); 476769Speter # endif OBJ 477769Speter # ifdef PC 478769Speter putprintf( " .word %d" , 0 , len ); 479769Speter # endif PC 480769Speter } while (next = next->chain); 481769Speter /* list of scalar names */ 482769Speter strptr = getnext(ap, &next); 483769Speter # ifdef OBJ 484769Speter do { 4853077Smckusic # ifdef DEC11 4863077Smckusic w = (unsigned) *strptr; 4873077Smckusic # else 4883077Smckusic w = *strptr << 8; 4893077Smckusic # endif DEC11 490769Speter if (!*strptr++) 491769Speter strptr = getnext(next, &next); 4923077Smckusic # ifdef DEC11 4933077Smckusic w |= *strptr << 8; 4943077Smckusic # else 4953077Smckusic w |= (unsigned) *strptr; 4963077Smckusic # endif DEC11 497769Speter if (!*strptr++) 498769Speter strptr = getnext(next, &next); 499769Speter word(w); 500769Speter } while (next); 501769Speter /* jump over the mess */ 502769Speter patch(oldlc); 503769Speter # endif OBJ 504769Speter # ifdef PC 505769Speter while ( next ) { 506769Speter while ( *strptr ) { 507769Speter putprintf( " .byte 0%o" , 1 , *strptr++ ); 508769Speter for ( w = 2 ; ( w <= 8 ) && *strptr ; w ++ ) { 509769Speter putprintf( ",0%o" , 1 , *strptr++ ); 510769Speter } 511769Speter putprintf( "" , 0 ); 512769Speter } 513769Speter putprintf( " .byte 0" , 0 ); 514769Speter strptr = getnext( next , &next ); 515769Speter } 516769Speter putprintf( " .text" , 0 ); 517769Speter # endif PC 518769Speter return( ap -> value[ NL_ELABEL ] ); 519769Speter } 520769Speter 521769Speter getnext(next, new) 522769Speter 523769Speter struct nl *next, **new; 524769Speter { 525769Speter if (next != NIL) { 526769Speter next = next->chain; 527769Speter *new = next; 528769Speter } 529769Speter if (next == NIL) 530769Speter return(""); 531769Speter #ifdef OBJ 5323317Speter if (opt('k') && CGENNING ) 5333317Speter printf("%5d\t\t\"%s\"\n", lc-HEADER_BYTES, next->symbol); 5342213Speter #endif OBJ 535769Speter return(next->symbol); 536769Speter } 537769Speter 538769Speter #ifdef OBJ 539769Speter /* 540769Speter * Putspace puts out a table 541769Speter * of nothing to leave space 542769Speter * for the case branch table e.g. 543769Speter */ 544769Speter putspace(n) 545769Speter int n; 546769Speter { 547769Speter register i; 548769Speter 5493317Speter if ( !CGENNING ) 550769Speter /* 551769Speter * code disabled - do nothing 552769Speter */ 553769Speter return(lc); 554769Speter #ifdef DEBUG 555769Speter if (opt('k')) 5563317Speter printf("%5d\t.=.+%d\n", lc - HEADER_BYTES, n); 557769Speter #endif 558769Speter for (i = even(n); i > 0; i -= 2) 559769Speter word(0); 560769Speter } 561769Speter 562769Speter putstr(sptr, padding) 563769Speter 564769Speter char *sptr; 565769Speter int padding; 566769Speter { 567769Speter register unsigned short w; 568769Speter register char *strptr = sptr; 569769Speter register int pad = padding; 570769Speter 5713317Speter if ( !CGENNING ) 572769Speter /* 573769Speter * code disabled - do nothing 574769Speter */ 575769Speter return(lc); 576769Speter #ifdef DEBUG 577769Speter if (opt('k')) 5783317Speter printf("%5d\t\t\"%s\"\n", lc-HEADER_BYTES, strptr); 579769Speter #endif 580769Speter if (pad == 0) { 581769Speter do { 5823077Smckusic # ifdef DEC11 5833077Smckusic w = (unsigned short) * strptr; 5843077Smckusic # else 5853077Smckusic w = (unsigned short)*strptr<<8; 5863077Smckusic # endif DEC11 587769Speter if (w) 5883077Smckusic # ifdef DEC11 5893077Smckusic w |= *++strptr << 8; 5903077Smckusic # else 5913077Smckusic w |= *++strptr; 5923077Smckusic # endif DEC11 593769Speter word(w); 594769Speter } while (*strptr++); 595769Speter } else { 5963077Smckusic # ifdef DEC11 5973077Smckusic do { 5983077Smckusic w = (unsigned short) * strptr; 5993077Smckusic if (w) { 6003077Smckusic if (*++strptr) 6013077Smckusic w |= *strptr << 8; 6023077Smckusic else { 6033077Smckusic w |= ' \0'; 6043077Smckusic pad--; 6053077Smckusic } 6063077Smckusic word(w); 6073077Smckusic } 6083077Smckusic } while (*strptr++); 6093077Smckusic # else 6103077Smckusic do { 6113077Smckusic w = (unsigned short)*strptr<<8; 6123077Smckusic if (w) { 6133077Smckusic if (*++strptr) 6143077Smckusic w |= *strptr; 6153077Smckusic else { 6163077Smckusic w |= ' '; 6173077Smckusic pad--; 6183077Smckusic } 6193077Smckusic word(w); 6203077Smckusic } 6213077Smckusic } while (*strptr++); 6223077Smckusic # endif DEC11 623769Speter while (pad > 1) { 624769Speter word(' '); 625769Speter pad -= 2; 626769Speter } 627769Speter if (pad == 1) 6283077Smckusic # ifdef DEC11 6293077Smckusic word(' '); 6303077Smckusic # else 6313077Smckusic word(' \0'); 6323077Smckusic # endif DEC11 633769Speter else 634769Speter word(0); 635769Speter } 636769Speter } 637769Speter #endif OBJ 638769Speter 639769Speter lenstr(sptr, padding) 640769Speter 641769Speter char *sptr; 642769Speter int padding; 643769Speter 644769Speter { 645769Speter register int cnt; 646769Speter register char *strptr = sptr; 647769Speter 648769Speter cnt = padding; 649769Speter do { 650769Speter cnt++; 651769Speter } while (*strptr++); 652769Speter return((++cnt) & ~1); 653769Speter } 654769Speter 655769Speter /* 656769Speter * Patch repairs the branch 657769Speter * at location loc to come 658769Speter * to the current location. 659769Speter * for PC, this puts down the label 660769Speter * and the branch just references that label. 661769Speter * lets here it for two pass assemblers. 662769Speter */ 663769Speter patch(loc) 664769Speter { 665769Speter 666769Speter # ifdef OBJ 6673077Smckusic patchfil(loc, (long)(lc-loc-2), 1); 668769Speter # endif OBJ 669769Speter # ifdef PC 670769Speter putlab( loc ); 671769Speter # endif PC 672769Speter } 673769Speter 674769Speter #ifdef OBJ 675769Speter patch4(loc) 676769Speter { 6773077Smckusic patchfil(loc, (long)(lc - HEADER_BYTES), 2); 678769Speter } 679769Speter 680769Speter /* 6817921Smckusick * Patchfil makes loc+2 have jmploc 682769Speter * as its contents. 683769Speter */ 6847921Smckusick patchfil(loc, jmploc, words) 685769Speter PTR_DCL loc; 6867921Smckusick long jmploc; 6873077Smckusic int words; 688769Speter { 689769Speter register i; 690*10562Smckusick short val; 691769Speter 6923317Speter if ( !CGENNING ) 693769Speter return; 694769Speter if (loc > (unsigned) lc) 695769Speter panic("patchfil"); 696769Speter #ifdef DEBUG 697769Speter if (opt('k')) 6987921Smckusick printf("\tpatch %u %D\n", loc - HEADER_BYTES, jmploc); 699769Speter #endif 7007921Smckusick val = jmploc; 701769Speter do { 7023077Smckusic # ifndef DEC11 7033077Smckusic if (words > 1) 7047921Smckusick val = jmploc >> 16; 7053077Smckusic else 7067921Smckusick val = jmploc; 7073077Smckusic # endif DEC11 708769Speter i = ((unsigned) loc + 2 - ((unsigned) lc & ~01777))/2; 709*10562Smckusick if (i >= 0 && i < 1024) { 7103077Smckusic obuf[i] = val; 711*10562Smckusick } else { 712769Speter lseek(ofil, (long) loc+2, 0); 7133077Smckusic write(ofil, &val, 2); 714769Speter lseek(ofil, (long) 0, 2); 715769Speter } 716769Speter loc += 2; 7173077Smckusic # ifdef DEC11 7187921Smckusick val = jmploc >> 16; 7193077Smckusic # endif DEC11 720769Speter } while (--words); 721769Speter } 722769Speter 723769Speter /* 724769Speter * Put the word o into the code 725769Speter */ 726769Speter word(o) 727769Speter int o; 728769Speter { 729769Speter 730769Speter *obufp = o; 731769Speter obufp++; 732769Speter lc += 2; 733769Speter if (obufp >= obuf+512) 734769Speter pflush(); 735769Speter } 736769Speter 737769Speter extern char *obj; 738769Speter /* 739769Speter * Flush the code buffer 740769Speter */ 741769Speter pflush() 742769Speter { 743769Speter register i; 744769Speter 745769Speter i = (obufp - ( ( short * ) obuf ) ) * 2; 746769Speter if (i != 0 && write(ofil, obuf, i) != i) 747769Speter perror(obj), pexit(DIED); 748769Speter obufp = obuf; 749769Speter } 750769Speter #endif OBJ 751769Speter 752769Speter /* 753769Speter * Getlab - returns the location counter. 754769Speter * included here for the eventual code generator. 755769Speter * for PC, thank you! 756769Speter */ 757769Speter getlab() 758769Speter { 759769Speter # ifdef OBJ 760769Speter 761769Speter return (lc); 762769Speter # endif OBJ 763769Speter # ifdef PC 764769Speter static long lastlabel; 765769Speter 766769Speter return ( ++lastlabel ); 767769Speter # endif PC 768769Speter } 769769Speter 770769Speter /* 771769Speter * Putlab - lay down a label. 772769Speter * for PC, just print the label name with a colon after it. 773769Speter */ 774769Speter putlab(l) 775769Speter int l; 776769Speter { 777769Speter 778769Speter # ifdef PC 779769Speter putprintf( PREFIXFORMAT , 1 , LABELPREFIX , l ); 780769Speter putprintf( ":" , 0 ); 781769Speter # endif PC 782769Speter return (l); 783769Speter } 784