mirror of
https://github.com/golang/go
synced 2024-11-25 15:08:02 -07:00
6g, 6l, 8g, 8l: move read-only data to text segment
Changing 5g and 5l too, but it doesn't work yet. R=ken2 CC=golang-dev https://golang.org/cl/2136047
This commit is contained in:
parent
be443ee8bc
commit
698fb4f192
@ -147,6 +147,8 @@ ggloblnod(Node *nam, int32 width)
|
|||||||
p->to.sym = S;
|
p->to.sym = S;
|
||||||
p->to.type = D_CONST;
|
p->to.type = D_CONST;
|
||||||
p->to.offset = width;
|
p->to.offset = width;
|
||||||
|
if(nam->readonly)
|
||||||
|
p->from.scale = RODATA;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -163,6 +165,7 @@ ggloblsym(Sym *s, int32 width, int dupok)
|
|||||||
p->to.offset = width;
|
p->to.offset = width;
|
||||||
if(dupok)
|
if(dupok)
|
||||||
p->from.scale = DUPOK;
|
p->from.scale = DUPOK;
|
||||||
|
p->from.scale |= RODATA;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
@ -47,13 +47,17 @@ Pconv(Fmt *fp)
|
|||||||
{
|
{
|
||||||
char str[STRINGSZ];
|
char str[STRINGSZ];
|
||||||
Prog *p;
|
Prog *p;
|
||||||
|
char scale[40];
|
||||||
|
|
||||||
p = va_arg(fp->args, Prog*);
|
p = va_arg(fp->args, Prog*);
|
||||||
sconsize = 8;
|
sconsize = 8;
|
||||||
|
scale[0] = '\0';
|
||||||
|
if(p->from.scale != 0 && (p->as == AGLOBL || p->as == ATEXT))
|
||||||
|
snprint(scale, sizeof scale, "%d,", p->from.scale);
|
||||||
switch(p->as) {
|
switch(p->as) {
|
||||||
default:
|
default:
|
||||||
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%D",
|
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%s%D",
|
||||||
p->loc, p->lineno, p->as, &p->from, &p->to);
|
p->loc, p->lineno, p->as, &p->from, scale, &p->to);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ADATA:
|
case ADATA:
|
||||||
@ -63,8 +67,8 @@ Pconv(Fmt *fp)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case ATEXT:
|
case ATEXT:
|
||||||
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%lD",
|
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%s%lD",
|
||||||
p->loc, p->lineno, p->as, &p->from, &p->to);
|
p->loc, p->lineno, p->as, &p->from, scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return fmtstrcpy(fp, str);
|
return fmtstrcpy(fp, str);
|
||||||
|
@ -33,6 +33,7 @@
|
|||||||
#define NOPROF (1<<0)
|
#define NOPROF (1<<0)
|
||||||
#define DUPOK (1<<1)
|
#define DUPOK (1<<1)
|
||||||
#define NOSPLIT (1<<2)
|
#define NOSPLIT (1<<2)
|
||||||
|
#define RODATA (1<<3)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* amd64
|
* amd64
|
||||||
|
@ -136,16 +136,16 @@ addstring(Sym *s, char *str)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
n = strlen(str)+1;
|
n = strlen(str)+1;
|
||||||
while(n > 0) {
|
while(n > 0) {
|
||||||
m = n;
|
m = n;
|
||||||
if(m > sizeof(p->to.scon))
|
if(m > sizeof(p->to.scon))
|
||||||
m = sizeof(p->to.scon);
|
m = sizeof(p->to.scon);
|
||||||
p = newdata(s, s->value, m, D_EXTERN);
|
p = newdata(s, s->size, m, D_EXTERN);
|
||||||
p->to.type = D_SCONST;
|
p->to.type = D_SCONST;
|
||||||
memmove(p->to.scon, str, m);
|
memmove(p->to.scon, str, m);
|
||||||
s->value += m;
|
s->size += m;
|
||||||
str += m;
|
str += m;
|
||||||
n -= m;
|
n -= m;
|
||||||
}
|
}
|
||||||
@ -161,9 +161,9 @@ adduintxx(Sym *s, uint64 v, int wid)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, wid, D_EXTERN);
|
p = newdata(s, s->size, wid, D_EXTERN);
|
||||||
s->value += wid;
|
s->size += wid;
|
||||||
p->to.type = D_CONST;
|
p->to.type = D_CONST;
|
||||||
p->to.offset = v;
|
p->to.offset = v;
|
||||||
return r;
|
return r;
|
||||||
@ -203,9 +203,9 @@ addaddr(Sym *s, Sym *t)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, Ptrsize, D_EXTERN);
|
p = newdata(s, s->size, Ptrsize, D_EXTERN);
|
||||||
s->value += Ptrsize;
|
s->size += Ptrsize;
|
||||||
p->to.type = D_ADDR;
|
p->to.type = D_ADDR;
|
||||||
p->to.index = D_EXTERN;
|
p->to.index = D_EXTERN;
|
||||||
p->to.offset = 0;
|
p->to.offset = 0;
|
||||||
@ -223,9 +223,9 @@ addsize(Sym *s, Sym *t)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, Ptrsize, D_EXTERN);
|
p = newdata(s, s->size, Ptrsize, D_EXTERN);
|
||||||
s->value += Ptrsize;
|
s->size += Ptrsize;
|
||||||
p->to.type = D_SIZE;
|
p->to.type = D_SIZE;
|
||||||
p->to.index = D_EXTERN;
|
p->to.index = D_EXTERN;
|
||||||
p->to.offset = 0;
|
p->to.offset = 0;
|
||||||
@ -321,13 +321,12 @@ doelf(void)
|
|||||||
s = lookup(".dynsym", 0);
|
s = lookup(".dynsym", 0);
|
||||||
s->type = SELFDATA;
|
s->type = SELFDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
s->value += ELF64SYMSIZE;
|
s->size += ELF64SYMSIZE;
|
||||||
|
|
||||||
/* dynamic string table */
|
/* dynamic string table */
|
||||||
s = lookup(".dynstr", 0);
|
s = lookup(".dynstr", 0);
|
||||||
s->type = SELFDATA;
|
s->type = SELFDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
s->value += ELF64SYMSIZE;
|
|
||||||
addstring(s, "");
|
addstring(s, "");
|
||||||
dynstr = s;
|
dynstr = s;
|
||||||
|
|
||||||
@ -467,7 +466,7 @@ asmb(void)
|
|||||||
int32 v, magic;
|
int32 v, magic;
|
||||||
int a, dynsym;
|
int a, dynsym;
|
||||||
uchar *op1;
|
uchar *op1;
|
||||||
vlong vl, va, startva, fo, w, symo, elfsymo, elfstro, elfsymsize, machlink;
|
vlong vl, va, startva, fo, w, symo, elfsymo, elfstro, elfsymsize, machlink, etext;
|
||||||
vlong symdatva = SYMDATVA;
|
vlong symdatva = SYMDATVA;
|
||||||
ElfEhdr *eh;
|
ElfEhdr *eh;
|
||||||
ElfPhdr *ph, *pph;
|
ElfPhdr *ph, *pph;
|
||||||
@ -519,6 +518,16 @@ asmb(void)
|
|||||||
}
|
}
|
||||||
cflush();
|
cflush();
|
||||||
|
|
||||||
|
datap = datsort(datap);
|
||||||
|
|
||||||
|
/* output read-only data in text segment */
|
||||||
|
etext = INITTEXT + textsize;
|
||||||
|
for(v = pc; v < etext; v += sizeof(buf)-Dbufslop) {
|
||||||
|
if(etext - v > sizeof(buf)-Dbufslop)
|
||||||
|
datblk(v, sizeof(buf)-Dbufslop);
|
||||||
|
else
|
||||||
|
datblk(v, etext-v);
|
||||||
|
}
|
||||||
|
|
||||||
switch(HEADTYPE) {
|
switch(HEADTYPE) {
|
||||||
default:
|
default:
|
||||||
@ -564,12 +573,11 @@ asmb(void)
|
|||||||
textsize = INITDAT;
|
textsize = INITDAT;
|
||||||
}
|
}
|
||||||
|
|
||||||
datap = datsort(datap);
|
|
||||||
for(v = 0; v < datsize; v += sizeof(buf)-Dbufslop) {
|
for(v = 0; v < datsize; v += sizeof(buf)-Dbufslop) {
|
||||||
if(datsize-v > sizeof(buf)-Dbufslop)
|
if(datsize-v > sizeof(buf)-Dbufslop)
|
||||||
datblk(v, sizeof(buf)-Dbufslop);
|
datblk(v+INITDAT, sizeof(buf)-Dbufslop);
|
||||||
else
|
else
|
||||||
datblk(v, datsize-v);
|
datblk(v+INITDAT, datsize-v);
|
||||||
}
|
}
|
||||||
|
|
||||||
machlink = 0;
|
machlink = 0;
|
||||||
@ -1102,6 +1110,8 @@ datsort(Prog *l)
|
|||||||
for(p = l; p != P; p = p->link) {
|
for(p = l; p != P; p = p->link) {
|
||||||
a = &p->from;
|
a = &p->from;
|
||||||
a->offset += a->sym->value;
|
a->offset += a->sym->value;
|
||||||
|
if(a->sym->type != SRODATA)
|
||||||
|
a->offset += INITDAT;
|
||||||
}
|
}
|
||||||
datp = dsort(l);
|
datp = dsort(l);
|
||||||
return datp;
|
return datp;
|
||||||
@ -1202,10 +1212,10 @@ datblk(int32 s, int32 n)
|
|||||||
diag("missing symbol %s", p->to.sym->name);
|
diag("missing symbol %s", p->to.sym->name);
|
||||||
}
|
}
|
||||||
o += p->to.sym->value;
|
o += p->to.sym->value;
|
||||||
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF)
|
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF && p->to.sym->type != SRODATA)
|
||||||
o += INITDAT;
|
o += INITDAT;
|
||||||
if(dlm)
|
if(dlm)
|
||||||
dynreloc(p->to.sym, l+s+INITDAT, 1);
|
dynreloc(p->to.sym, l+s, 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fl = o;
|
fl = o;
|
||||||
@ -1266,6 +1276,7 @@ datblk(int32 s, int32 n)
|
|||||||
if(a->sym->type == SMACHO)
|
if(a->sym->type == SMACHO)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
curp = p;
|
||||||
switch(p->to.type) {
|
switch(p->to.type) {
|
||||||
case D_FCONST:
|
case D_FCONST:
|
||||||
switch(c) {
|
switch(c) {
|
||||||
@ -1273,17 +1284,17 @@ datblk(int32 s, int32 n)
|
|||||||
case 4:
|
case 4:
|
||||||
fl = ieeedtof(&p->to.ieee);
|
fl = ieeedtof(&p->to.ieee);
|
||||||
cast = (uchar*)&fl;
|
cast = (uchar*)&fl;
|
||||||
outa(c, cast, fnuxi4, l+s+INITDAT);
|
outa(c, cast, fnuxi4, l+s);
|
||||||
break;
|
break;
|
||||||
case 8:
|
case 8:
|
||||||
cast = (uchar*)&p->to.ieee;
|
cast = (uchar*)&p->to.ieee;
|
||||||
outa(c, cast, fnuxi8, l+s+INITDAT);
|
outa(c, cast, fnuxi8, l+s);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_SCONST:
|
case D_SCONST:
|
||||||
outa(c, (uchar*)p->to.scon, nil, l+s+INITDAT);
|
outa(c, (uchar*)p->to.scon, nil, l+s);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@ -1293,7 +1304,7 @@ datblk(int32 s, int32 n)
|
|||||||
if(p->to.type == D_ADDR) {
|
if(p->to.type == D_ADDR) {
|
||||||
if(p->to.sym) {
|
if(p->to.sym) {
|
||||||
o += p->to.sym->value;
|
o += p->to.sym->value;
|
||||||
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF)
|
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF && p->to.sym->type != SRODATA)
|
||||||
o += INITDAT;
|
o += INITDAT;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1301,17 +1312,17 @@ datblk(int32 s, int32 n)
|
|||||||
cast = (uchar*)&fl;
|
cast = (uchar*)&fl;
|
||||||
switch(c) {
|
switch(c) {
|
||||||
case 1:
|
case 1:
|
||||||
outa(c, cast, inuxi1, l+s+INITDAT);
|
outa(c, cast, inuxi1, l+s);
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
outa(c, cast, inuxi2, l+s+INITDAT);
|
outa(c, cast, inuxi2, l+s);
|
||||||
break;
|
break;
|
||||||
case 4:
|
case 4:
|
||||||
outa(c, cast, inuxi4, l+s+INITDAT);
|
outa(c, cast, inuxi4, l+s);
|
||||||
break;
|
break;
|
||||||
case 8:
|
case 8:
|
||||||
cast = (uchar*)&o;
|
cast = (uchar*)&o;
|
||||||
outa(c, cast, inuxi8, l+s+INITDAT);
|
outa(c, cast, inuxi8, l+s);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -169,6 +169,7 @@ enum
|
|||||||
SMACHO,
|
SMACHO,
|
||||||
SFIXED,
|
SFIXED,
|
||||||
SELFDATA,
|
SELFDATA,
|
||||||
|
SRODATA,
|
||||||
|
|
||||||
NHASH = 10007,
|
NHASH = 10007,
|
||||||
NHUNK = 100000,
|
NHUNK = 100000,
|
||||||
|
@ -47,41 +47,30 @@ listinit(void)
|
|||||||
int
|
int
|
||||||
Pconv(Fmt *fp)
|
Pconv(Fmt *fp)
|
||||||
{
|
{
|
||||||
char str[STRINGSZ], str1[STRINGSZ];
|
|
||||||
Prog *p;
|
Prog *p;
|
||||||
|
|
||||||
p = va_arg(fp->args, Prog*);
|
p = va_arg(fp->args, Prog*);
|
||||||
if(p == P)
|
|
||||||
return fmtstrcpy(fp, "<P>");
|
|
||||||
|
|
||||||
bigP = p;
|
bigP = p;
|
||||||
|
|
||||||
snprint(str1, sizeof(str1), "(%ld)", p->line);
|
|
||||||
switch(p->as) {
|
switch(p->as) {
|
||||||
case ATEXT:
|
case ATEXT:
|
||||||
if(p->from.scale) {
|
if(p->from.scale) {
|
||||||
snprint(str, sizeof(str), "%-7s %-7A %D,%d,%lD",
|
fmtprint(fp, "(%d) %A %D,%d,%D",
|
||||||
str1, p->as, &p->from, p->from.scale, &p->to);
|
p->line, p->as, &p->from, p->from.scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
snprint(str, sizeof(str), "%-7s %-7A %D,%lD",
|
|
||||||
str1, p->as, &p->from, &p->to);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
default:
|
||||||
snprint(str, sizeof(str), "%-7s %-7A %D,%D",
|
fmtprint(fp, "(%d) %A %D,%D",
|
||||||
str1, p->as, &p->from, &p->to);
|
p->line, p->as, &p->from, &p->to);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ADATA:
|
case ADATA:
|
||||||
case AINIT:
|
case AINIT:
|
||||||
case ADYNT:
|
case ADYNT:
|
||||||
snprint(str, sizeof(str), "%-7s %-7A %D/%d,%D",
|
fmtprint(fp, "(%d) %A %D/%d,%D",
|
||||||
str1, p->as, &p->from, p->from.scale, &p->to);
|
p->line, p->as, &p->from, p->from.scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
bigP = P;
|
bigP = P;
|
||||||
return fmtstrcpy(fp, str);
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
@ -633,18 +633,20 @@ loop:
|
|||||||
s = p->from.sym;
|
s = p->from.sym;
|
||||||
if(s->type == 0 || s->type == SXREF) {
|
if(s->type == 0 || s->type == SXREF) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 0;
|
s->size = 0;
|
||||||
}
|
}
|
||||||
if(s->type != SBSS) {
|
if(s->type != SBSS && !s->dupok) {
|
||||||
diag("%s: redefinition: %s in %s",
|
diag("%s: redefinition: %s in %s",
|
||||||
pn, s->name, TNAME);
|
pn, s->name, TNAME);
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 0;
|
s->size = 0;
|
||||||
}
|
}
|
||||||
if(p->to.offset > s->value)
|
if(p->to.offset > s->size)
|
||||||
s->value = p->to.offset;
|
s->size = p->to.offset;
|
||||||
if(p->from.scale & DUPOK)
|
if(p->from.scale & DUPOK)
|
||||||
s->dupok = 1;
|
s->dupok = 1;
|
||||||
|
if(p->from.scale & RODATA)
|
||||||
|
s->type = SRODATA;
|
||||||
goto loop;
|
goto loop;
|
||||||
|
|
||||||
case ADYNT:
|
case ADYNT:
|
||||||
@ -791,7 +793,7 @@ loop:
|
|||||||
s = lookup(literal, 0);
|
s = lookup(literal, 0);
|
||||||
if(s->type == 0) {
|
if(s->type == 0) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 4;
|
s->size = 4;
|
||||||
t = prg();
|
t = prg();
|
||||||
t->as = ADATA;
|
t->as = ADATA;
|
||||||
t->line = p->line;
|
t->line = p->line;
|
||||||
@ -837,7 +839,7 @@ loop:
|
|||||||
s = lookup(literal, 0);
|
s = lookup(literal, 0);
|
||||||
if(s->type == 0) {
|
if(s->type == 0) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 8;
|
s->size = 8;
|
||||||
t = prg();
|
t = prg();
|
||||||
t->as = ADATA;
|
t->as = ADATA;
|
||||||
t->line = p->line;
|
t->line = p->line;
|
||||||
@ -967,7 +969,7 @@ doprof1(void)
|
|||||||
q->to.offset = n;
|
q->to.offset = n;
|
||||||
|
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = n*4;
|
s->size = n*4;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -56,13 +56,13 @@ dodata(void)
|
|||||||
s->value = dtype;
|
s->value = dtype;
|
||||||
if(s->type == SBSS)
|
if(s->type == SBSS)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
if(s->type != SDATA && s->type != SELFDATA)
|
if(s->type != SDATA && s->type != SELFDATA && s->type != SRODATA)
|
||||||
diag("initialize non-data (%d): %s\n%P",
|
diag("initialize non-data (%d): %s\n%P",
|
||||||
s->type, s->name, p);
|
s->type, s->name, p);
|
||||||
t = p->from.offset + p->width;
|
t = p->from.offset + p->width;
|
||||||
if(t > s->value)
|
if(t > s->size)
|
||||||
diag("initialize bounds (%lld): %s\n%P",
|
diag("initialize bounds (%lld): %s\n%P",
|
||||||
s->value, s->name, p);
|
s->size, s->name, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* allocate elf guys - must be segregated from real data */
|
/* allocate elf guys - must be segregated from real data */
|
||||||
@ -73,7 +73,7 @@ dodata(void)
|
|||||||
continue;
|
continue;
|
||||||
if(s->type != SELFDATA)
|
if(s->type != SELFDATA)
|
||||||
continue;
|
continue;
|
||||||
t = rnd(s->value, 8);
|
t = rnd(s->size, 8);
|
||||||
s->size = t;
|
s->size = t;
|
||||||
s->value = datsize;
|
s->value = datsize;
|
||||||
datsize += t;
|
datsize += t;
|
||||||
@ -88,13 +88,12 @@ dodata(void)
|
|||||||
if(s->type != SDATA)
|
if(s->type != SDATA)
|
||||||
if(s->type != SBSS)
|
if(s->type != SBSS)
|
||||||
continue;
|
continue;
|
||||||
t = s->value;
|
t = s->size;
|
||||||
if(t == 0 && s->name[0] != '.') {
|
if(t == 0 && s->name[0] != '.') {
|
||||||
diag("%s: no size", s->name);
|
diag("%s: no size", s->name);
|
||||||
t = 1;
|
t = 1;
|
||||||
}
|
}
|
||||||
t = rnd(t, 4);
|
t = rnd(t, 4);
|
||||||
s->value = t;
|
|
||||||
if(t > MINSIZ)
|
if(t > MINSIZ)
|
||||||
continue;
|
continue;
|
||||||
if(t >= 8)
|
if(t >= 8)
|
||||||
@ -115,10 +114,9 @@ dodata(void)
|
|||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
t = s->value;
|
t = s->size;
|
||||||
if(t >= 8)
|
if(t >= 8)
|
||||||
datsize = rnd(datsize, 8);
|
datsize = rnd(datsize, 8);
|
||||||
s->size = t;
|
|
||||||
s->value = datsize;
|
s->value = datsize;
|
||||||
datsize += t;
|
datsize += t;
|
||||||
}
|
}
|
||||||
@ -171,8 +169,7 @@ dobss(void)
|
|||||||
continue;
|
continue;
|
||||||
if(s->type != SBSS)
|
if(s->type != SBSS)
|
||||||
continue;
|
continue;
|
||||||
t = s->value;
|
t = s->size;
|
||||||
s->size = t;
|
|
||||||
if(t >= 8)
|
if(t >= 8)
|
||||||
bsssize = rnd(bsssize, 8);
|
bsssize = rnd(bsssize, 8);
|
||||||
s->value = bsssize + dynptrsize + datsize;
|
s->value = bsssize + dynptrsize + datsize;
|
||||||
@ -1164,10 +1161,10 @@ export(void)
|
|||||||
newdata(et, off, sizeof(int32), D_EXTERN);
|
newdata(et, off, sizeof(int32), D_EXTERN);
|
||||||
off += sizeof(int32);
|
off += sizeof(int32);
|
||||||
}
|
}
|
||||||
et->value = off;
|
et->size = off;
|
||||||
if(sv == 0)
|
if(sv == 0)
|
||||||
sv = 1;
|
sv = 1;
|
||||||
str->value = sv;
|
str->size = sv;
|
||||||
exports = ne;
|
exports = ne;
|
||||||
free(esyms);
|
free(esyms);
|
||||||
}
|
}
|
||||||
|
@ -39,9 +39,10 @@ void
|
|||||||
span(void)
|
span(void)
|
||||||
{
|
{
|
||||||
Prog *p, *q;
|
Prog *p, *q;
|
||||||
int32 v;
|
int32 i, v;
|
||||||
vlong c, idat;
|
vlong c, idat;
|
||||||
int m, n, again;
|
int m, n, again;
|
||||||
|
Sym *s;
|
||||||
|
|
||||||
xdefine("etext", STEXT, 0L);
|
xdefine("etext", STEXT, 0L);
|
||||||
idat = INITDAT;
|
idat = INITDAT;
|
||||||
@ -121,6 +122,22 @@ loop:
|
|||||||
textsize = c;
|
textsize = c;
|
||||||
goto loop;
|
goto loop;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* allocate read-only data to the text segment.
|
||||||
|
*/
|
||||||
|
c = rnd(c, 8);
|
||||||
|
for(i=0; i<NHASH; i++)
|
||||||
|
for(s = hash[i]; s != S; s = s->link) {
|
||||||
|
if(s->type != SRODATA)
|
||||||
|
continue;
|
||||||
|
v = s->size;
|
||||||
|
while(v & 7)
|
||||||
|
v++;
|
||||||
|
s->value = c;
|
||||||
|
c += v;
|
||||||
|
}
|
||||||
|
|
||||||
if(INITRND) {
|
if(INITRND) {
|
||||||
INITDAT = rnd(c, INITRND);
|
INITDAT = rnd(c, INITRND);
|
||||||
if(INITDAT != idat) {
|
if(INITDAT != idat) {
|
||||||
@ -128,6 +145,7 @@ loop:
|
|||||||
goto start;
|
goto start;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
xdefine("etext", STEXT, c);
|
xdefine("etext", STEXT, c);
|
||||||
if(debug['v'])
|
if(debug['v'])
|
||||||
Bprint(&bso, "etext = %llux\n", c);
|
Bprint(&bso, "etext = %llux\n", c);
|
||||||
@ -228,6 +246,7 @@ genasmsym(void (*put)(char*, int, vlong, vlong, int, Sym*))
|
|||||||
for(s=hash[h]; s!=S; s=s->link) {
|
for(s=hash[h]; s!=S; s=s->link) {
|
||||||
switch(s->type) {
|
switch(s->type) {
|
||||||
case SCONST:
|
case SCONST:
|
||||||
|
case SRODATA:
|
||||||
if(!s->reachable)
|
if(!s->reachable)
|
||||||
continue;
|
continue;
|
||||||
put(s->name, 'D', s->value, s->size, s->version, s->gotype);
|
put(s->name, 'D', s->value, s->size, s->version, s->gotype);
|
||||||
@ -809,6 +828,7 @@ vaddr(Adr *a)
|
|||||||
ckoff(s, v);
|
ckoff(s, v);
|
||||||
case STEXT:
|
case STEXT:
|
||||||
case SCONST:
|
case SCONST:
|
||||||
|
case SRODATA:
|
||||||
if(!s->reachable)
|
if(!s->reachable)
|
||||||
diag("unreachable symbol in vaddr - %s", s->name);
|
diag("unreachable symbol in vaddr - %s", s->name);
|
||||||
if((uvlong)s->value < (uvlong)INITTEXT)
|
if((uvlong)s->value < (uvlong)INITTEXT)
|
||||||
|
@ -149,6 +149,8 @@ ggloblnod(Node *nam, int32 width)
|
|||||||
p->to.sym = S;
|
p->to.sym = S;
|
||||||
p->to.type = D_CONST;
|
p->to.type = D_CONST;
|
||||||
p->to.offset = width;
|
p->to.offset = width;
|
||||||
|
if(nam->readonly)
|
||||||
|
p->from.scale = RODATA;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
@ -165,6 +167,7 @@ ggloblsym(Sym *s, int32 width, int dupok)
|
|||||||
p->to.offset = width;
|
p->to.offset = width;
|
||||||
if(dupok)
|
if(dupok)
|
||||||
p->from.scale = DUPOK;
|
p->from.scale = DUPOK;
|
||||||
|
p->from.scale |= RODATA;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
@ -47,13 +47,17 @@ Pconv(Fmt *fp)
|
|||||||
{
|
{
|
||||||
char str[STRINGSZ];
|
char str[STRINGSZ];
|
||||||
Prog *p;
|
Prog *p;
|
||||||
|
char scale[40];
|
||||||
|
|
||||||
p = va_arg(fp->args, Prog*);
|
p = va_arg(fp->args, Prog*);
|
||||||
sconsize = 8;
|
sconsize = 8;
|
||||||
|
scale[0] = '\0';
|
||||||
|
if(p->from.scale != 0 && (p->as == AGLOBL || p->as == ATEXT))
|
||||||
|
snprint(scale, sizeof scale, "%d,", p->from.scale);
|
||||||
switch(p->as) {
|
switch(p->as) {
|
||||||
default:
|
default:
|
||||||
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%D",
|
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%s%D",
|
||||||
p->loc, p->lineno, p->as, &p->from, &p->to);
|
p->loc, p->lineno, p->as, &p->from, scale, &p->to);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ADATA:
|
case ADATA:
|
||||||
@ -63,8 +67,8 @@ Pconv(Fmt *fp)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case ATEXT:
|
case ATEXT:
|
||||||
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%lD",
|
snprint(str, sizeof(str), "%.4ld (%L) %-7A %D,%s%lD",
|
||||||
p->loc, p->lineno, p->as, &p->from, &p->to);
|
p->loc, p->lineno, p->as, &p->from, scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
return fmtstrcpy(fp, str);
|
return fmtstrcpy(fp, str);
|
||||||
|
@ -33,6 +33,7 @@
|
|||||||
#define NOPROF (1<<0)
|
#define NOPROF (1<<0)
|
||||||
#define DUPOK (1<<1)
|
#define DUPOK (1<<1)
|
||||||
#define NOSPLIT (1<<2)
|
#define NOSPLIT (1<<2)
|
||||||
|
#define RODATA (1<<3)
|
||||||
|
|
||||||
enum as
|
enum as
|
||||||
{
|
{
|
||||||
|
@ -127,16 +127,16 @@ addstring(Sym *s, char *str)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
n = strlen(str)+1;
|
n = strlen(str)+1;
|
||||||
while(n > 0) {
|
while(n > 0) {
|
||||||
m = n;
|
m = n;
|
||||||
if(m > sizeof(p->to.scon))
|
if(m > sizeof(p->to.scon))
|
||||||
m = sizeof(p->to.scon);
|
m = sizeof(p->to.scon);
|
||||||
p = newdata(s, s->value, m, D_EXTERN);
|
p = newdata(s, s->size, m, D_EXTERN);
|
||||||
p->to.type = D_SCONST;
|
p->to.type = D_SCONST;
|
||||||
memmove(p->to.scon, str, m);
|
memmove(p->to.scon, str, m);
|
||||||
s->value += m;
|
s->size += m;
|
||||||
str += m;
|
str += m;
|
||||||
n -= m;
|
n -= m;
|
||||||
}
|
}
|
||||||
@ -152,9 +152,9 @@ adduintxx(Sym *s, uint64 v, int wid)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, wid, D_EXTERN);
|
p = newdata(s, s->size, wid, D_EXTERN);
|
||||||
s->value += wid;
|
s->size += wid;
|
||||||
p->to.type = D_CONST;
|
p->to.type = D_CONST;
|
||||||
p->to.offset = v;
|
p->to.offset = v;
|
||||||
return r;
|
return r;
|
||||||
@ -194,9 +194,9 @@ addaddr(Sym *s, Sym *t)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, Ptrsize, D_EXTERN);
|
p = newdata(s, s->size, Ptrsize, D_EXTERN);
|
||||||
s->value += Ptrsize;
|
s->size += Ptrsize;
|
||||||
p->to.type = D_ADDR;
|
p->to.type = D_ADDR;
|
||||||
p->to.index = D_EXTERN;
|
p->to.index = D_EXTERN;
|
||||||
p->to.offset = 0;
|
p->to.offset = 0;
|
||||||
@ -214,9 +214,9 @@ addsize(Sym *s, Sym *t)
|
|||||||
if(s->type == 0)
|
if(s->type == 0)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
r = s->value;
|
r = s->size;
|
||||||
p = newdata(s, s->value, Ptrsize, D_EXTERN);
|
p = newdata(s, s->size, Ptrsize, D_EXTERN);
|
||||||
s->value += Ptrsize;
|
s->size += Ptrsize;
|
||||||
p->to.type = D_SIZE;
|
p->to.type = D_SIZE;
|
||||||
p->to.index = D_EXTERN;
|
p->to.index = D_EXTERN;
|
||||||
p->to.offset = 0;
|
p->to.offset = 0;
|
||||||
@ -317,7 +317,7 @@ doelf(void)
|
|||||||
s = lookup(".dynsym", 0);
|
s = lookup(".dynsym", 0);
|
||||||
s->type = SELFDATA;
|
s->type = SELFDATA;
|
||||||
s->reachable = 1;
|
s->reachable = 1;
|
||||||
s->value += ELF32SYMSIZE;
|
s->size += ELF32SYMSIZE;
|
||||||
|
|
||||||
/* dynamic string table */
|
/* dynamic string table */
|
||||||
s = lookup(".dynstr", 0);
|
s = lookup(".dynstr", 0);
|
||||||
@ -455,7 +455,7 @@ asmb(void)
|
|||||||
Prog *p;
|
Prog *p;
|
||||||
int32 v, magic;
|
int32 v, magic;
|
||||||
int a, dynsym;
|
int a, dynsym;
|
||||||
uint32 va, fo, w, symo, startva, machlink;
|
uint32 va, fo, w, symo, startva, machlink, etext;
|
||||||
uchar *op1;
|
uchar *op1;
|
||||||
ulong expectpc;
|
ulong expectpc;
|
||||||
ElfEhdr *eh;
|
ElfEhdr *eh;
|
||||||
@ -530,6 +530,15 @@ asmb(void)
|
|||||||
}
|
}
|
||||||
cflush();
|
cflush();
|
||||||
|
|
||||||
|
/* output read-only data in text segment */
|
||||||
|
etext = INITTEXT + textsize;
|
||||||
|
for(v = pc; v < etext; v += sizeof(buf)-Dbufslop) {
|
||||||
|
if(etext-v > sizeof(buf)-Dbufslop)
|
||||||
|
datblk(v, sizeof(buf)-Dbufslop, 1);
|
||||||
|
else
|
||||||
|
datblk(v, etext-v, 1);
|
||||||
|
}
|
||||||
|
|
||||||
switch(HEADTYPE) {
|
switch(HEADTYPE) {
|
||||||
default:
|
default:
|
||||||
if(iself)
|
if(iself)
|
||||||
@ -587,9 +596,9 @@ asmb(void)
|
|||||||
|
|
||||||
for(v = 0; v < datsize; v += sizeof(buf)-Dbufslop) {
|
for(v = 0; v < datsize; v += sizeof(buf)-Dbufslop) {
|
||||||
if(datsize-v > sizeof(buf)-Dbufslop)
|
if(datsize-v > sizeof(buf)-Dbufslop)
|
||||||
datblk(v, sizeof(buf)-Dbufslop);
|
datblk(v, sizeof(buf)-Dbufslop, 0);
|
||||||
else
|
else
|
||||||
datblk(v, datsize-v);
|
datblk(v, datsize-v, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
machlink = 0;
|
machlink = 0;
|
||||||
@ -1135,17 +1144,24 @@ cpos(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
datblk(int32 s, int32 n)
|
datblk(int32 s, int32 n, int32 rodata)
|
||||||
{
|
{
|
||||||
Prog *p;
|
Prog *p;
|
||||||
char *cast;
|
char *cast;
|
||||||
int32 l, fl, j;
|
int32 l, fl, j;
|
||||||
int i, c;
|
int i, c;
|
||||||
Adr *a;
|
Adr *a;
|
||||||
|
int32 base;
|
||||||
|
|
||||||
|
base = INITDAT;
|
||||||
|
if(rodata)
|
||||||
|
base = 0;
|
||||||
|
|
||||||
memset(buf.dbuf, 0, n+Dbufslop);
|
memset(buf.dbuf, 0, n+Dbufslop);
|
||||||
for(p = datap; p != P; p = p->link) {
|
for(p = datap; p != P; p = p->link) {
|
||||||
a = &p->from;
|
a = &p->from;
|
||||||
|
if(rodata != (a->sym->type == SRODATA))
|
||||||
|
continue;
|
||||||
|
|
||||||
l = a->sym->value + a->offset - s;
|
l = a->sym->value + a->offset - s;
|
||||||
if(l >= n)
|
if(l >= n)
|
||||||
@ -1214,7 +1230,7 @@ datblk(int32 s, int32 n)
|
|||||||
if(p->to.sym->type == SUNDEF)
|
if(p->to.sym->type == SUNDEF)
|
||||||
ckoff(p->to.sym, fl);
|
ckoff(p->to.sym, fl);
|
||||||
fl += p->to.sym->value;
|
fl += p->to.sym->value;
|
||||||
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF)
|
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF && p->to.sym->type != SRODATA)
|
||||||
fl += INITDAT;
|
fl += INITDAT;
|
||||||
if(dlm)
|
if(dlm)
|
||||||
dynreloc(p->to.sym, l+s+INITDAT, 1);
|
dynreloc(p->to.sym, l+s+INITDAT, 1);
|
||||||
@ -1257,6 +1273,8 @@ datblk(int32 s, int32 n)
|
|||||||
*/
|
*/
|
||||||
for(p = datap; p != P; p = p->link) {
|
for(p = datap; p != P; p = p->link) {
|
||||||
a = &p->from;
|
a = &p->from;
|
||||||
|
if(rodata != (a->sym->type == SRODATA))
|
||||||
|
continue;
|
||||||
|
|
||||||
l = a->sym->value + a->offset - s;
|
l = a->sym->value + a->offset - s;
|
||||||
if(l < 0 || l >= n)
|
if(l < 0 || l >= n)
|
||||||
@ -1272,26 +1290,26 @@ datblk(int32 s, int32 n)
|
|||||||
case 4:
|
case 4:
|
||||||
fl = ieeedtof(&p->to.ieee);
|
fl = ieeedtof(&p->to.ieee);
|
||||||
cast = (char*)&fl;
|
cast = (char*)&fl;
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", cast[fnuxi4[j]] & 0xff);
|
Bprint(&bso, "%.2ux", cast[fnuxi4[j]] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
case 8:
|
case 8:
|
||||||
cast = (char*)&p->to.ieee;
|
cast = (char*)&p->to.ieee;
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", cast[fnuxi8[j]] & 0xff);
|
Bprint(&bso, "%.2ux", cast[fnuxi8[j]] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_SCONST:
|
case D_SCONST:
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", p->to.scon[j] & 0xff);
|
Bprint(&bso, "%.2ux", p->to.scon[j] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
@ -1305,34 +1323,34 @@ datblk(int32 s, int32 n)
|
|||||||
if(p->to.sym->type == SUNDEF)
|
if(p->to.sym->type == SUNDEF)
|
||||||
ckoff(p->to.sym, fl);
|
ckoff(p->to.sym, fl);
|
||||||
fl += p->to.sym->value;
|
fl += p->to.sym->value;
|
||||||
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF)
|
if(p->to.sym->type != STEXT && p->to.sym->type != SUNDEF && p->to.sym->type != SRODATA)
|
||||||
fl += INITDAT;
|
fl += INITDAT;
|
||||||
if(dlm)
|
if(dlm)
|
||||||
dynreloc(p->to.sym, l+s+INITDAT, 1);
|
dynreloc(p->to.sym, l+s+base, 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cast = (char*)&fl;
|
cast = (char*)&fl;
|
||||||
switch(c) {
|
switch(c) {
|
||||||
default:
|
default:
|
||||||
diag("bad nuxi %d %d\n%P", c, i, curp);
|
diag("bad nuxi %d %d\n%P", c, i, p);
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", cast[inuxi1[j]] & 0xff);
|
Bprint(&bso, "%.2ux", cast[inuxi1[j]] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", cast[inuxi2[j]] & 0xff);
|
Bprint(&bso, "%.2ux", cast[inuxi2[j]] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
case 4:
|
case 4:
|
||||||
Bprint(&bso, pcstr, l+s+INITDAT);
|
Bprint(&bso, pcstr, l+s+base);
|
||||||
for(j=0; j<c; j++)
|
for(j=0; j<c; j++)
|
||||||
Bprint(&bso, "%.2ux", cast[inuxi4[j]] & 0xff);
|
Bprint(&bso, "%.2ux", cast[inuxi4[j]] & 0xff);
|
||||||
Bprint(&bso, "\t%P\n", curp);
|
Bprint(&bso, "\t%P\n", p);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -163,6 +163,7 @@ enum
|
|||||||
|
|
||||||
SFIXED,
|
SFIXED,
|
||||||
SELFDATA,
|
SELFDATA,
|
||||||
|
SRODATA,
|
||||||
|
|
||||||
NHASH = 10007,
|
NHASH = 10007,
|
||||||
NHUNK = 100000,
|
NHUNK = 100000,
|
||||||
@ -347,7 +348,7 @@ void ckoff(Sym*, int32);
|
|||||||
Prog* copyp(Prog*);
|
Prog* copyp(Prog*);
|
||||||
vlong cpos(void);
|
vlong cpos(void);
|
||||||
double cputime(void);
|
double cputime(void);
|
||||||
void datblk(int32, int32);
|
void datblk(int32, int32, int32);
|
||||||
void diag(char*, ...);
|
void diag(char*, ...);
|
||||||
void dodata(void);
|
void dodata(void);
|
||||||
void doelf(void);
|
void doelf(void);
|
||||||
|
@ -47,7 +47,6 @@ static Prog *bigP;
|
|||||||
int
|
int
|
||||||
Pconv(Fmt *fp)
|
Pconv(Fmt *fp)
|
||||||
{
|
{
|
||||||
char str[STRINGSZ];
|
|
||||||
Prog *p;
|
Prog *p;
|
||||||
|
|
||||||
p = va_arg(fp->args, Prog*);
|
p = va_arg(fp->args, Prog*);
|
||||||
@ -55,23 +54,23 @@ Pconv(Fmt *fp)
|
|||||||
switch(p->as) {
|
switch(p->as) {
|
||||||
case ATEXT:
|
case ATEXT:
|
||||||
if(p->from.scale) {
|
if(p->from.scale) {
|
||||||
sprint(str, "(%d) %A %D,%d,%D",
|
fmtprint(fp, "(%d) %A %D,%d,%D",
|
||||||
p->line, p->as, &p->from, p->from.scale, &p->to);
|
p->line, p->as, &p->from, p->from.scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
sprint(str, "(%d) %A %D,%D",
|
fmtprint(fp, "(%d) %A %D,%D",
|
||||||
p->line, p->as, &p->from, &p->to);
|
p->line, p->as, &p->from, &p->to);
|
||||||
break;
|
break;
|
||||||
case ADATA:
|
case ADATA:
|
||||||
case AINIT:
|
case AINIT:
|
||||||
case ADYNT:
|
case ADYNT:
|
||||||
sprint(str, "(%d) %A %D/%d,%D",
|
fmtprint(fp, "(%d) %A %D/%d,%D",
|
||||||
p->line, p->as, &p->from, p->from.scale, &p->to);
|
p->line, p->as, &p->from, p->from.scale, &p->to);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
bigP = P;
|
bigP = P;
|
||||||
return fmtstrcpy(fp, str);
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
@ -102,15 +101,15 @@ Dconv(Fmt *fp)
|
|||||||
i = a->type;
|
i = a->type;
|
||||||
if(i >= D_INDIR && i < 2*D_INDIR) {
|
if(i >= D_INDIR && i < 2*D_INDIR) {
|
||||||
if(a->offset)
|
if(a->offset)
|
||||||
sprint(str, "%ld(%R)", (long)a->offset, i-D_INDIR);
|
snprint(str, sizeof str, "%ld(%R)", (long)a->offset, i-D_INDIR);
|
||||||
else
|
else
|
||||||
sprint(str, "(%R)", i-D_INDIR);
|
snprint(str, sizeof str, "(%R)", i-D_INDIR);
|
||||||
goto brk;
|
goto brk;
|
||||||
}
|
}
|
||||||
switch(i) {
|
switch(i) {
|
||||||
|
|
||||||
default:
|
default:
|
||||||
sprint(str, "%R", i);
|
snprint(str, sizeof str, "%R", i);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_NONE:
|
case D_NONE:
|
||||||
@ -120,54 +119,54 @@ Dconv(Fmt *fp)
|
|||||||
case D_BRANCH:
|
case D_BRANCH:
|
||||||
if(bigP != P && bigP->pcond != P)
|
if(bigP != P && bigP->pcond != P)
|
||||||
if(a->sym != S)
|
if(a->sym != S)
|
||||||
sprint(str, "%lux+%s", bigP->pcond->pc,
|
snprint(str, sizeof str, "%lux+%s", bigP->pcond->pc,
|
||||||
a->sym->name);
|
a->sym->name);
|
||||||
else
|
else
|
||||||
sprint(str, "%lux", bigP->pcond->pc);
|
snprint(str, sizeof str, "%lux", bigP->pcond->pc);
|
||||||
else
|
else
|
||||||
sprint(str, "%ld(PC)", a->offset);
|
snprint(str, sizeof str, "%ld(PC)", a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_EXTERN:
|
case D_EXTERN:
|
||||||
sprint(str, "%s+%ld(SB)", xsymname(a->sym), a->offset);
|
snprint(str, sizeof str, "%s+%ld(SB)", xsymname(a->sym), a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_STATIC:
|
case D_STATIC:
|
||||||
sprint(str, "%s<%d>+%ld(SB)", xsymname(a->sym),
|
snprint(str, sizeof str, "%s<%d>+%ld(SB)", xsymname(a->sym),
|
||||||
a->sym->version, a->offset);
|
a->sym->version, a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_AUTO:
|
case D_AUTO:
|
||||||
sprint(str, "%s+%ld(SP)", xsymname(a->sym), a->offset);
|
snprint(str, sizeof str, "%s+%ld(SP)", xsymname(a->sym), a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_PARAM:
|
case D_PARAM:
|
||||||
if(a->sym)
|
if(a->sym)
|
||||||
sprint(str, "%s+%ld(FP)", a->sym->name, a->offset);
|
snprint(str, sizeof str, "%s+%ld(FP)", a->sym->name, a->offset);
|
||||||
else
|
else
|
||||||
sprint(str, "%ld(FP)", a->offset);
|
snprint(str, sizeof str, "%ld(FP)", a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_CONST:
|
case D_CONST:
|
||||||
sprint(str, "$%ld", a->offset);
|
snprint(str, sizeof str, "$%ld", a->offset);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_CONST2:
|
case D_CONST2:
|
||||||
sprint(str, "$%ld-%ld", a->offset, a->offset2);
|
snprint(str, sizeof str, "$%ld-%ld", a->offset, a->offset2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_FCONST:
|
case D_FCONST:
|
||||||
sprint(str, "$(%.8lux,%.8lux)", a->ieee.h, a->ieee.l);
|
snprint(str, sizeof str, "$(%.8lux,%.8lux)", a->ieee.h, a->ieee.l);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_SCONST:
|
case D_SCONST:
|
||||||
sprint(str, "$\"%S\"", a->scon);
|
snprint(str, sizeof str, "$\"%S\"", a->scon);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case D_ADDR:
|
case D_ADDR:
|
||||||
a->type = a->index;
|
a->type = a->index;
|
||||||
a->index = D_NONE;
|
a->index = D_NONE;
|
||||||
sprint(str, "$%D", a);
|
snprint(str, sizeof str, "$%D", a);
|
||||||
a->index = a->type;
|
a->index = a->type;
|
||||||
a->type = D_ADDR;
|
a->type = D_ADDR;
|
||||||
goto conv;
|
goto conv;
|
||||||
|
@ -432,7 +432,7 @@ zsym(char *pn, Biobuf *f, Sym *h[])
|
|||||||
void
|
void
|
||||||
zaddr(char *pn, Biobuf *f, Adr *a, Sym *h[])
|
zaddr(char *pn, Biobuf *f, Adr *a, Sym *h[])
|
||||||
{
|
{
|
||||||
int o, t;
|
int t;
|
||||||
int32 l;
|
int32 l;
|
||||||
Sym *s;
|
Sym *s;
|
||||||
Auto *u;
|
Auto *u;
|
||||||
@ -652,18 +652,20 @@ loop:
|
|||||||
s = p->from.sym;
|
s = p->from.sym;
|
||||||
if(s->type == 0 || s->type == SXREF) {
|
if(s->type == 0 || s->type == SXREF) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 0;
|
s->size = 0;
|
||||||
}
|
}
|
||||||
if(s->type != SBSS) {
|
if(s->type != SBSS && !s->dupok) {
|
||||||
diag("%s: redefinition: %s in %s",
|
diag("%s: redefinition: %s in %s",
|
||||||
pn, s->name, TNAME);
|
pn, s->name, TNAME);
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 0;
|
s->size = 0;
|
||||||
}
|
}
|
||||||
if(p->to.offset > s->value)
|
if(p->to.offset > s->size)
|
||||||
s->value = p->to.offset;
|
s->size = p->to.offset;
|
||||||
if(p->from.scale & DUPOK)
|
if(p->from.scale & DUPOK)
|
||||||
s->dupok = 1;
|
s->dupok = 1;
|
||||||
|
if(p->from.scale & RODATA)
|
||||||
|
s->type = SRODATA;
|
||||||
goto loop;
|
goto loop;
|
||||||
|
|
||||||
case ADYNT:
|
case ADYNT:
|
||||||
@ -788,7 +790,7 @@ loop:
|
|||||||
s = lookup(literal, 0);
|
s = lookup(literal, 0);
|
||||||
if(s->type == 0) {
|
if(s->type == 0) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 4;
|
s->size = 4;
|
||||||
t = prg();
|
t = prg();
|
||||||
t->as = ADATA;
|
t->as = ADATA;
|
||||||
t->line = p->line;
|
t->line = p->line;
|
||||||
@ -827,7 +829,7 @@ loop:
|
|||||||
s = lookup(literal, 0);
|
s = lookup(literal, 0);
|
||||||
if(s->type == 0) {
|
if(s->type == 0) {
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = 8;
|
s->size = 8;
|
||||||
t = prg();
|
t = prg();
|
||||||
t->as = ADATA;
|
t->as = ADATA;
|
||||||
t->line = p->line;
|
t->line = p->line;
|
||||||
@ -955,7 +957,7 @@ doprof1(void)
|
|||||||
q->to.offset = n;
|
q->to.offset = n;
|
||||||
|
|
||||||
s->type = SBSS;
|
s->type = SBSS;
|
||||||
s->value = n*4;
|
s->size = n*4;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -55,13 +55,13 @@ dodata(void)
|
|||||||
s->value = dtype;
|
s->value = dtype;
|
||||||
if(s->type == SBSS)
|
if(s->type == SBSS)
|
||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
if(s->type != SDATA && s->type != SELFDATA)
|
if(s->type != SDATA && s->type != SELFDATA && s->type != SRODATA)
|
||||||
diag("initialize non-data (%d): %s\n%P",
|
diag("initialize non-data (%d): %s\n%P",
|
||||||
s->type, s->name, p);
|
s->type, s->name, p);
|
||||||
t = p->from.offset + p->width;
|
t = p->from.offset + p->width;
|
||||||
if(t > s->value)
|
if(t > s->size)
|
||||||
diag("initialize bounds (%ld): %s\n%P",
|
diag("initialize bounds (%ld): %s\n%P",
|
||||||
s->value, s->name, p);
|
s->size, s->name, p);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* allocate elf guys - must be segregated from real data */
|
/* allocate elf guys - must be segregated from real data */
|
||||||
@ -72,7 +72,7 @@ dodata(void)
|
|||||||
continue;
|
continue;
|
||||||
if(s->type != SELFDATA)
|
if(s->type != SELFDATA)
|
||||||
continue;
|
continue;
|
||||||
t = rnd(s->value, 4);
|
t = rnd(s->size, 4);
|
||||||
s->size = t;
|
s->size = t;
|
||||||
s->value = datsize;
|
s->value = datsize;
|
||||||
datsize += t;
|
datsize += t;
|
||||||
@ -87,14 +87,13 @@ dodata(void)
|
|||||||
if(s->type != SDATA)
|
if(s->type != SDATA)
|
||||||
if(s->type != SBSS)
|
if(s->type != SBSS)
|
||||||
continue;
|
continue;
|
||||||
t = s->value;
|
t = s->size;
|
||||||
if(t == 0 && s->name[0] != '.') {
|
if(t == 0 && s->name[0] != '.') {
|
||||||
diag("%s: no size", s->name);
|
diag("%s: no size", s->name);
|
||||||
t = 1;
|
t = 1;
|
||||||
}
|
}
|
||||||
t = rnd(t, 4);
|
t = rnd(t, 4);
|
||||||
s->size = t;
|
s->size = t;
|
||||||
s->value = t;
|
|
||||||
if(t > MINSIZ)
|
if(t > MINSIZ)
|
||||||
continue;
|
continue;
|
||||||
s->value = datsize;
|
s->value = datsize;
|
||||||
@ -110,8 +109,7 @@ dodata(void)
|
|||||||
s->type = SDATA;
|
s->type = SDATA;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
t = s->value;
|
t = s->size;
|
||||||
s->size = t;
|
|
||||||
s->value = datsize;
|
s->value = datsize;
|
||||||
datsize += t;
|
datsize += t;
|
||||||
}
|
}
|
||||||
@ -154,8 +152,7 @@ dodata(void)
|
|||||||
continue;
|
continue;
|
||||||
if(s->type != SBSS)
|
if(s->type != SBSS)
|
||||||
continue;
|
continue;
|
||||||
t = s->value;
|
t = s->size;
|
||||||
s->size = t;
|
|
||||||
s->value = bsssize + dynptrsize + datsize;
|
s->value = bsssize + dynptrsize + datsize;
|
||||||
bsssize += t;
|
bsssize += t;
|
||||||
}
|
}
|
||||||
@ -1042,10 +1039,10 @@ export(void)
|
|||||||
newdata(et, off, sizeof(int32), D_EXTERN);
|
newdata(et, off, sizeof(int32), D_EXTERN);
|
||||||
off += sizeof(int32);
|
off += sizeof(int32);
|
||||||
}
|
}
|
||||||
et->value = off;
|
et->size = off;
|
||||||
if(sv == 0)
|
if(sv == 0)
|
||||||
sv = 1;
|
sv = 1;
|
||||||
str->value = sv;
|
str->size = sv;
|
||||||
exports = ne;
|
exports = ne;
|
||||||
free(esyms);
|
free(esyms);
|
||||||
}
|
}
|
||||||
|
@ -35,8 +35,9 @@ void
|
|||||||
span(void)
|
span(void)
|
||||||
{
|
{
|
||||||
Prog *p, *q;
|
Prog *p, *q;
|
||||||
int32 v, c, idat;
|
int32 i, v, c, idat;
|
||||||
int m, n, again;
|
int m, n, again;
|
||||||
|
Sym *s;
|
||||||
|
|
||||||
xdefine("etext", STEXT, 0L);
|
xdefine("etext", STEXT, 0L);
|
||||||
idat = INITDAT;
|
idat = INITDAT;
|
||||||
@ -107,6 +108,21 @@ start:
|
|||||||
n++;
|
n++;
|
||||||
}while(again);
|
}while(again);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* allocate read-only data to the text segment.
|
||||||
|
*/
|
||||||
|
c = rnd(c, 8);
|
||||||
|
for(i=0; i<NHASH; i++)
|
||||||
|
for(s = hash[i]; s != S; s = s->link) {
|
||||||
|
if(s->type != SRODATA)
|
||||||
|
continue;
|
||||||
|
v = s->size;
|
||||||
|
while(v & 3)
|
||||||
|
v++;
|
||||||
|
s->value = c;
|
||||||
|
c += v;
|
||||||
|
}
|
||||||
|
|
||||||
if(INITRND) {
|
if(INITRND) {
|
||||||
INITDAT = rnd(c+textpad, INITRND);
|
INITDAT = rnd(c+textpad, INITRND);
|
||||||
if(INITDAT != idat) {
|
if(INITDAT != idat) {
|
||||||
@ -114,6 +130,7 @@ start:
|
|||||||
goto start;
|
goto start;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
xdefine("etext", STEXT, c);
|
xdefine("etext", STEXT, c);
|
||||||
if(debug['v'])
|
if(debug['v'])
|
||||||
Bprint(&bso, "etext = %lux\n", c);
|
Bprint(&bso, "etext = %lux\n", c);
|
||||||
@ -208,6 +225,7 @@ asmsym(void)
|
|||||||
for(s=hash[h]; s!=S; s=s->link)
|
for(s=hash[h]; s!=S; s=s->link)
|
||||||
switch(s->type) {
|
switch(s->type) {
|
||||||
case SCONST:
|
case SCONST:
|
||||||
|
case SRODATA:
|
||||||
if(!s->reachable)
|
if(!s->reachable)
|
||||||
continue;
|
continue;
|
||||||
putsymb(s->name, 'D', s->value, s->version, s->gotype);
|
putsymb(s->name, 'D', s->value, s->version, s->gotype);
|
||||||
@ -618,6 +636,7 @@ vaddr(Adr *a)
|
|||||||
ckoff(s, v);
|
ckoff(s, v);
|
||||||
case STEXT:
|
case STEXT:
|
||||||
case SCONST:
|
case SCONST:
|
||||||
|
case SRODATA:
|
||||||
if(!s->reachable)
|
if(!s->reachable)
|
||||||
sysfatal("unreachable symbol in vaddr - %s", s->name);
|
sysfatal("unreachable symbol in vaddr - %s", s->name);
|
||||||
v += s->value;
|
v += s->value;
|
||||||
|
@ -211,6 +211,7 @@ struct Node
|
|||||||
uchar used;
|
uchar used;
|
||||||
uchar isddd;
|
uchar isddd;
|
||||||
uchar pun; // dont registerize variable ONAME
|
uchar pun; // dont registerize variable ONAME
|
||||||
|
uchar readonly;
|
||||||
|
|
||||||
// most nodes
|
// most nodes
|
||||||
Node* left;
|
Node* left;
|
||||||
|
@ -2600,6 +2600,7 @@ staticname(Type *t)
|
|||||||
snprint(namebuf, sizeof(namebuf), "statictmp_%.4d", statuniqgen);
|
snprint(namebuf, sizeof(namebuf), "statictmp_%.4d", statuniqgen);
|
||||||
statuniqgen++;
|
statuniqgen++;
|
||||||
n = newname(lookup(namebuf));
|
n = newname(lookup(namebuf));
|
||||||
|
// n->readonly = 1;
|
||||||
addvar(n, t, PEXTERN);
|
addvar(n, t, PEXTERN);
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
@ -495,6 +495,7 @@ lookup(char *symb, int v)
|
|||||||
s->version = v;
|
s->version = v;
|
||||||
s->value = 0;
|
s->value = 0;
|
||||||
s->sig = 0;
|
s->sig = 0;
|
||||||
|
s->size = 0;
|
||||||
hash[h] = s;
|
hash[h] = s;
|
||||||
nsymbol++;
|
nsymbol++;
|
||||||
return s;
|
return s;
|
||||||
|
@ -533,7 +533,7 @@ asmbmacho(vlong symdatva, vlong symo)
|
|||||||
ml->data[0] = 4; /* thread type */
|
ml->data[0] = 4; /* thread type */
|
||||||
ml->data[1] = 42; /* word count */
|
ml->data[1] = 42; /* word count */
|
||||||
ml->data[2+32] = entryvalue(); /* start pc */
|
ml->data[2+32] = entryvalue(); /* start pc */
|
||||||
ml->data[2+32+1] = entryvalue()>>32;
|
ml->data[2+32+1] = entryvalue()>>16>>16; // hide >>32 for 8l
|
||||||
break;
|
break;
|
||||||
case '8':
|
case '8':
|
||||||
ml = newMachoLoad(5, 16+2); /* unix thread */
|
ml = newMachoLoad(5, 16+2); /* unix thread */
|
||||||
|
Loading…
Reference in New Issue
Block a user