зеркало из https://github.com/mozilla/gecko-dev.git
125 строки
4.6 KiB
ArmAsm
125 строки
4.6 KiB
ArmAsm
|
|
// Select C numeric constant
|
|
.radix C
|
|
.psr abi64
|
|
.psr lsb
|
|
// Section has executable code
|
|
.section .text, "ax","progbits"
|
|
// procedure named 'SharedStub'
|
|
.proc SharedStub
|
|
// manual bundling
|
|
.explicit
|
|
|
|
.global PrepareAndDispatch
|
|
// .exclass PrepareAndDispatch, @fullyvisible
|
|
.type PrepareAndDispatch,@function
|
|
|
|
SharedStub::
|
|
// 10 arguments, first 8 are the input arguments of previous
|
|
// function call. The 9th one is methodIndex and the 10th is the
|
|
// pointer to the remaining input arguments. The last two arguments
|
|
// are passed in memory.
|
|
.prologue
|
|
.save ar.pfs , r41
|
|
// allocate 8 input args, 4 local args, and 5 output args
|
|
alloc r41 = ar.pfs, 8, 4, 5, 0 // M
|
|
.save rp, r40
|
|
mov r40 = rp // I
|
|
add out4 = 24, sp ;; // I
|
|
|
|
.save ar.unat, r42
|
|
mov r42 = ar.unat // M
|
|
.fframe 144
|
|
add sp = -144, sp // A
|
|
// unwind table already knows gp, don't need to specify anything
|
|
add r43 = 0, gp ;; // A
|
|
|
|
// We have possible 8 integer registers and 8 float registers that could
|
|
// be arguments. We also have a stack region from the previous
|
|
// stack frame that may hold some stack arguments.
|
|
// We need to write the integer registers to a memory region, write
|
|
// the float registers to a memory region (making sure we don't step
|
|
// on NAT while touching the registers). We also mark the memory
|
|
// address of the stack arguments.
|
|
// We then call PrepareAndDispatch() specifying the three memory
|
|
// region pointers.
|
|
|
|
|
|
.body
|
|
add out0 = 0, in0 // A move self ptr
|
|
// 144 bytes = 16 byte stack header + 64 byte int space + 64 byte float space
|
|
// methodIndex is at 144 + 16 bytes away from current sp
|
|
// (current frame + previous frame header)
|
|
ld8 out4 = [out4] // M restarg address
|
|
add r11 = 160, sp ;; // A address of methodIndex
|
|
|
|
ld8 out1 = [r11] // M load methodIndex
|
|
// sp + 16 is the start of intargs
|
|
add out2 = 16, sp // A address of intargs
|
|
// the intargs take up 64 bytes, so sp + 16 + 64 is the start of floatargs
|
|
add out3 = 80, sp ;; // A address of floatargs
|
|
|
|
add r11 = 0, out2 ;; // A
|
|
st8.spill [r11] = in1, 8 // M
|
|
add r10 = 0, out3 ;; // A
|
|
|
|
st8.spill [r11] = in2, 8 ;; // M
|
|
st8.spill [r11] = in3, 8 // M
|
|
nop.i 0 ;; // I
|
|
|
|
st8.spill [r11] = in4, 8 ;; // M
|
|
st8.spill [r11] = in5, 8 // M
|
|
nop.i 0 ;; // I
|
|
|
|
st8.spill [r11] = in6, 8 ;; // M
|
|
st8.spill [r11] = in7 // M
|
|
fclass.nm p14,p15 = f8,@nat ;; // F
|
|
|
|
(p14) stfd [r10] = f8, 8 // M
|
|
(p15) add r10 = 8, r10 // A
|
|
fclass.nm p12,p13 = f9,@nat ;; // F
|
|
|
|
(p12) stfd [r10] = f9, 8 // M
|
|
(p13) add r10 = 8, r10 // A
|
|
fclass.nm p14,p15 =f10,@nat ;; // F
|
|
|
|
(p14) stfd [r10] = f10, 8 // M
|
|
(p15) add r10 = 8, r10 // A
|
|
fclass.nm p12,p13 =f11,@nat ;; // F
|
|
|
|
(p12) stfd [r10] = f11, 8 // M
|
|
(p13) add r10 = 8, r10 // A
|
|
fclass.nm p14,p15 =f12,@nat ;; // F
|
|
|
|
(p14) stfd [r10] = f12, 8 // M
|
|
(p15) add r10 = 8, r10 // A
|
|
fclass.nm p12,p13 =f13,@nat ;; // F
|
|
|
|
(p12) stfd [r10] = f13, 8 // M
|
|
(p13) add r10 = 8, r10 // A
|
|
fclass.nm p14,p15 =f14,@nat ;; // F
|
|
|
|
(p14) stfd [r10] = f14, 8 // M
|
|
(p15) add r10 = 8, r10 // A
|
|
fclass.nm p12,p13 =f15,@nat ;; // F
|
|
|
|
(p12) stfd [r10] = f15, 8 // M
|
|
(p13) add r10 = 8, r10 // A
|
|
|
|
// branch to PrepareAndDispatch
|
|
br.call.dptk.few rp = PrepareAndDispatch ;; // B
|
|
|
|
// epilog
|
|
mov ar.unat = r42 // M
|
|
mov ar.pfs = r41 // I
|
|
mov rp = r40 ;; // I
|
|
|
|
add gp = 0, r43 // A
|
|
add sp = 144, sp // A
|
|
br.ret.dptk.few rp ;; // B
|
|
|
|
.endp
|
|
|
|
/* Magic indicating no need for an executable stack */
|
|
.section .note.GNU-stack, "", @progbits ; .previous
|