• Keith Randall's avatar
    [dev.ssa] cmd/compile: fix PIC for SSA-generated code · 2cbdd55d
    Keith Randall authored
    Access to globals requires a 2-instruction sequence on PIC 386.
    
        MOVL foo(SB), AX
    
    is translated by the obj package into:
    
        CALL getPCofNextInstructionInTempRegister(SB)
        MOVL (&foo-&thisInstruction)(tmpReg), AX
    
    The call returns the PC of the next instruction in a register.
    The next instruction then offsets from that register to get the
    address required.  The tricky part is the allocation of the
    temp register.  The legacy compiler always used CX, and forbid
    the register allocator from allocating CX when in PIC mode.
    We can't easily do that in SSA because CX is actually a required
    register for shift instructions. (I think the old backend got away
    with this because the register allocator never uses CX, only
    codegen knows that shifts must use CX.)
    
    Instead, we allow the temp register to be anything.  When the
    destination of the MOV (or LEA) is an integer register, we can
    use that register.  Otherwise, we make sure to compile the
    operation using an LEA to reference the global.  So
    
        MOVL AX, foo(SB)
    
    is never generated directly.  Instead, SSA generates:
    
        LEAL foo(SB), DX
        MOVL AX, (DX)
    
    which is then rewritten by the obj package to:
    
        CALL getPcInDX(SB)
        LEAL (&foo-&thisInstruction)(DX), AX
        MOVL AX, (DX)
    
    So this CL modifies the obj package to use different thunks
    to materialize the pc into different registers.  We use the
    registers that regalloc chose so that SSA can still allocate
    the full set of registers.
    
    Change-Id: Ie095644f7164a026c62e95baf9d18a8bcaed0bba
    Reviewed-on: https://go-review.googlesource.com/25442
    Run-TryBot: Keith Randall <khr@golang.org>
    TryBot-Result: Gobot Gobot <gobot@golang.org>
    Reviewed-by: 's avatarDavid Chase <drchase@google.com>
    2cbdd55d
Name
Last commit
Last update
..
archive Loading commit data...
bufio Loading commit data...
builtin Loading commit data...
bytes Loading commit data...
cmd Loading commit data...
compress Loading commit data...
container Loading commit data...
context Loading commit data...
crypto Loading commit data...
database/sql Loading commit data...
debug Loading commit data...
encoding Loading commit data...
errors Loading commit data...
expvar Loading commit data...
flag Loading commit data...
fmt Loading commit data...
go Loading commit data...
hash Loading commit data...
html Loading commit data...
image Loading commit data...
index/suffixarray Loading commit data...
internal Loading commit data...
io Loading commit data...
log Loading commit data...
math Loading commit data...
mime Loading commit data...
net Loading commit data...
os Loading commit data...
path Loading commit data...
reflect Loading commit data...
regexp Loading commit data...
runtime Loading commit data...
sort Loading commit data...
strconv Loading commit data...
strings Loading commit data...
sync Loading commit data...
syscall Loading commit data...
testing Loading commit data...
text Loading commit data...
time Loading commit data...
unicode Loading commit data...
unsafe Loading commit data...
vendor/golang_org/x/net Loading commit data...
Make.dist Loading commit data...
all.bash Loading commit data...
all.bat Loading commit data...
all.rc Loading commit data...
androidtest.bash Loading commit data...
bootstrap.bash Loading commit data...
buildall.bash Loading commit data...
clean.bash Loading commit data...
clean.bat Loading commit data...
clean.rc Loading commit data...
cmp.bash Loading commit data...
iostest.bash Loading commit data...
make.bash Loading commit data...
make.bat Loading commit data...
make.rc Loading commit data...
naclmake.bash Loading commit data...
nacltest.bash Loading commit data...
race.bash Loading commit data...
race.bat Loading commit data...
run.bash Loading commit data...
run.bat Loading commit data...
run.rc Loading commit data...