diff --git a/src/pal/inc/unixasmmacrosarm.inc b/src/pal/inc/unixasmmacrosarm.inc index 169a5a727fb6..1295967192be 100644 --- a/src/pal/inc/unixasmmacrosarm.inc +++ b/src/pal/inc/unixasmmacrosarm.inc @@ -152,9 +152,8 @@ C_FUNC(\Name\()_End): .endif PUSH_CALLEE_SAVED_REGISTERS - .setfp r7, sp, #(3 * 4) + PROLOG_STACK_SAVE_OFFSET r7, #12 // let r7 point the saved r7 in the stack (clang FP style) - add r7, sp, #(3 * 4) alloc_stack __PWTB_StackAlloc @@ -208,6 +207,11 @@ C_FUNC(\Name\()_End): mov \Register, sp .endm +.macro PROLOG_STACK_SAVE_OFFSET Register, Offset + .setfp \Register, sp, \Offset + add \Register, sp, \Offset +.endm + .macro EPILOG_STACK_FREE Size add sp, sp, \Size .endm @@ -216,6 +220,10 @@ C_FUNC(\Name\()_End): mov sp, \Register .endm +.macro EPILOG_STACK_RESTORE_OFFSET Register, Offset + sub sp, \Register, \Offset +.endm + .macro EPILOG_BRANCH Target b \Target .endm diff --git a/src/vm/arm/asmhelpers.S b/src/vm/arm/asmhelpers.S index 4f8a3d8de83a..715dce89512b 100644 --- a/src/vm/arm/asmhelpers.S +++ b/src/vm/arm/asmhelpers.S @@ -32,7 +32,7 @@ //void CallDescrWorkerInternal(CallDescrData * pCallDescrData)// NESTED_ENTRY CallDescrWorkerInternal,_TEXT,NoHandler PROLOG_PUSH "{r4,r5,r7,lr}" - PROLOG_STACK_SAVE r7 + PROLOG_STACK_SAVE_OFFSET r7, #8 mov r5,r0 // save pCallDescrData in r5 @@ -129,7 +129,7 @@ LOCAL_LABEL(LReturnDone): vldm sp, {d0-d3} #endif - EPILOG_STACK_RESTORE r7 + EPILOG_STACK_RESTORE_OFFSET r7, #8 EPILOG_POP "{r4,r5,r7,pc}" NESTED_END CallDescrWorkerInternal,_TEXT @@ -174,7 +174,7 @@ LOCAL_LABEL(LReturnDone): // Spill callee saved registers and return address. PROLOG_PUSH "{r4-r11,lr}" - PROLOG_STACK_SAVE r7 + PROLOG_STACK_SAVE_OFFSET r7, #12 // // This is the code that would have to run to setup this frame @@ -241,7 +241,7 @@ LOCAL_LABEL(GoodGSCookie): // // epilog // - EPILOG_STACK_RESTORE r7 + EPILOG_STACK_RESTORE_OFFSET r7, #12 EPILOG_POP "{r4-r11,lr}" bx lr @@ -287,7 +287,8 @@ LOCAL_LABEL(LNullThis): // NESTED_ENTRY TheUMEntryPrestub,_TEXT,NoHandler - push {r0-r4,lr} + PROLOG_PUSH "{r0-r4,r7,r8,lr}" // add r8 to make stack aligned by 8B + PROLOG_STACK_SAVE_OFFSET r7, #20 vpush {d0-d7} CHECK_STACK_ALIGNMENT @@ -300,7 +301,7 @@ LOCAL_LABEL(LNullThis): // Epilog vpop {d0-d7} - pop {r0-r4,lr} + pop {r0-r4,r7,r8,lr} bx r12 NESTED_END TheUMEntryPrestub,_TEXT @@ -311,7 +312,7 @@ LOCAL_LABEL(LNullThis): NESTED_ENTRY UMThunkStub,_TEXT,NoHandler PROLOG_PUSH "{r4,r5,r7,r11,lr}" push {r0-r3,r12} - PROLOG_STACK_SAVE r7 + PROLOG_STACK_SAVE_OFFSET r7, #28 //GBLA UMThunkStub_HiddenArg // offset of saved UMEntryThunk * //GBLA UMThunkStub_StackArgs // offset of original stack args (total size of UMThunkStub frame) @@ -374,7 +375,7 @@ LOCAL_LABEL(UMThunkStub_PostCall): mov r4, 0 str r4, [r5, #Thread__m_fPreemptiveGCDisabled] - EPILOG_STACK_RESTORE r7 + EPILOG_STACK_RESTORE_OFFSET r7, #28 free_stack 4 * 5 EPILOG_POP "{r4,r5,r7,r11,pc}" @@ -424,7 +425,7 @@ LOCAL_LABEL(UMThunkStub_WrongAppDomain): NESTED_ENTRY UM2MThunk_WrapperHelper, _TEXT, NoHandler PROLOG_PUSH "{r4-r7,r11,lr}" - PROLOG_STACK_SAVE r7 + PROLOG_STACK_SAVE_OFFSET r7, #12 CHECK_STACK_ALIGNMENT @@ -480,7 +481,7 @@ LOCAL_LABEL(UM2MThunk_WrapperHelper_ArgumentsSetup): vldm sp, {d0-d3} #endif - EPILOG_STACK_RESTORE r7 + EPILOG_STACK_RESTORE_OFFSET r7, #12 EPILOG_POP "{r4-r7,r11,pc}" NESTED_END UM2MThunk_WrapperHelper, _TEXT @@ -516,7 +517,8 @@ ThePreStubPatchLabel: // The call in ndirect import precode points to this function. NESTED_ENTRY NDirectImportThunk, _TEXT, NoHandler - push {r0-r4,lr} // Spill general argument registers, return address and + PROLOG_PUSH "{r0-r4,r7,r8,lr}" // Spill general argument registers, return address and + PROLOG_STACK_SAVE_OFFSET r7, #20 // arbitrary register to keep stack aligned vpush {d0-d7} // Spill floating point argument registers @@ -527,7 +529,7 @@ ThePreStubPatchLabel: mov r12, r0 vpop {d0-d7} - pop {r0-r4,lr} + pop {r0-r4,r7,r8,lr} // If we got back from NDirectImportWorker, the MD has been successfully // linked. Proceed to execute the original DLL call. @@ -676,8 +678,8 @@ LOCAL_LABEL(Done): NESTED_ENTRY RedirectedHandledJITCaseFor\reason\()_Stub, _TEXT, NoHandler PROLOG_PUSH "{r7,lr}" // return address - alloc_stack 4 // stack slot to save the CONTEXT * PROLOG_STACK_SAVE r7 + alloc_stack 4 // stack slot to save the CONTEXT * //REDIRECTSTUB_SP_OFFSET_CONTEXT is defined in asmconstants.h //If CONTEXT is not saved at 0 offset from SP it must be changed as well. @@ -793,7 +795,8 @@ LOCAL_LABEL(stackProbe_loop): NESTED_ENTRY VirtualMethodFixupStub, _TEXT, NoHandler // Save arguments and return address - push {r0-r3, lr} + PROLOG_PUSH "{r0-r3, r7,r8, lr}" // keep increase by 8B for alignment + PROLOG_STACK_SAVE_OFFSET r7, #20 // Align stack alloc_stack SIZEOF__FloatArgumentRegisters + 4 @@ -820,7 +823,7 @@ LOCAL_LABEL(stackProbe_loop): // pop the stack and restore original register state vldm sp, {d0-d7} free_stack SIZEOF__FloatArgumentRegisters + 4 - pop {r0-r3, lr} + pop {r0-r3, r7,r8, lr} PATCH_LABEL VirtualMethodFixupPatchLabel @@ -906,7 +909,8 @@ LOCAL_LABEL(stackProbe_loop): // NESTED_ENTRY JIT_RareDisableHelper, _TEXT, NoHandler - PROLOG_PUSH "{r0-r1, r11, lr}" // save integer return value + PROLOG_PUSH "{r0-r1, r7,r8, r11, lr}" // save integer return value + PROLOG_STACK_SAVE_OFFSET r7, #8 vpush {d0-d3} // floating point return value CHECK_STACK_ALIGNMENT @@ -914,7 +918,7 @@ LOCAL_LABEL(stackProbe_loop): bl C_FUNC(JIT_RareDisableHelperWorker) vpop {d0-d3} - EPILOG_POP "{r0-r1, r11, pc}" + EPILOG_POP "{r0-r1, r7,r8, r11, pc}" NESTED_END JIT_RareDisableHelper, _TEXT diff --git a/src/vm/arm/ehhelpers.S b/src/vm/arm/ehhelpers.S index dfe1b11e0d31..c32a06b7ee6c 100644 --- a/src/vm/arm/ehhelpers.S +++ b/src/vm/arm/ehhelpers.S @@ -47,6 +47,8 @@ OFFSET_OF_FRAME=(4 + SIZEOF__GSCookie) // // Runtime check for 8-byte alignment. PROLOG_STACK_SAVE r7 + // We lose stack unwindability here by configuring fp(r7) incorrectely + // here. and r0, r7, #4 sub sp, sp, r0 @@ -99,6 +101,7 @@ OFFSET_OF_FRAME=(4 + SIZEOF__GSCookie) NESTED_ENTRY CallEHFunclet, _TEXT, NoHandler PROLOG_PUSH "{r4-r11, lr}" + PROLOG_STACK_SAVE_OFFSET r7, #12 alloc_stack 4 // On entry: @@ -124,7 +127,8 @@ OFFSET_OF_FRAME=(4 + SIZEOF__GSCookie) // frame pointer for accessing the locals in the parent method. NESTED_ENTRY CallEHFilterFunclet, _TEXT, NoHandler - PROLOG_PUSH "{lr}" + PROLOG_PUSH "{r7, lr}" + PROLOG_STACK_SAVE r7 alloc_stack 4 // On entry: @@ -140,6 +144,6 @@ OFFSET_OF_FRAME=(4 + SIZEOF__GSCookie) blx r2 free_stack 4 - EPILOG_POP "{pc}" + EPILOG_POP "{r7, pc}" NESTED_END CallEHFilterFunclet, _TEXT