12 Bprint(&bso, "%5.2f dodata\n", cputime());
14 for(p = datap; p != P; p = p->link) {
16 if(p->as == ADYNT || p->as == AINIT)
21 diag("initialize non-data (%d): %s\n%P",
23 t = p->from.offset + p->width;
25 diag("initialize bounds (%ld): %s\n%P",
26 s->value, s->name, p);
28 /* allocate small guys */
30 for(i=0; i<NHASH; i++)
31 for(s = hash[i]; s != S; s = s->link) {
37 diag("%s: no size", s->name);
49 /* allocate the rest of the data */
50 for(i=0; i<NHASH; i++)
51 for(s = hash[i]; s != S; s = s->link) {
52 if(s->type != SDATA) {
64 * pad data with bss that fits up to next
65 * 8k boundary, then push data to 8k
67 u = rnd(datsize, 8192);
69 for(i=0; i<NHASH; i++)
70 for(s = hash[i]; s != S; s = s->link) {
86 for(i=0; i<NHASH; i++)
87 for(s = hash[i]; s != S; s = s->link) {
91 s->value = bsssize + datsize;
94 xdefine("bdata", SDATA, 0L);
95 xdefine("edata", SBSS, datsize);
96 xdefine("end", SBSS, bsssize + datsize);
97 /* etext is defined in span.c */
105 for(i=0; i<20; i++) {
106 if(p == P || p->as != AJMP)
118 Bprint(&bso, "%5.2f follow\n", cputime());
124 firstp = firstp->link;
140 if((q = p->pcond) != P) {
147 /* copy up to 4 instructions to avoid branch */
148 for(i=0,q=p; i<4; i++,q=q->link) {
173 if(q->pcond == P || q->pcond->mark)
175 if(a == ACALL || a == ALOOP)
187 if(q->as != a || q->pcond == P || q->pcond->mark)
190 q->as = relinv(q->as);
205 q->to.type = D_BRANCH;
206 q->to.offset = p->pc;
214 if(a == AJMP || a == ARET || a == AIRETL)
218 q = brchain(p->link);
219 if(q != P && q->mark)
226 q = brchain(p->pcond);
243 case AJEQ: return AJNE;
244 case AJNE: return AJEQ;
245 case AJLE: return AJGT;
246 case AJLS: return AJHI;
247 case AJLT: return AJGE;
248 case AJMI: return AJPL;
249 case AJGE: return AJLT;
250 case AJPL: return AJMI;
251 case AJGT: return AJLE;
252 case AJHI: return AJLS;
253 case AJCS: return AJCC;
254 case AJCC: return AJCS;
255 case AJPS: return AJPC;
256 case AJPC: return AJPS;
257 case AJOS: return AJOC;
258 case AJOC: return AJOS;
260 diag("unknown relation: %s in %s", anames[a], TNAME);
271 for(p = datap; p != P; p = p->link) {
273 if(x != D_EXTERN && x != D_STATIC)
276 if(s->type == 0 || s->type == SXREF)
277 diag("undefined %s initializer of %s",
278 s->name, p->from.sym->name);
279 p->to.offset += s->value;
280 p->to.type = D_CONST;
281 if(s->type == SDATA || s->type == SBSS)
282 p->to.offset += INITDAT;
295 Bprint(&bso, "%5.2f mkfwd\n", cputime());
299 Bprint(&bso, "%5.2f patch\n", cputime());
301 s = lookup("exit", 0);
303 for(p = firstp; p != P; p = p->link) {
306 if(p->as == ACALL || p->as == ARET) {
310 Bprint(&bso, "%s calls %s\n", TNAME, s->name);
313 /* diag prints TNAME first */
314 diag("%s is undefined", s->name);
317 break; /* or fall through to set offset? */
319 p->to.offset = s->value;
326 p->to.type = D_BRANCH;
329 if(p->to.type != D_BRANCH || p->pcond == UP)
332 for(q = firstp; q != P;) {
334 if(c >= q->forwd->pc) {
343 diag("branch out of range in %s\n%P", TNAME, p);
349 for(p = firstp; p != P; p = p->link) {
352 p->mark = 0; /* initialization for follow */
353 if(p->pcond != P && p->pcond != UP) {
354 p->pcond = brloop(p->pcond);
356 if(p->to.type == D_BRANCH)
357 p->to.offset = p->pcond->pc;
368 long dwn[LOG], cnt[LOG];
371 for(i=0; i<LOG; i++) {
374 cnt[i] = LOG * cnt[i-1];
379 for(p = firstp; p != P; p = p->link) {
403 for(q = p; q != P; q = q->pcond) {
417 long autoffset, deltasp;
418 int a, f, curframe, curbecome, maxbecome;
424 for(p = firstp; p != P; p = p->link) {
426 /* find out how much arg space is used in this TEXT */
427 if(p->to.type == (D_INDIR+D_SP))
428 if(p->to.offset > curframe)
429 curframe = p->to.offset;
433 if(curtext && curtext->from.sym) {
434 curtext->from.sym->frame = curframe;
435 curtext->from.sym->become = curbecome;
436 if(curbecome > maxbecome)
437 maxbecome = curbecome;
446 /* special form of RET is BECOME */
447 if(p->from.type == D_CONST)
448 if(p->from.offset > curbecome)
449 curbecome = p->from.offset;
453 if(curtext && curtext->from.sym) {
454 curtext->from.sym->frame = curframe;
455 curtext->from.sym->become = curbecome;
456 if(curbecome > maxbecome)
457 maxbecome = curbecome;
461 print("max become = %d\n", maxbecome);
462 xdefine("ALEFbecome", STEXT, maxbecome);
465 for(p = firstp; p != P; p = p->link) {
471 if(curtext != P && curtext->from.sym != S && curtext->to.offset >= 0) {
472 f = maxbecome - curtext->from.sym->frame;
475 /* calling a become or calling a variable */
476 if(p->to.sym == S || p->to.sym->become) {
477 curtext->to.offset += f;
480 print("%D calling %D increase %d\n",
481 &curtext->from, &p->to, f);
491 for(p = firstp; p != P; p = p->link) {
494 autoffset = p->to.offset;
500 p->from.type = D_CONST;
501 p->from.offset = autoffset;
507 p->from.offset += deltasp;
509 p->from.offset += deltasp + 4;
512 p->to.offset += deltasp;
514 p->to.offset += deltasp + 4;
539 if(autoffset != deltasp)
540 diag("unbalanced PUSH/POP");
541 if(p->from.type == D_CONST)
550 q->from.type = D_CONST;
551 q->from.offset = -autoffset;
564 q->from.type = D_CONST;
565 q->from.offset = -autoffset;
579 while(*s == ' ' || *s == '\t')
581 if(*s == '-' || *s == '+') {
584 while(*s == ' ' || *s == '\t')
587 if(s[0]=='0' && s[1]){
588 if(s[1]=='x' || s[1]=='X'){
591 if(*s >= '0' && *s <= '9')
592 n = n*16 + *s++ - '0';
593 else if(*s >= 'a' && *s <= 'f')
594 n = n*16 + *s++ - 'a' + 10;
595 else if(*s >= 'A' && *s <= 'F')
596 n = n*16 + *s++ - 'A' + 10;
601 while(*s >= '0' && *s <= '7')
602 n = n*8 + *s++ - '0';
604 while(*s >= '0' && *s <= '9')
605 n = n*10 + *s++ - '0';
617 for(i=0; i<NHASH; i++)
618 for(s = hash[i]; s != S; s = s->link)
620 diag("%s: not defined", s->name);
629 for(i = 0; i < NHASH; i++)
630 for(s = hash[i]; s != S; s = s->link)
631 if(s->sig != 0 && s->type == SXREF && (nimports == 0 || s->subtype == SIMPORT)){
633 diag("value != 0 on SXREF");
636 Bprint(&bso, "IMPORT: %s sig=%lux v=%ld\n", s->name, s->sig, s->value);
643 ckoff(Sym *s, long v)
645 if(v < 0 || v >= 1<<Roffset)
646 diag("relocation offset %ld for %s out of range", v, s->name);
650 newdata(Sym *s, int o, int w, int t)
666 p->to.type = D_CONST;
673 int i, j, n, off, nb, sv, ne;
674 Sym *s, *et, *str, **esyms;
676 char buf[NSNAME], *t;
679 for(i = 0; i < NHASH; i++)
680 for(s = hash[i]; s != S; s = s->link)
681 if(s->sig != 0 && s->type != SXREF && s->type != SUNDEF && (nexports == 0 || s->subtype == SEXPORT))
683 esyms = malloc(n*sizeof(Sym*));
686 for(i = 0; i < NHASH; i++)
687 for(s = hash[i]; s != S; s = s->link)
688 if(s->sig != 0 && s->type != SXREF && s->type != SUNDEF && (nexports == 0 || s->subtype == SEXPORT))
690 for(i = 0; i < ne-1; i++)
691 for(j = i+1; j < ne; j++)
692 if(strcmp(esyms[i]->name, esyms[j]->name) > 0){
700 et = lookup(EXPTAB, 0);
701 if(et->type != 0 && et->type != SXREF)
702 diag("%s already defined", EXPTAB);
704 str = lookup(".string", 0);
708 for(i = 0; i < ne; i++){
712 /* Bprint(&bso, "EXPORT: %s sig=%lux t=%d\n", s->name, s->sig, s->type); */
715 p = newdata(et, off, sizeof(long), D_EXTERN);
717 p->to.offset = s->sig;
720 p = newdata(et, off, sizeof(long), D_EXTERN);
723 p->to.index = D_EXTERN;
733 p = newdata(str, sv-NSNAME, NSNAME, D_STATIC);
734 p->to.type = D_SCONST;
735 memmove(p->to.scon, buf, NSNAME);
743 p = newdata(et, off, sizeof(long), D_EXTERN);
746 p->to.index = D_STATIC;
752 p = newdata(str, sv-nb, nb, D_STATIC);
753 p->to.type = D_SCONST;
754 memmove(p->to.scon, buf, nb);
757 for(i = 0; i < 3; i++){
758 newdata(et, off, sizeof(long), D_EXTERN);