1// Copyright 2015 The Chromium Authors 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#if defined(__x86_64__) || defined(__aarch64__) 6 7// base::apple::CallWithEHFrame(void () block_pointer) 8#define CALL_WITH_EH_FRAME __ZN4base5apple15CallWithEHFrameEU13block_pointerFvvE 9 10 .section __TEXT,__text,regular,pure_instructions 11#if !defined(COMPONENT_BUILD) 12 .private_extern CALL_WITH_EH_FRAME 13#endif 14 .globl CALL_WITH_EH_FRAME 15 .p2align 2 16CALL_WITH_EH_FRAME: 17 18 .cfi_startproc 19 20 // Configure the C++ exception handler personality routine. Normally the 21 // compiler would emit ___gxx_personality_v0 here. The purpose of this 22 // function is to use a custom personality routine. 23 .cfi_personality 155, __ZN4base5apple21CxxPersonalityRoutineEi14_Unwind_ActionyP17_Unwind_ExceptionP15_Unwind_Context 24 .cfi_lsda 16, CallWithEHFrame_exception_table 25 26#if defined(__x86_64__) 27Lfunction_start: 28 pushq %rbp 29 .cfi_def_cfa_offset 16 30 .cfi_offset %rbp, -16 31 movq %rsp, %rbp 32 .cfi_def_cfa_register %rbp 33 34 // Load the function pointer from the block descriptor. 35 movq 16(%rdi), %rax 36 37 // Execute the block in the context of a C++ try{}. 38Ltry_start: 39 callq *%rax 40Ltry_end: 41 popq %rbp 42 ret 43 44 // Landing pad for the exception handler. This should never be called, since 45 // the personality routine will stop the search for an exception handler, 46 // which will cause the runtime to invoke the default terminate handler. 47Lcatch: 48 movq %rax, %rdi 49 callq ___cxa_begin_catch // The ABI requires a call to the catch handler. 50 ud2 // In the event this is called, make it fatal. 51 52#elif defined(__aarch64__) 53Lfunction_start: 54 stp x29, x30, [sp, #-16]! 55 mov x29, sp 56 .cfi_def_cfa w29, 16 57 .cfi_offset w30, -8 58 .cfi_offset w29, -16 59 60 // Load the function pointer from the block descriptor. 61 ldr x8, [x0, #16] 62 63 // Execute the block in the context of a C++ try{}. 64Ltry_start: 65 blr x8 66Ltry_end: 67 ldp x29, x30, [sp], #16 68 ret 69 70 // Landing pad for the exception handler. This should never be called, since 71 // the personality routine will stop the search for an exception handler, 72 // which will cause the runtime to invoke the default terminate handler. 73Lcatch: 74 bl ___cxa_begin_catch // The ABI requires a call to the catch handler. 75 brk #0x1 // In the event this is called, make it fatal. 76#endif 77 78Lfunction_end: 79 .cfi_endproc 80 81 // The C++ exception table that is used to identify this frame as an 82 // exception handler. See https://llvm.org/docs/ExceptionHandling.html, 83 // https://itanium-cxx-abi.github.io/cxx-abi/exceptions.pdf and 84 // https://www.airs.com/blog/archives/464. 85 .section __TEXT,__gcc_except_tab 86 .p2align 2 87CallWithEHFrame_exception_table: 88 .byte 255 // DW_EH_PE_omit 89 .byte 155 // DW_EH_PE_indirect | DW_EH_PE_pcrel | DW_EH_PE_sdata4 90 // The number of bytes in this table 91 .uleb128 Ltypes_table_base - Ltypes_table_ref_base 92 93Ltypes_table_ref_base: 94 .byte 1 // DW_EH_PE_uleb128 95 // Callsite table length. 96 .uleb128 Lcall_site_table_end - Lcall_site_table_start 97 98Lcall_site_table_start: 99// First callsite. 100CS1_begin = Ltry_start - Lfunction_start 101 .uleb128 CS1_begin 102CS1_end = Ltry_end - Ltry_start 103 .uleb128 CS1_end 104 105// First landing pad. 106LP1 = Lcatch - Lfunction_start 107 .uleb128 LP1 108 .uleb128 1 // Action record. 109 110// Second callsite. 111CS2_begin = Ltry_end - Lfunction_start 112 .uleb128 CS2_begin 113CS2_end = Lfunction_end - Ltry_end 114 .uleb128 CS2_end 115 116 // Second landing pad (none). 117 .uleb128 0 118 .uleb128 0 // No action. 119 120Lcall_site_table_end: 121 // Action table. 122 // Action record 1. 123 .uleb128 1 // Type filter -1. 124 .uleb128 0 // No further action to take. 125 126 // Types table. 127 .p2align 2 128 .long 0 // Type filter -1: no type filter for this catch(){} clause. 129 130Ltypes_table_base: 131 .p2align 2 132 133#endif // defined(__x86_64__) || defined(__aarch64__) 134