mirror of
https://github.com/golang/go
synced 2024-11-21 15:44:44 -07:00
5l: data-relocatable code layout
R=ken2 CC=golang-dev https://golang.org/cl/2479043
This commit is contained in:
parent
a647f59c1f
commit
3d0a85785a
@ -291,13 +291,11 @@ phsh(Elf64_Phdr *ph, Elf64_Shdr *sh)
|
||||
void
|
||||
asmb(void)
|
||||
{
|
||||
Prog *p;
|
||||
int32 t;
|
||||
int a, dynsym;
|
||||
uint32 va, fo, w, symo, startva;
|
||||
uint32 symdatva = SYMDATVA;
|
||||
int strtabsize;
|
||||
Optab *o;
|
||||
ElfEhdr *eh;
|
||||
ElfPhdr *ph, *pph;
|
||||
ElfShdr *sh;
|
||||
@ -312,28 +310,8 @@ asmb(void)
|
||||
OFFSET = HEADR;
|
||||
seek(cout, OFFSET, 0);
|
||||
pc = INITTEXT;
|
||||
for(cursym = textp; cursym != nil; cursym = cursym->next) {
|
||||
for(p = cursym->text; p != P; p = p->link) {
|
||||
setarch(p);
|
||||
if(p->as == ATEXT)
|
||||
autosize = p->to.offset + 4;
|
||||
if(p->pc != pc) {
|
||||
diag("phase error %ux sb %ux",
|
||||
p->pc, pc);
|
||||
if(!debug['a'])
|
||||
prasm(curp);
|
||||
pc = p->pc;
|
||||
}
|
||||
curp = p;
|
||||
o = oplook(p); /* could probably avoid this call */
|
||||
if(thumb)
|
||||
thumbasmout(p, o);
|
||||
else
|
||||
asmout(p, o);
|
||||
pc += o->size;
|
||||
}
|
||||
}
|
||||
cflush();
|
||||
codeblk(pc, segtext.sect->len);
|
||||
pc += segtext.sect->len;
|
||||
if(seek(cout, 0, 1) != pc - segtext.vaddr + segtext.fileoff)
|
||||
diag("text phase error");
|
||||
|
||||
@ -846,10 +824,11 @@ asmthumbmap(void)
|
||||
}
|
||||
|
||||
void
|
||||
asmout(Prog *p, Optab *o)
|
||||
asmout(Prog *p, Optab *o, int32 *out)
|
||||
{
|
||||
int32 o1, o2, o3, o4, o5, o6, v;
|
||||
int r, rf, rt, rt2;
|
||||
Reloc *rel;
|
||||
|
||||
PP = p;
|
||||
o1 = 0;
|
||||
@ -991,6 +970,15 @@ if(debug['G']) print("%ux: %s: arm %d %d %d %d\n", (uint32)(p->pc), p->from.sym-
|
||||
case 11: /* word */
|
||||
aclass(&p->to);
|
||||
o1 = instoffset;
|
||||
if(p->to.sym != S) {
|
||||
rel = addrel(cursym);
|
||||
rel->off = pc - cursym->value;
|
||||
rel->siz = 4;
|
||||
rel->type = D_ADDR;
|
||||
rel->sym = p->to.sym;
|
||||
rel->add = p->to.offset;
|
||||
o1 = 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case 12: /* movw $lcon, reg */
|
||||
@ -1588,6 +1576,14 @@ if(debug['G']) print("%ux: %s: arm %d %d %d %d\n", (uint32)(p->pc), p->from.sym-
|
||||
o1 |= (p->scond & C_SCOND) << 28;
|
||||
break;
|
||||
}
|
||||
|
||||
out[0] = o1;
|
||||
out[1] = o2;
|
||||
out[2] = o3;
|
||||
out[3] = o4;
|
||||
out[4] = o5;
|
||||
out[5] = o6;
|
||||
return;
|
||||
|
||||
v = p->pc;
|
||||
switch(o->size) {
|
||||
|
@ -379,7 +379,7 @@ void addhist(int32, int);
|
||||
Prog* appendp(Prog*);
|
||||
void asmb(void);
|
||||
void asmthumbmap(void);
|
||||
void asmout(Prog*, Optab*);
|
||||
void asmout(Prog*, Optab*, int32*);
|
||||
void thumbasmout(Prog*, Optab*);
|
||||
void asmsym(void);
|
||||
int32 atolwhex(char*);
|
||||
|
@ -70,7 +70,7 @@ main(int argc, char *argv[])
|
||||
{
|
||||
int c, i;
|
||||
|
||||
debug['s'] = 1;
|
||||
//debug['s'] = 1; // qemu cannot handle symdat load
|
||||
Binit(&bso, 1, OWRITE);
|
||||
cout = -1;
|
||||
listinit();
|
||||
|
@ -166,11 +166,12 @@ span(void)
|
||||
{
|
||||
Prog *p, *op;
|
||||
Optab *o;
|
||||
int m, bflag;
|
||||
int32 c, otxt;
|
||||
int m, bflag, i, v;
|
||||
int32 c, otxt, out[6];
|
||||
int lastthumb = -1;
|
||||
Section *rosect, *sect;
|
||||
Sym *sym;
|
||||
uchar *bp;
|
||||
|
||||
if(debug['v'])
|
||||
Bprint(&bso, "%5.2f span\n", cputime());
|
||||
@ -187,11 +188,8 @@ span(void)
|
||||
p = cursym->text;
|
||||
setarch(p);
|
||||
p->pc = c;
|
||||
cursym->value = c;
|
||||
|
||||
if(blitrl && lastthumb != -1 && lastthumb != thumb){ // flush literal pool
|
||||
if(flushpool(op, 0, 1))
|
||||
c = p->pc = scan(op, p, c);
|
||||
}
|
||||
lastthumb = thumb;
|
||||
autosize = p->to.offset + 4;
|
||||
if(p->from.sym != S)
|
||||
@ -216,8 +214,6 @@ span(void)
|
||||
c = p->pc = scan(op, p, c);
|
||||
}
|
||||
if(m == 0) {
|
||||
if(p->as == ATEXT) {
|
||||
}
|
||||
diag("zero-width instruction\n%P", p);
|
||||
continue;
|
||||
}
|
||||
@ -237,12 +233,13 @@ span(void)
|
||||
flushpool(p, 0, 0);
|
||||
c += m;
|
||||
}
|
||||
if(blitrl && cursym->next == nil){
|
||||
if(blitrl){
|
||||
if(thumb && isbranch(op))
|
||||
pool.extra += brextra(op);
|
||||
if(checkpool(op, 0))
|
||||
c = scan(op, P, c);
|
||||
}
|
||||
cursym->size = c - cursym->value;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -257,6 +254,7 @@ span(void)
|
||||
bflag = 0;
|
||||
c = INITTEXT;
|
||||
for(cursym = textp; cursym != nil; cursym = cursym->next) {
|
||||
cursym->value = c;
|
||||
for(p = cursym->text; p != P; p = p->link) {
|
||||
setarch(p);
|
||||
p->pc = c;
|
||||
@ -299,6 +297,7 @@ span(void)
|
||||
}
|
||||
c += m;
|
||||
}
|
||||
cursym->size = c - cursym->value;
|
||||
}
|
||||
}
|
||||
|
||||
@ -318,6 +317,7 @@ span(void)
|
||||
oop = op = nil;
|
||||
again = 0;
|
||||
for(cursym = textp; cursym != nil; cursym = cursym->next) {
|
||||
cursym->value = c;
|
||||
for(p = cursym->text; p != P; oop = op, op = p, p = p->link) {
|
||||
setarch(p);
|
||||
if(p->pc != c)
|
||||
@ -361,6 +361,7 @@ span(void)
|
||||
}
|
||||
c += m;
|
||||
}
|
||||
cursym->size = c - cursym->value;
|
||||
}
|
||||
if(c != lastc || again){
|
||||
lastc = c;
|
||||
@ -368,12 +369,39 @@ span(void)
|
||||
}
|
||||
}
|
||||
c = rnd(c, 8);
|
||||
|
||||
xdefine("etext", STEXT, c);
|
||||
for(cursym = textp; cursym != nil; cursym = cursym->next)
|
||||
cursym->value = cursym->text->pc;
|
||||
textsize = c - INITTEXT;
|
||||
|
||||
/*
|
||||
* lay out the code. all the pc-relative code references,
|
||||
* even cross-function, are resolved now;
|
||||
* only data references need to be relocated.
|
||||
* with more work we could leave cross-function
|
||||
* code references to be relocated too, and then
|
||||
* perhaps we'd be able to parallelize the span loop above.
|
||||
*/
|
||||
for(cursym = textp; cursym != nil; cursym = cursym->next) {
|
||||
p = cursym->text;
|
||||
setarch(p);
|
||||
autosize = p->to.offset + 4;
|
||||
symgrow(cursym, cursym->size);
|
||||
|
||||
bp = cursym->p;
|
||||
for(p = p->link; p != P; p = p->link) {
|
||||
pc = p->pc;
|
||||
curp = p;
|
||||
o = oplook(p);
|
||||
asmout(p, o, out);
|
||||
for(i=0; i<o->size/4; i++) {
|
||||
v = out[i];
|
||||
*bp++ = v;
|
||||
*bp++ = v>>8;
|
||||
*bp++ = v>>16;
|
||||
*bp++ = v>>24;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
rosect = segtext.sect->next;
|
||||
if(rosect) {
|
||||
if(INITRND)
|
||||
|
Loading…
Reference in New Issue
Block a user