From f60cb1f8de690854a3895d6190117dd0ff5f4feb Mon Sep 17 00:00:00 2001 From: Andreas Gampe Date: Wed, 27 May 2015 18:31:42 -0700 Subject: [PATCH] ART: Add Mips o32 callee-save registers to SaveAll frame The floating point registers f20-f31 are callee-save in the Mips ABI. While the managed code does not touch them, they need to be saved when throwing an exception, so that they will be correctly restored and not smashed. Bug: 21266656 (cherry picked from commit a4e0e67611f54180694e0807d6599c1132269b6c) Change-Id: Ia96d52ce7fb41bf604da1797ce4d7a703e292415 --- runtime/arch/mips/asm_support_mips.h | 2 +- runtime/arch/mips/quick_entrypoints_mips.S | 58 ++++++++++++++---------- runtime/arch/mips/quick_method_frame_info_mips.h | 11 ++++- 3 files changed, 44 insertions(+), 27 deletions(-) diff --git a/runtime/arch/mips/asm_support_mips.h b/runtime/arch/mips/asm_support_mips.h index 02c098216..390c60637 100644 --- a/runtime/arch/mips/asm_support_mips.h +++ b/runtime/arch/mips/asm_support_mips.h @@ -19,7 +19,7 @@ #include "asm_support.h" -#define FRAME_SIZE_SAVE_ALL_CALLEE_SAVE 48 +#define FRAME_SIZE_SAVE_ALL_CALLEE_SAVE 96 #define FRAME_SIZE_REFS_ONLY_CALLEE_SAVE 48 #define FRAME_SIZE_REFS_AND_ARGS_CALLEE_SAVE 64 diff --git a/runtime/arch/mips/quick_entrypoints_mips.S b/runtime/arch/mips/quick_entrypoints_mips.S index ee5c59f96..f3d227455 100644 --- a/runtime/arch/mips/quick_entrypoints_mips.S +++ b/runtime/arch/mips/quick_entrypoints_mips.S @@ -37,36 +37,44 @@ * Reserves FRAME_SIZE_SAVE_ALL_CALLEE_SAVE + ARG_SLOT_SIZE bytes on the stack */ .macro SETUP_SAVE_ALL_CALLEE_SAVE_FRAME - addiu $sp, $sp, -48 - .cfi_adjust_cfa_offset 48 + addiu $sp, $sp, -96 + .cfi_adjust_cfa_offset 96 // Ugly compile-time check, but we only have the preprocessor. -#if (FRAME_SIZE_SAVE_ALL_CALLEE_SAVE != 48) +#if (FRAME_SIZE_SAVE_ALL_CALLEE_SAVE != 96) #error "SAVE_ALL_CALLEE_SAVE_FRAME(MIPS) size not as expected." #endif - sw $ra, 44($sp) - .cfi_rel_offset 31, 44 - sw $s8, 40($sp) - .cfi_rel_offset 30, 40 - sw $gp, 36($sp) - .cfi_rel_offset 28, 36 - sw $s7, 32($sp) - .cfi_rel_offset 23, 32 - sw $s6, 28($sp) - .cfi_rel_offset 22, 28 - sw $s5, 24($sp) - .cfi_rel_offset 21, 24 - sw $s4, 20($sp) - .cfi_rel_offset 20, 20 - sw $s3, 16($sp) - .cfi_rel_offset 19, 16 - sw $s2, 12($sp) - .cfi_rel_offset 18, 12 - sw $s1, 8($sp) - .cfi_rel_offset 17, 8 - sw $s0, 4($sp) - .cfi_rel_offset 16, 4 + sw $ra, 92($sp) + .cfi_rel_offset 31, 92 + sw $s8, 88($sp) + .cfi_rel_offset 30, 88 + sw $gp, 84($sp) + .cfi_rel_offset 28, 84 + sw $s7, 80($sp) + .cfi_rel_offset 23, 80 + sw $s6, 76($sp) + .cfi_rel_offset 22, 76 + sw $s5, 72($sp) + .cfi_rel_offset 21, 72 + sw $s4, 68($sp) + .cfi_rel_offset 20, 68 + sw $s3, 64($sp) + .cfi_rel_offset 19, 64 + sw $s2, 60($sp) + .cfi_rel_offset 18, 60 + sw $s1, 56($sp) + .cfi_rel_offset 17, 56 + sw $s0, 52($sp) + .cfi_rel_offset 16, 52 + + SDu $f30, $f31, 44, $sp, $t1 + SDu $f28, $f29, 36, $sp, $t1 + SDu $f26, $f27, 28, $sp, $t1 + SDu $f24, $f25, 20, $sp, $t1 + SDu $f22, $f23, 12, $sp, $t1 + SDu $f20, $f21, 4, $sp, $t1 + # 1 word for holding Method* lw $t0, %got(_ZN3art7Runtime9instance_E)($gp) diff --git a/runtime/arch/mips/quick_method_frame_info_mips.h b/runtime/arch/mips/quick_method_frame_info_mips.h index 5fbffbcac..e61e4ee4c 100644 --- a/runtime/arch/mips/quick_method_frame_info_mips.h +++ b/runtime/arch/mips/quick_method_frame_info_mips.h @@ -31,6 +31,10 @@ static constexpr uint32_t kMipsCalleeSaveArgSpills = (1 << art::mips::A1) | (1 << art::mips::A2) | (1 << art::mips::A3); static constexpr uint32_t kMipsCalleeSaveAllSpills = (1 << art::mips::S0) | (1 << art::mips::S1); +static constexpr uint32_t kMipsCalleeSaveAllFPSpills = + (1 << art::mips::F20) | (1 << art::mips::F21) | (1 << art::mips::F22) | (1 << art::mips::F23) | + (1 << art::mips::F24) | (1 << art::mips::F25) | (1 << art::mips::F26) | (1 << art::mips::F27) | + (1 << art::mips::F28) | (1 << art::mips::F29) | (1 << art::mips::F30) | (1 << art::mips::F31); constexpr uint32_t MipsCalleeSaveCoreSpills(Runtime::CalleeSaveType type) { return kMipsCalleeSaveRefSpills | @@ -38,15 +42,20 @@ constexpr uint32_t MipsCalleeSaveCoreSpills(Runtime::CalleeSaveType type) { (type == Runtime::kSaveAll ? kMipsCalleeSaveAllSpills : 0) | (1 << art::mips::RA); } +constexpr uint32_t MipsCalleeSaveFPSpills(Runtime::CalleeSaveType type) { + return type == Runtime::kSaveAll ? kMipsCalleeSaveAllFPSpills : 0; +} + constexpr uint32_t MipsCalleeSaveFrameSize(Runtime::CalleeSaveType type) { return RoundUp((POPCOUNT(MipsCalleeSaveCoreSpills(type)) /* gprs */ + + POPCOUNT(MipsCalleeSaveFPSpills(type)) /* fprs */ + 1 /* Method* */) * kMipsPointerSize, kStackAlignment); } constexpr QuickMethodFrameInfo MipsCalleeSaveMethodFrameInfo(Runtime::CalleeSaveType type) { return QuickMethodFrameInfo(MipsCalleeSaveFrameSize(type), MipsCalleeSaveCoreSpills(type), - 0u); + MipsCalleeSaveFPSpills(type)); } } // namespace mips -- 2.11.0