this repo has no description
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Adding libunwind-darwin extracted from GCC

+7131 -4
+1 -1
CMakeLists.txt
··· 50 50 51 51 install(TARGETS dyld fatmacho-extract DESTINATION bin) 52 52 53 - add_subdirectory(src/libSystem) 53 + add_subdirectory(src/libSystem src/libunwind-darwin) 54 54
+16 -3
src/libSystem/CMakeLists.txt
··· 7 7 8 8 enable_language(ASM_NASM) 9 9 10 + if (NOT "${CMAKE_CXX_COMPILER} ${CMAKE_CXX_COMPILER_ARG1}" MATCHES ".*clang") 11 + message(FATAL_ERROR "Clang is the only supported compiler.") 12 + endif (NOT "${CMAKE_CXX_COMPILER} ${CMAKE_CXX_COMPILER_ARG1}" MATCHES ".*clang") 13 + 10 14 configure_file(config.h.in config.h) 11 - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fblocks") 12 - #set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fPIC") 15 + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fblocks -std=c++0x") 16 + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fblocks") 17 + 18 + #find_path(LIBCXX_INCLUDE_DIR c++/v1/vector) 19 + #if (DEFINED LIBCXX_INCLUDE_DIR) 20 + # message(STATUS "Found libcxx in ${LIBCXX_INCLUDE_DIR}") 21 + #else (DEFINED LIBCXX_INCLUDE_DIR) 22 + # message(FATAL_ERROR "libcxx not found") 23 + #endif (DEFINED LIBCXX_INCLUDE_DIR) 24 + 25 + #include_directories(${LIBCXX_INCLUDE_DIR}) 13 26 14 27 include_directories(${CMAKE_CURRENT_SOURCE_DIR}) 15 28 include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../util) ··· 60 73 61 74 add_library(System.dylib SHARED ${libc_SRCS} ${bsdkern_SRCS} ${machkern_SRCS}) 62 75 # -luuid to make uuid_ functions available for Darwin apps 63 - target_link_libraries(System.dylib -ldl -lpthread -luuid mach-o) 76 + target_link_libraries(System.dylib -ldl -lpthread -luuid -lmach-o) 64 77 65 78 install(TARGETS System.dylib DESTINATION lib) 66 79
+1
src/libSystem/config.h.in
··· 19 19 #include <stdint.h> 20 20 21 21 #define __uint64_t uint64_t 22 + #define __darwin_natural_t long
+20
src/libunwind-darwin/CMakeLists.txt
··· 1 + project(unwind-darwin) 2 + 3 + cmake_minimum_required(VERSION 2.4.0) 4 + if(COMMAND cmake_policy) 5 + cmake_policy(SET CMP0003 NEW) 6 + endif(COMMAND cmake_policy) 7 + 8 + set (unwind_SRCS 9 + emutls.c 10 + unwind-c.c 11 + unwind-compat.c 12 + unwind-dw2-fde-darwin.c 13 + unwind-dw2-fde-compat.c 14 + unwind-dw2.c 15 + unwind-sjlj.c 16 + ) 17 + 18 + add_library(unwind-darwin SHARED ${unwind_SRCS}) 19 + target_link_libraries(unwind-darwin -Tlink.cmd) 20 + install(TARGETS unwind-darwin DESTINATION lib)
+175
src/libunwind-darwin/coretypes.h
··· 1 + /* GCC core type declarations. 2 + Copyright (C) 2002, 2004, 2007, 2008, 2009, 2010 3 + Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it under 8 + the terms of the GNU General Public License as published by the Free 9 + Software Foundation; either version 3, or (at your option) any later 10 + version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT ANY 13 + WARRANTY; without even the implied warranty of MERCHANTABILITY or 14 + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 + for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + /* Provide forward declarations of core types which are referred to by 27 + most of the compiler. This allows header files to use these types 28 + (e.g. in function prototypes) without concern for whether the full 29 + definitions are visible. Some other declarations that need to be 30 + universally visible are here, too. 31 + 32 + In the context of tconfig.h, most of these have special definitions 33 + which prevent them from being used except in further type 34 + declarations. This is a kludge; the right thing is to avoid 35 + including the "tm.h" header set in the context of tconfig.h, but 36 + we're not there yet. */ 37 + 38 + #ifndef GCC_CORETYPES_H 39 + #define GCC_CORETYPES_H 40 + 41 + #ifndef GTY 42 + #define GTY(x) /* nothing - marker for gengtype */ 43 + #endif 44 + 45 + #ifndef USED_FOR_TARGET 46 + 47 + struct bitmap_head_def; 48 + typedef struct bitmap_head_def *bitmap; 49 + typedef const struct bitmap_head_def *const_bitmap; 50 + struct simple_bitmap_def; 51 + typedef struct simple_bitmap_def *sbitmap; 52 + typedef const struct simple_bitmap_def *const_sbitmap; 53 + struct rtx_def; 54 + typedef struct rtx_def *rtx; 55 + typedef const struct rtx_def *const_rtx; 56 + struct rtvec_def; 57 + typedef struct rtvec_def *rtvec; 58 + typedef const struct rtvec_def *const_rtvec; 59 + union tree_node; 60 + typedef union tree_node *tree; 61 + union gimple_statement_d; 62 + typedef union gimple_statement_d *gimple; 63 + typedef const union tree_node *const_tree; 64 + typedef const union gimple_statement_d *const_gimple; 65 + union section; 66 + typedef union section section; 67 + struct gcc_options; 68 + struct cl_target_option; 69 + struct cl_optimization; 70 + struct cl_option; 71 + struct cl_decoded_option; 72 + struct cl_option_handlers; 73 + struct diagnostic_context; 74 + typedef struct diagnostic_context diagnostic_context; 75 + struct gimple_seq_d; 76 + typedef struct gimple_seq_d *gimple_seq; 77 + typedef const struct gimple_seq_d *const_gimple_seq; 78 + 79 + /* Address space number for named address space support. */ 80 + typedef unsigned char addr_space_t; 81 + 82 + /* The value of addr_space_t that represents the generic address space. */ 83 + #define ADDR_SPACE_GENERIC 0 84 + #define ADDR_SPACE_GENERIC_P(AS) ((AS) == ADDR_SPACE_GENERIC) 85 + 86 + /* The major intermediate representations of GCC. */ 87 + enum ir_type { 88 + IR_GIMPLE, 89 + IR_RTL_CFGRTL, 90 + IR_RTL_CFGLAYOUT 91 + }; 92 + 93 + /* Provide forward struct declaration so that we don't have to include 94 + all of cpplib.h whenever a random prototype includes a pointer. 95 + Note that the cpp_reader and cpp_token typedefs remain part of 96 + cpplib.h. */ 97 + 98 + struct cpp_reader; 99 + struct cpp_token; 100 + 101 + /* The thread-local storage model associated with a given VAR_DECL 102 + or SYMBOL_REF. This isn't used much, but both trees and RTL refer 103 + to it, so it's here. */ 104 + enum tls_model { 105 + TLS_MODEL_NONE, 106 + TLS_MODEL_EMULATED, 107 + TLS_MODEL_REAL, 108 + TLS_MODEL_GLOBAL_DYNAMIC = TLS_MODEL_REAL, 109 + TLS_MODEL_LOCAL_DYNAMIC, 110 + TLS_MODEL_INITIAL_EXEC, 111 + TLS_MODEL_LOCAL_EXEC 112 + }; 113 + 114 + /* Types of unwind/exception handling info that can be generated. */ 115 + 116 + enum unwind_info_type 117 + { 118 + UI_NONE, 119 + UI_SJLJ, 120 + UI_DWARF2, 121 + UI_TARGET 122 + }; 123 + 124 + /* Callgraph node profile representation. */ 125 + enum node_frequency { 126 + /* This function most likely won't be executed at all. 127 + (set only when profile feedback is available or via function attribute). */ 128 + NODE_FREQUENCY_UNLIKELY_EXECUTED, 129 + /* For functions that are known to be executed once (i.e. constructors, destructors 130 + and main function. */ 131 + NODE_FREQUENCY_EXECUTED_ONCE, 132 + /* The default value. */ 133 + NODE_FREQUENCY_NORMAL, 134 + /* Optimize this function hard 135 + (set only when profile feedback is available or via function attribute). */ 136 + NODE_FREQUENCY_HOT 137 + }; 138 + 139 + 140 + struct edge_def; 141 + typedef struct edge_def *edge; 142 + typedef const struct edge_def *const_edge; 143 + struct basic_block_def; 144 + typedef struct basic_block_def *basic_block; 145 + typedef const struct basic_block_def *const_basic_block; 146 + 147 + #define obstack_chunk_alloc ((void *(*) (long)) xmalloc) 148 + #define obstack_chunk_free ((void (*) (void *)) free) 149 + #define OBSTACK_CHUNK_SIZE 0 150 + #define gcc_obstack_init(OBSTACK) \ 151 + _obstack_begin ((OBSTACK), OBSTACK_CHUNK_SIZE, 0, \ 152 + obstack_chunk_alloc, \ 153 + obstack_chunk_free) 154 + 155 + /* enum reg_class is target specific, so it should not appear in 156 + target-independent code or interfaces, like the target hook declarations 157 + in target.h. */ 158 + typedef int reg_class_t; 159 + 160 + #else 161 + 162 + struct _dont_use_rtx_here_; 163 + struct _dont_use_rtvec_here_; 164 + union _dont_use_tree_here_; 165 + #define rtx struct _dont_use_rtx_here_ * 166 + #define const_rtx struct _dont_use_rtx_here_ * 167 + #define rtvec struct _dont_use_rtvec_here * 168 + #define const_rtvec struct _dont_use_rtvec_here * 169 + #define tree union _dont_use_tree_here_ * 170 + #define const_tree union _dont_use_tree_here_ * 171 + 172 + #endif 173 + 174 + #endif /* coretypes.h */ 175 +
src/libunwind-darwin/defaults.h

This is a binary file and will not be displayed.

+869
src/libunwind-darwin/dwarf2.h
··· 1 + /* Declarations and definitions of codes relating to the DWARF2 and 2 + DWARF3 symbolic debugging information formats. 3 + Copyright (C) 1992, 1993, 1995, 1996, 1997, 1999, 2000, 2001, 2002, 4 + 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010 5 + Free Software Foundation, Inc. 6 + 7 + Written by Gary Funck (gary@intrepid.com) The Ada Joint Program 8 + Office (AJPO), Florida State University and Silicon Graphics Inc. 9 + provided support for this effort -- June 21, 1995. 10 + 11 + Derived from the DWARF 1 implementation written by Ron Guilmette 12 + (rfg@netcom.com), November 1990. 13 + 14 + This file is part of GCC. 15 + 16 + GCC is free software; you can redistribute it and/or modify it under 17 + the terms of the GNU General Public License as published by the Free 18 + Software Foundation; either version 3, or (at your option) any later 19 + version. 20 + 21 + GCC is distributed in the hope that it will be useful, but WITHOUT 22 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 23 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 24 + License for more details. 25 + 26 + Under Section 7 of GPL version 3, you are granted additional 27 + permissions described in the GCC Runtime Library Exception, version 28 + 3.1, as published by the Free Software Foundation. 29 + 30 + You should have received a copy of the GNU General Public License and 31 + a copy of the GCC Runtime Library Exception along with this program; 32 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 33 + <http://www.gnu.org/licenses/>. */ 34 + 35 + /* This file is derived from the DWARF specification (a public document) 36 + Revision 2.0.0 (July 27, 1993) developed by the UNIX International 37 + Programming Languages Special Interest Group (UI/PLSIG) and distributed 38 + by UNIX International. Copies of this specification are available from 39 + UNIX International, 20 Waterview Boulevard, Parsippany, NJ, 07054. 40 + 41 + This file also now contains definitions from the DWARF 3 specification 42 + published Dec 20, 2005, available from: http://dwarf.freestandards.org. */ 43 + 44 + /* This file is shared between GCC and GDB, and should not contain 45 + prototypes. */ 46 + 47 + #ifndef _DWARF2_H 48 + #define _DWARF2_H 49 + 50 + /* Tag names and codes. */ 51 + enum dwarf_tag 52 + { 53 + DW_TAG_padding = 0x00, 54 + DW_TAG_array_type = 0x01, 55 + DW_TAG_class_type = 0x02, 56 + DW_TAG_entry_point = 0x03, 57 + DW_TAG_enumeration_type = 0x04, 58 + DW_TAG_formal_parameter = 0x05, 59 + DW_TAG_imported_declaration = 0x08, 60 + DW_TAG_label = 0x0a, 61 + DW_TAG_lexical_block = 0x0b, 62 + DW_TAG_member = 0x0d, 63 + DW_TAG_pointer_type = 0x0f, 64 + DW_TAG_reference_type = 0x10, 65 + DW_TAG_compile_unit = 0x11, 66 + DW_TAG_string_type = 0x12, 67 + DW_TAG_structure_type = 0x13, 68 + DW_TAG_subroutine_type = 0x15, 69 + DW_TAG_typedef = 0x16, 70 + DW_TAG_union_type = 0x17, 71 + DW_TAG_unspecified_parameters = 0x18, 72 + DW_TAG_variant = 0x19, 73 + DW_TAG_common_block = 0x1a, 74 + DW_TAG_common_inclusion = 0x1b, 75 + DW_TAG_inheritance = 0x1c, 76 + DW_TAG_inlined_subroutine = 0x1d, 77 + DW_TAG_module = 0x1e, 78 + DW_TAG_ptr_to_member_type = 0x1f, 79 + DW_TAG_set_type = 0x20, 80 + DW_TAG_subrange_type = 0x21, 81 + DW_TAG_with_stmt = 0x22, 82 + DW_TAG_access_declaration = 0x23, 83 + DW_TAG_base_type = 0x24, 84 + DW_TAG_catch_block = 0x25, 85 + DW_TAG_const_type = 0x26, 86 + DW_TAG_constant = 0x27, 87 + DW_TAG_enumerator = 0x28, 88 + DW_TAG_file_type = 0x29, 89 + DW_TAG_friend = 0x2a, 90 + DW_TAG_namelist = 0x2b, 91 + DW_TAG_namelist_item = 0x2c, 92 + DW_TAG_packed_type = 0x2d, 93 + DW_TAG_subprogram = 0x2e, 94 + DW_TAG_template_type_param = 0x2f, 95 + DW_TAG_template_value_param = 0x30, 96 + DW_TAG_thrown_type = 0x31, 97 + DW_TAG_try_block = 0x32, 98 + DW_TAG_variant_part = 0x33, 99 + DW_TAG_variable = 0x34, 100 + DW_TAG_volatile_type = 0x35, 101 + /* DWARF 3. */ 102 + DW_TAG_dwarf_procedure = 0x36, 103 + DW_TAG_restrict_type = 0x37, 104 + DW_TAG_interface_type = 0x38, 105 + DW_TAG_namespace = 0x39, 106 + DW_TAG_imported_module = 0x3a, 107 + DW_TAG_unspecified_type = 0x3b, 108 + DW_TAG_partial_unit = 0x3c, 109 + DW_TAG_imported_unit = 0x3d, 110 + DW_TAG_condition = 0x3f, 111 + DW_TAG_shared_type = 0x40, 112 + /* DWARF 4. */ 113 + DW_TAG_type_unit = 0x41, 114 + DW_TAG_rvalue_reference_type = 0x42, 115 + DW_TAG_template_alias = 0x43, 116 + 117 + DW_TAG_lo_user = 0x4080, 118 + DW_TAG_hi_user = 0xffff, 119 + 120 + /* SGI/MIPS Extensions. */ 121 + DW_TAG_MIPS_loop = 0x4081, 122 + 123 + /* HP extensions. See: ftp://ftp.hp.com/pub/lang/tools/WDB/wdb-4.0.tar.gz . */ 124 + DW_TAG_HP_array_descriptor = 0x4090, 125 + DW_TAG_HP_Bliss_field = 0x4091, 126 + DW_TAG_HP_Bliss_field_set = 0x4092, 127 + 128 + /* GNU extensions. */ 129 + DW_TAG_format_label = 0x4101, /* For FORTRAN 77 and Fortran 90. */ 130 + DW_TAG_function_template = 0x4102, /* For C++. */ 131 + DW_TAG_class_template = 0x4103, /* For C++. */ 132 + DW_TAG_GNU_BINCL = 0x4104, 133 + DW_TAG_GNU_EINCL = 0x4105, 134 + /* Template template parameter. 135 + See http://gcc.gnu.org/wiki/TemplateParmsDwarf . */ 136 + DW_TAG_GNU_template_template_param = 0x4106, 137 + 138 + /* Template parameter pack extension, specified at 139 + http://wiki.dwarfstd.org/index.php?title=C%2B%2B0x:_Variadic_templates 140 + The values of these two TAGS are in the DW_TAG_GNU_* space until the tags 141 + are properly part of DWARF 5. */ 142 + DW_TAG_GNU_template_parameter_pack = 0x4107, 143 + DW_TAG_GNU_formal_parameter_pack = 0x4108, 144 + /* Extensions for UPC. See: http://upc.gwu.edu/~upc. */ 145 + DW_TAG_upc_shared_type = 0x8765, 146 + DW_TAG_upc_strict_type = 0x8766, 147 + DW_TAG_upc_relaxed_type = 0x8767, 148 + /* PGI (STMicroelectronics) extensions. No documentation available. */ 149 + DW_TAG_PGI_kanji_type = 0xA000, 150 + DW_TAG_PGI_interface_block = 0xA020 151 + }; 152 + 153 + /* Flag that tells whether entry has a child or not. */ 154 + #define DW_children_no 0 155 + #define DW_children_yes 1 156 + 157 + /* Form names and codes. */ 158 + enum dwarf_form 159 + { 160 + DW_FORM_addr = 0x01, 161 + DW_FORM_block2 = 0x03, 162 + DW_FORM_block4 = 0x04, 163 + DW_FORM_data2 = 0x05, 164 + DW_FORM_data4 = 0x06, 165 + DW_FORM_data8 = 0x07, 166 + DW_FORM_string = 0x08, 167 + DW_FORM_block = 0x09, 168 + DW_FORM_block1 = 0x0a, 169 + DW_FORM_data1 = 0x0b, 170 + DW_FORM_flag = 0x0c, 171 + DW_FORM_sdata = 0x0d, 172 + DW_FORM_strp = 0x0e, 173 + DW_FORM_udata = 0x0f, 174 + DW_FORM_ref_addr = 0x10, 175 + DW_FORM_ref1 = 0x11, 176 + DW_FORM_ref2 = 0x12, 177 + DW_FORM_ref4 = 0x13, 178 + DW_FORM_ref8 = 0x14, 179 + DW_FORM_ref_udata = 0x15, 180 + DW_FORM_indirect = 0x16, 181 + /* DWARF 4. */ 182 + DW_FORM_sec_offset = 0x17, 183 + DW_FORM_exprloc = 0x18, 184 + DW_FORM_flag_present = 0x19, 185 + DW_FORM_ref_sig8 = 0x20 186 + #define DW_FORM_sig8 DW_FORM_ref_sig8 /* Note: The use of DW_FORM_sig8 is deprecated. */ 187 + }; 188 + 189 + /* Attribute names and codes. */ 190 + enum dwarf_attribute 191 + { 192 + DW_AT_sibling = 0x01, 193 + DW_AT_location = 0x02, 194 + DW_AT_name = 0x03, 195 + DW_AT_ordering = 0x09, 196 + DW_AT_subscr_data = 0x0a, 197 + DW_AT_byte_size = 0x0b, 198 + DW_AT_bit_offset = 0x0c, 199 + DW_AT_bit_size = 0x0d, 200 + DW_AT_element_list = 0x0f, 201 + DW_AT_stmt_list = 0x10, 202 + DW_AT_low_pc = 0x11, 203 + DW_AT_high_pc = 0x12, 204 + DW_AT_language = 0x13, 205 + DW_AT_member = 0x14, 206 + DW_AT_discr = 0x15, 207 + DW_AT_discr_value = 0x16, 208 + DW_AT_visibility = 0x17, 209 + DW_AT_import = 0x18, 210 + DW_AT_string_length = 0x19, 211 + DW_AT_common_reference = 0x1a, 212 + DW_AT_comp_dir = 0x1b, 213 + DW_AT_const_value = 0x1c, 214 + DW_AT_containing_type = 0x1d, 215 + DW_AT_default_value = 0x1e, 216 + DW_AT_inline = 0x20, 217 + DW_AT_is_optional = 0x21, 218 + DW_AT_lower_bound = 0x22, 219 + DW_AT_producer = 0x25, 220 + DW_AT_prototyped = 0x27, 221 + DW_AT_return_addr = 0x2a, 222 + DW_AT_start_scope = 0x2c, 223 + DW_AT_bit_stride = 0x2e, 224 + #define DW_AT_stride_size DW_AT_bit_stride /* Note: The use of DW_AT_stride_size is deprecated. */ 225 + DW_AT_upper_bound = 0x2f, 226 + DW_AT_abstract_origin = 0x31, 227 + DW_AT_accessibility = 0x32, 228 + DW_AT_address_class = 0x33, 229 + DW_AT_artificial = 0x34, 230 + DW_AT_base_types = 0x35, 231 + DW_AT_calling_convention = 0x36, 232 + DW_AT_count = 0x37, 233 + DW_AT_data_member_location = 0x38, 234 + DW_AT_decl_column = 0x39, 235 + DW_AT_decl_file = 0x3a, 236 + DW_AT_decl_line = 0x3b, 237 + DW_AT_declaration = 0x3c, 238 + DW_AT_discr_list = 0x3d, 239 + DW_AT_encoding = 0x3e, 240 + DW_AT_external = 0x3f, 241 + DW_AT_frame_base = 0x40, 242 + DW_AT_friend = 0x41, 243 + DW_AT_identifier_case = 0x42, 244 + DW_AT_macro_info = 0x43, 245 + DW_AT_namelist_items = 0x44, 246 + DW_AT_priority = 0x45, 247 + DW_AT_segment = 0x46, 248 + DW_AT_specification = 0x47, 249 + DW_AT_static_link = 0x48, 250 + DW_AT_type = 0x49, 251 + DW_AT_use_location = 0x4a, 252 + DW_AT_variable_parameter = 0x4b, 253 + DW_AT_virtuality = 0x4c, 254 + DW_AT_vtable_elem_location = 0x4d, 255 + /* DWARF 3 values. */ 256 + DW_AT_allocated = 0x4e, 257 + DW_AT_associated = 0x4f, 258 + DW_AT_data_location = 0x50, 259 + DW_AT_byte_stride = 0x51, 260 + #define DW_AT_stride DW_AT_byte_stride /* Note: The use of DW_AT_stride is deprecated. */ 261 + DW_AT_entry_pc = 0x52, 262 + DW_AT_use_UTF8 = 0x53, 263 + DW_AT_extension = 0x54, 264 + DW_AT_ranges = 0x55, 265 + DW_AT_trampoline = 0x56, 266 + DW_AT_call_column = 0x57, 267 + DW_AT_call_file = 0x58, 268 + DW_AT_call_line = 0x59, 269 + DW_AT_description = 0x5a, 270 + DW_AT_binary_scale = 0x5b, 271 + DW_AT_decimal_scale = 0x5c, 272 + DW_AT_small = 0x5d, 273 + DW_AT_decimal_sign = 0x5e, 274 + DW_AT_digit_count = 0x5f, 275 + DW_AT_picture_string = 0x60, 276 + DW_AT_mutable = 0x61, 277 + DW_AT_threads_scaled = 0x62, 278 + DW_AT_explicit = 0x63, 279 + DW_AT_object_pointer = 0x64, 280 + DW_AT_endianity = 0x65, 281 + DW_AT_elemental = 0x66, 282 + DW_AT_pure = 0x67, 283 + DW_AT_recursive = 0x68, 284 + /* DWARF 4. */ 285 + DW_AT_signature = 0x69, 286 + DW_AT_main_subprogram = 0x6a, 287 + DW_AT_data_bit_offset = 0x6b, 288 + DW_AT_const_expr = 0x6c, 289 + DW_AT_enum_class = 0x6d, 290 + DW_AT_linkage_name = 0x6e, 291 + 292 + DW_AT_lo_user = 0x2000, /* Implementation-defined range start. */ 293 + DW_AT_hi_user = 0x3fff, /* Implementation-defined range end. */ 294 + 295 + /* SGI/MIPS extensions. */ 296 + DW_AT_MIPS_fde = 0x2001, 297 + DW_AT_MIPS_loop_begin = 0x2002, 298 + DW_AT_MIPS_tail_loop_begin = 0x2003, 299 + DW_AT_MIPS_epilog_begin = 0x2004, 300 + DW_AT_MIPS_loop_unroll_factor = 0x2005, 301 + DW_AT_MIPS_software_pipeline_depth = 0x2006, 302 + DW_AT_MIPS_linkage_name = 0x2007, 303 + DW_AT_MIPS_stride = 0x2008, 304 + DW_AT_MIPS_abstract_name = 0x2009, 305 + DW_AT_MIPS_clone_origin = 0x200a, 306 + DW_AT_MIPS_has_inlines = 0x200b, 307 + /* HP extensions. */ 308 + DW_AT_HP_block_index = 0x2000, 309 + DW_AT_HP_unmodifiable = 0x2001, /* Same as DW_AT_MIPS_fde. */ 310 + DW_AT_HP_prologue = 0x2005, /* Same as DW_AT_MIPS_loop_unroll. */ 311 + DW_AT_HP_epilogue = 0x2008, /* Same as DW_AT_MIPS_stride. */ 312 + DW_AT_HP_actuals_stmt_list = 0x2010, 313 + DW_AT_HP_proc_per_section = 0x2011, 314 + DW_AT_HP_raw_data_ptr = 0x2012, 315 + DW_AT_HP_pass_by_reference = 0x2013, 316 + DW_AT_HP_opt_level = 0x2014, 317 + DW_AT_HP_prof_version_id = 0x2015, 318 + DW_AT_HP_opt_flags = 0x2016, 319 + DW_AT_HP_cold_region_low_pc = 0x2017, 320 + DW_AT_HP_cold_region_high_pc = 0x2018, 321 + DW_AT_HP_all_variables_modifiable = 0x2019, 322 + DW_AT_HP_linkage_name = 0x201a, 323 + DW_AT_HP_prof_flags = 0x201b, /* In comp unit of procs_info for -g. */ 324 + DW_AT_HP_unit_name = 0x201f, 325 + DW_AT_HP_unit_size = 0x2020, 326 + DW_AT_HP_widened_byte_size = 0x2021, 327 + DW_AT_HP_definition_points = 0x2022, 328 + DW_AT_HP_default_location = 0x2023, 329 + DW_AT_HP_is_result_param = 0x2029, 330 + 331 + /* GNU extensions. */ 332 + DW_AT_sf_names = 0x2101, 333 + DW_AT_src_info = 0x2102, 334 + DW_AT_mac_info = 0x2103, 335 + DW_AT_src_coords = 0x2104, 336 + DW_AT_body_begin = 0x2105, 337 + DW_AT_body_end = 0x2106, 338 + DW_AT_GNU_vector = 0x2107, 339 + /* Thread-safety annotations. 340 + See http://gcc.gnu.org/wiki/ThreadSafetyAnnotation . */ 341 + DW_AT_GNU_guarded_by = 0x2108, 342 + DW_AT_GNU_pt_guarded_by = 0x2109, 343 + DW_AT_GNU_guarded = 0x210a, 344 + DW_AT_GNU_pt_guarded = 0x210b, 345 + DW_AT_GNU_locks_excluded = 0x210c, 346 + DW_AT_GNU_exclusive_locks_required = 0x210d, 347 + DW_AT_GNU_shared_locks_required = 0x210e, 348 + /* One-definition rule violation detection. 349 + See http://gcc.gnu.org/wiki/DwarfSeparateTypeInfo . */ 350 + DW_AT_GNU_odr_signature = 0x210f, 351 + /* Template template argument name. 352 + See http://gcc.gnu.org/wiki/TemplateParmsDwarf . */ 353 + DW_AT_GNU_template_name = 0x2110, 354 + /* VMS extensions. */ 355 + DW_AT_VMS_rtnbeg_pd_address = 0x2201, 356 + /* GNAT extensions. */ 357 + /* GNAT descriptive type. 358 + See http://gcc.gnu.org/wiki/DW_AT_GNAT_descriptive_type . */ 359 + DW_AT_use_GNAT_descriptive_type = 0x2301, 360 + DW_AT_GNAT_descriptive_type = 0x2302, 361 + /* UPC extension. */ 362 + DW_AT_upc_threads_scaled = 0x3210, 363 + /* PGI (STMicroelectronics) extensions. */ 364 + DW_AT_PGI_lbase = 0x3a00, 365 + DW_AT_PGI_soffset = 0x3a01, 366 + DW_AT_PGI_lstride = 0x3a02 367 + }; 368 + 369 + /* Location atom names and codes. */ 370 + enum dwarf_location_atom 371 + { 372 + DW_OP_addr = 0x03, 373 + DW_OP_deref = 0x06, 374 + DW_OP_const1u = 0x08, 375 + DW_OP_const1s = 0x09, 376 + DW_OP_const2u = 0x0a, 377 + DW_OP_const2s = 0x0b, 378 + DW_OP_const4u = 0x0c, 379 + DW_OP_const4s = 0x0d, 380 + DW_OP_const8u = 0x0e, 381 + DW_OP_const8s = 0x0f, 382 + DW_OP_constu = 0x10, 383 + DW_OP_consts = 0x11, 384 + DW_OP_dup = 0x12, 385 + DW_OP_drop = 0x13, 386 + DW_OP_over = 0x14, 387 + DW_OP_pick = 0x15, 388 + DW_OP_swap = 0x16, 389 + DW_OP_rot = 0x17, 390 + DW_OP_xderef = 0x18, 391 + DW_OP_abs = 0x19, 392 + DW_OP_and = 0x1a, 393 + DW_OP_div = 0x1b, 394 + DW_OP_minus = 0x1c, 395 + DW_OP_mod = 0x1d, 396 + DW_OP_mul = 0x1e, 397 + DW_OP_neg = 0x1f, 398 + DW_OP_not = 0x20, 399 + DW_OP_or = 0x21, 400 + DW_OP_plus = 0x22, 401 + DW_OP_plus_uconst = 0x23, 402 + DW_OP_shl = 0x24, 403 + DW_OP_shr = 0x25, 404 + DW_OP_shra = 0x26, 405 + DW_OP_xor = 0x27, 406 + DW_OP_bra = 0x28, 407 + DW_OP_eq = 0x29, 408 + DW_OP_ge = 0x2a, 409 + DW_OP_gt = 0x2b, 410 + DW_OP_le = 0x2c, 411 + DW_OP_lt = 0x2d, 412 + DW_OP_ne = 0x2e, 413 + DW_OP_skip = 0x2f, 414 + DW_OP_lit0 = 0x30, 415 + DW_OP_lit1 = 0x31, 416 + DW_OP_lit2 = 0x32, 417 + DW_OP_lit3 = 0x33, 418 + DW_OP_lit4 = 0x34, 419 + DW_OP_lit5 = 0x35, 420 + DW_OP_lit6 = 0x36, 421 + DW_OP_lit7 = 0x37, 422 + DW_OP_lit8 = 0x38, 423 + DW_OP_lit9 = 0x39, 424 + DW_OP_lit10 = 0x3a, 425 + DW_OP_lit11 = 0x3b, 426 + DW_OP_lit12 = 0x3c, 427 + DW_OP_lit13 = 0x3d, 428 + DW_OP_lit14 = 0x3e, 429 + DW_OP_lit15 = 0x3f, 430 + DW_OP_lit16 = 0x40, 431 + DW_OP_lit17 = 0x41, 432 + DW_OP_lit18 = 0x42, 433 + DW_OP_lit19 = 0x43, 434 + DW_OP_lit20 = 0x44, 435 + DW_OP_lit21 = 0x45, 436 + DW_OP_lit22 = 0x46, 437 + DW_OP_lit23 = 0x47, 438 + DW_OP_lit24 = 0x48, 439 + DW_OP_lit25 = 0x49, 440 + DW_OP_lit26 = 0x4a, 441 + DW_OP_lit27 = 0x4b, 442 + DW_OP_lit28 = 0x4c, 443 + DW_OP_lit29 = 0x4d, 444 + DW_OP_lit30 = 0x4e, 445 + DW_OP_lit31 = 0x4f, 446 + DW_OP_reg0 = 0x50, 447 + DW_OP_reg1 = 0x51, 448 + DW_OP_reg2 = 0x52, 449 + DW_OP_reg3 = 0x53, 450 + DW_OP_reg4 = 0x54, 451 + DW_OP_reg5 = 0x55, 452 + DW_OP_reg6 = 0x56, 453 + DW_OP_reg7 = 0x57, 454 + DW_OP_reg8 = 0x58, 455 + DW_OP_reg9 = 0x59, 456 + DW_OP_reg10 = 0x5a, 457 + DW_OP_reg11 = 0x5b, 458 + DW_OP_reg12 = 0x5c, 459 + DW_OP_reg13 = 0x5d, 460 + DW_OP_reg14 = 0x5e, 461 + DW_OP_reg15 = 0x5f, 462 + DW_OP_reg16 = 0x60, 463 + DW_OP_reg17 = 0x61, 464 + DW_OP_reg18 = 0x62, 465 + DW_OP_reg19 = 0x63, 466 + DW_OP_reg20 = 0x64, 467 + DW_OP_reg21 = 0x65, 468 + DW_OP_reg22 = 0x66, 469 + DW_OP_reg23 = 0x67, 470 + DW_OP_reg24 = 0x68, 471 + DW_OP_reg25 = 0x69, 472 + DW_OP_reg26 = 0x6a, 473 + DW_OP_reg27 = 0x6b, 474 + DW_OP_reg28 = 0x6c, 475 + DW_OP_reg29 = 0x6d, 476 + DW_OP_reg30 = 0x6e, 477 + DW_OP_reg31 = 0x6f, 478 + DW_OP_breg0 = 0x70, 479 + DW_OP_breg1 = 0x71, 480 + DW_OP_breg2 = 0x72, 481 + DW_OP_breg3 = 0x73, 482 + DW_OP_breg4 = 0x74, 483 + DW_OP_breg5 = 0x75, 484 + DW_OP_breg6 = 0x76, 485 + DW_OP_breg7 = 0x77, 486 + DW_OP_breg8 = 0x78, 487 + DW_OP_breg9 = 0x79, 488 + DW_OP_breg10 = 0x7a, 489 + DW_OP_breg11 = 0x7b, 490 + DW_OP_breg12 = 0x7c, 491 + DW_OP_breg13 = 0x7d, 492 + DW_OP_breg14 = 0x7e, 493 + DW_OP_breg15 = 0x7f, 494 + DW_OP_breg16 = 0x80, 495 + DW_OP_breg17 = 0x81, 496 + DW_OP_breg18 = 0x82, 497 + DW_OP_breg19 = 0x83, 498 + DW_OP_breg20 = 0x84, 499 + DW_OP_breg21 = 0x85, 500 + DW_OP_breg22 = 0x86, 501 + DW_OP_breg23 = 0x87, 502 + DW_OP_breg24 = 0x88, 503 + DW_OP_breg25 = 0x89, 504 + DW_OP_breg26 = 0x8a, 505 + DW_OP_breg27 = 0x8b, 506 + DW_OP_breg28 = 0x8c, 507 + DW_OP_breg29 = 0x8d, 508 + DW_OP_breg30 = 0x8e, 509 + DW_OP_breg31 = 0x8f, 510 + DW_OP_regx = 0x90, 511 + DW_OP_fbreg = 0x91, 512 + DW_OP_bregx = 0x92, 513 + DW_OP_piece = 0x93, 514 + DW_OP_deref_size = 0x94, 515 + DW_OP_xderef_size = 0x95, 516 + DW_OP_nop = 0x96, 517 + /* DWARF 3 extensions. */ 518 + DW_OP_push_object_address = 0x97, 519 + DW_OP_call2 = 0x98, 520 + DW_OP_call4 = 0x99, 521 + DW_OP_call_ref = 0x9a, 522 + DW_OP_form_tls_address = 0x9b, 523 + DW_OP_call_frame_cfa = 0x9c, 524 + DW_OP_bit_piece = 0x9d, 525 + 526 + /* DWARF 4 extensions. */ 527 + DW_OP_implicit_value = 0x9e, 528 + DW_OP_stack_value = 0x9f, 529 + 530 + DW_OP_lo_user = 0xe0, /* Implementation-defined range start. */ 531 + DW_OP_hi_user = 0xff, /* Implementation-defined range end. */ 532 + 533 + /* GNU extensions. */ 534 + DW_OP_GNU_push_tls_address = 0xe0, 535 + /* The following is for marking variables that are uninitialized. */ 536 + DW_OP_GNU_uninit = 0xf0, 537 + DW_OP_GNU_encoded_addr = 0xf1, 538 + DW_OP_GNU_implicit_pointer = 0xf2, 539 + /* HP extensions. */ 540 + DW_OP_HP_unknown = 0xe0, /* Ouch, the same as GNU_push_tls_address. */ 541 + DW_OP_HP_is_value = 0xe1, 542 + DW_OP_HP_fltconst4 = 0xe2, 543 + DW_OP_HP_fltconst8 = 0xe3, 544 + DW_OP_HP_mod_range = 0xe4, 545 + DW_OP_HP_unmod_range = 0xe5, 546 + DW_OP_HP_tls = 0xe6, 547 + /* PGI (STMicroelectronics) extensions. */ 548 + DW_OP_PGI_omp_thread_num = 0xf8 549 + }; 550 + 551 + /* Type encodings. */ 552 + enum dwarf_type 553 + { 554 + DW_ATE_void = 0x0, 555 + DW_ATE_address = 0x1, 556 + DW_ATE_boolean = 0x2, 557 + DW_ATE_complex_float = 0x3, 558 + DW_ATE_float = 0x4, 559 + DW_ATE_signed = 0x5, 560 + DW_ATE_signed_char = 0x6, 561 + DW_ATE_unsigned = 0x7, 562 + DW_ATE_unsigned_char = 0x8, 563 + /* DWARF 3. */ 564 + DW_ATE_imaginary_float = 0x9, 565 + DW_ATE_packed_decimal = 0xa, 566 + DW_ATE_numeric_string = 0xb, 567 + DW_ATE_edited = 0xc, 568 + DW_ATE_signed_fixed = 0xd, 569 + DW_ATE_unsigned_fixed = 0xe, 570 + DW_ATE_decimal_float = 0xf, 571 + /* DWARF 4. */ 572 + DW_ATE_UTF = 0x10, 573 + 574 + DW_ATE_lo_user = 0x80, 575 + DW_ATE_hi_user = 0xff, 576 + 577 + /* HP extensions. */ 578 + DW_ATE_HP_float80 = 0x80, /* Floating-point (80 bit). */ 579 + DW_ATE_HP_complex_float80 = 0x81, /* Complex floating-point (80 bit). */ 580 + DW_ATE_HP_float128 = 0x82, /* Floating-point (128 bit). */ 581 + DW_ATE_HP_complex_float128 = 0x83, /* Complex fp (128 bit). */ 582 + DW_ATE_HP_floathpintel = 0x84, /* Floating-point (82 bit IA64). */ 583 + DW_ATE_HP_imaginary_float80 = 0x85, 584 + DW_ATE_HP_imaginary_float128 = 0x86, 585 + DW_ATE_HP_VAX_float = 0x88, /* F or G floating. */ 586 + DW_ATE_HP_VAX_float_d = 0x89, /* D floating. */ 587 + DW_ATE_HP_packed_decimal = 0x8a, /* Cobol. */ 588 + DW_ATE_HP_zoned_decimal = 0x8b, /* Cobol. */ 589 + DW_ATE_HP_edited = 0x8c, /* Cobol. */ 590 + DW_ATE_HP_signed_fixed = 0x8d, /* Cobol. */ 591 + DW_ATE_HP_unsigned_fixed = 0x8e, /* Cobol. */ 592 + DW_ATE_HP_VAX_complex_float = 0x8f, /* F or G floating complex. */ 593 + DW_ATE_HP_VAX_complex_float_d = 0x90 /* D floating complex. */ 594 + }; 595 + 596 + /* Decimal sign encodings. */ 597 + enum dwarf_decimal_sign_encoding 598 + { 599 + /* DWARF 3. */ 600 + DW_DS_unsigned = 0x01, 601 + DW_DS_leading_overpunch = 0x02, 602 + DW_DS_trailing_overpunch = 0x03, 603 + DW_DS_leading_separate = 0x04, 604 + DW_DS_trailing_separate = 0x05 605 + }; 606 + 607 + /* Endianity encodings. */ 608 + enum dwarf_endianity_encoding 609 + { 610 + /* DWARF 3. */ 611 + DW_END_default = 0x00, 612 + DW_END_big = 0x01, 613 + DW_END_little = 0x02, 614 + 615 + DW_END_lo_user = 0x40, 616 + DW_END_hi_user = 0xff 617 + }; 618 + 619 + /* Array ordering names and codes. */ 620 + enum dwarf_array_dim_ordering 621 + { 622 + DW_ORD_row_major = 0, 623 + DW_ORD_col_major = 1 624 + }; 625 + 626 + /* Access attribute. */ 627 + enum dwarf_access_attribute 628 + { 629 + DW_ACCESS_public = 1, 630 + DW_ACCESS_protected = 2, 631 + DW_ACCESS_private = 3 632 + }; 633 + 634 + /* Visibility. */ 635 + enum dwarf_visibility_attribute 636 + { 637 + DW_VIS_local = 1, 638 + DW_VIS_exported = 2, 639 + DW_VIS_qualified = 3 640 + }; 641 + 642 + /* Virtuality. */ 643 + enum dwarf_virtuality_attribute 644 + { 645 + DW_VIRTUALITY_none = 0, 646 + DW_VIRTUALITY_virtual = 1, 647 + DW_VIRTUALITY_pure_virtual = 2 648 + }; 649 + 650 + /* Case sensitivity. */ 651 + enum dwarf_id_case 652 + { 653 + DW_ID_case_sensitive = 0, 654 + DW_ID_up_case = 1, 655 + DW_ID_down_case = 2, 656 + DW_ID_case_insensitive = 3 657 + }; 658 + 659 + /* Calling convention. */ 660 + enum dwarf_calling_convention 661 + { 662 + DW_CC_normal = 0x1, 663 + DW_CC_program = 0x2, 664 + DW_CC_nocall = 0x3, 665 + 666 + DW_CC_lo_user = 0x40, 667 + DW_CC_hi_user = 0xff, 668 + 669 + DW_CC_GNU_renesas_sh = 0x40, 670 + DW_CC_GNU_borland_fastcall_i386 = 0x41, 671 + 672 + /* This DW_CC_ value is not currently generated by any toolchain. It is 673 + used internally to GDB to indicate OpenCL C functions that have been 674 + compiled with the IBM XL C for OpenCL compiler and use a non-platform 675 + calling convention for passing OpenCL C vector types. This value may 676 + be changed freely as long as it does not conflict with any other DW_CC_ 677 + value defined here. */ 678 + DW_CC_GDB_IBM_OpenCL = 0xff 679 + }; 680 + 681 + /* Inline attribute. */ 682 + enum dwarf_inline_attribute 683 + { 684 + DW_INL_not_inlined = 0, 685 + DW_INL_inlined = 1, 686 + DW_INL_declared_not_inlined = 2, 687 + DW_INL_declared_inlined = 3 688 + }; 689 + 690 + /* Discriminant lists. */ 691 + enum dwarf_discrim_list 692 + { 693 + DW_DSC_label = 0, 694 + DW_DSC_range = 1 695 + }; 696 + 697 + /* Line number opcodes. */ 698 + enum dwarf_line_number_ops 699 + { 700 + DW_LNS_extended_op = 0, 701 + DW_LNS_copy = 1, 702 + DW_LNS_advance_pc = 2, 703 + DW_LNS_advance_line = 3, 704 + DW_LNS_set_file = 4, 705 + DW_LNS_set_column = 5, 706 + DW_LNS_negate_stmt = 6, 707 + DW_LNS_set_basic_block = 7, 708 + DW_LNS_const_add_pc = 8, 709 + DW_LNS_fixed_advance_pc = 9, 710 + /* DWARF 3. */ 711 + DW_LNS_set_prologue_end = 10, 712 + DW_LNS_set_epilogue_begin = 11, 713 + DW_LNS_set_isa = 12 714 + }; 715 + 716 + /* Line number extended opcodes. */ 717 + enum dwarf_line_number_x_ops 718 + { 719 + DW_LNE_end_sequence = 1, 720 + DW_LNE_set_address = 2, 721 + DW_LNE_define_file = 3, 722 + DW_LNE_set_discriminator = 4, 723 + /* HP extensions. */ 724 + DW_LNE_HP_negate_is_UV_update = 0x11, 725 + DW_LNE_HP_push_context = 0x12, 726 + DW_LNE_HP_pop_context = 0x13, 727 + DW_LNE_HP_set_file_line_column = 0x14, 728 + DW_LNE_HP_set_routine_name = 0x15, 729 + DW_LNE_HP_set_sequence = 0x16, 730 + DW_LNE_HP_negate_post_semantics = 0x17, 731 + DW_LNE_HP_negate_function_exit = 0x18, 732 + DW_LNE_HP_negate_front_end_logical = 0x19, 733 + DW_LNE_HP_define_proc = 0x20, 734 + DW_LNE_HP_source_file_correlation = 0x80, 735 + 736 + DW_LNE_lo_user = 0x80, 737 + DW_LNE_hi_user = 0xff 738 + }; 739 + 740 + /* Call frame information. */ 741 + enum dwarf_call_frame_info 742 + { 743 + DW_CFA_advance_loc = 0x40, 744 + DW_CFA_offset = 0x80, 745 + DW_CFA_restore = 0xc0, 746 + DW_CFA_nop = 0x00, 747 + DW_CFA_set_loc = 0x01, 748 + DW_CFA_advance_loc1 = 0x02, 749 + DW_CFA_advance_loc2 = 0x03, 750 + DW_CFA_advance_loc4 = 0x04, 751 + DW_CFA_offset_extended = 0x05, 752 + DW_CFA_restore_extended = 0x06, 753 + DW_CFA_undefined = 0x07, 754 + DW_CFA_same_value = 0x08, 755 + DW_CFA_register = 0x09, 756 + DW_CFA_remember_state = 0x0a, 757 + DW_CFA_restore_state = 0x0b, 758 + DW_CFA_def_cfa = 0x0c, 759 + DW_CFA_def_cfa_register = 0x0d, 760 + DW_CFA_def_cfa_offset = 0x0e, 761 + /* DWARF 3. */ 762 + DW_CFA_def_cfa_expression = 0x0f, 763 + DW_CFA_expression = 0x10, 764 + DW_CFA_offset_extended_sf = 0x11, 765 + DW_CFA_def_cfa_sf = 0x12, 766 + DW_CFA_def_cfa_offset_sf = 0x13, 767 + DW_CFA_val_offset = 0x14, 768 + DW_CFA_val_offset_sf = 0x15, 769 + DW_CFA_val_expression = 0x16, 770 + 771 + DW_CFA_lo_user = 0x1c, 772 + DW_CFA_hi_user = 0x3f, 773 + 774 + /* SGI/MIPS specific. */ 775 + DW_CFA_MIPS_advance_loc8 = 0x1d, 776 + /* GNU extensions. */ 777 + DW_CFA_GNU_window_save = 0x2d, 778 + DW_CFA_GNU_args_size = 0x2e, 779 + DW_CFA_GNU_negative_offset_extended = 0x2f 780 + }; 781 + 782 + #define DW_CIE_ID 0xffffffff 783 + #define DW64_CIE_ID 0xffffffffffffffffULL 784 + #define DW_CIE_VERSION 1 785 + 786 + #define DW_CFA_extended 0 787 + 788 + #define DW_CHILDREN_no 0x00 789 + #define DW_CHILDREN_yes 0x01 790 + 791 + #define DW_ADDR_none 0 792 + 793 + /* Source language names and codes. */ 794 + enum dwarf_source_language 795 + { 796 + DW_LANG_C89 = 0x0001, 797 + DW_LANG_C = 0x0002, 798 + DW_LANG_Ada83 = 0x0003, 799 + DW_LANG_C_plus_plus = 0x0004, 800 + DW_LANG_Cobol74 = 0x0005, 801 + DW_LANG_Cobol85 = 0x0006, 802 + DW_LANG_Fortran77 = 0x0007, 803 + DW_LANG_Fortran90 = 0x0008, 804 + DW_LANG_Pascal83 = 0x0009, 805 + DW_LANG_Modula2 = 0x000a, 806 + /* DWARF 3. */ 807 + DW_LANG_Java = 0x000b, 808 + DW_LANG_C99 = 0x000c, 809 + DW_LANG_Ada95 = 0x000d, 810 + DW_LANG_Fortran95 = 0x000e, 811 + DW_LANG_PLI = 0x000f, 812 + DW_LANG_ObjC = 0x0010, 813 + DW_LANG_ObjC_plus_plus = 0x0011, 814 + DW_LANG_UPC = 0x0012, 815 + DW_LANG_D = 0x0013, 816 + /* DWARF 4. */ 817 + DW_LANG_Python = 0x0014, 818 + /* DWARF 5. */ 819 + DW_LANG_Go = 0x0016, 820 + 821 + DW_LANG_lo_user = 0x8000, /* Implementation-defined range start. */ 822 + DW_LANG_hi_user = 0xffff, /* Implementation-defined range start. */ 823 + 824 + /* MIPS. */ 825 + DW_LANG_Mips_Assembler = 0x8001, 826 + /* UPC. */ 827 + DW_LANG_Upc = 0x8765, 828 + /* HP extensions. */ 829 + DW_LANG_HP_Bliss = 0x8003, 830 + DW_LANG_HP_Basic91 = 0x8004, 831 + DW_LANG_HP_Pascal91 = 0x8005, 832 + DW_LANG_HP_IMacro = 0x8006, 833 + DW_LANG_HP_Assembler = 0x8007 834 + }; 835 + 836 + /* Names and codes for macro information. */ 837 + enum dwarf_macinfo_record_type 838 + { 839 + DW_MACINFO_define = 1, 840 + DW_MACINFO_undef = 2, 841 + DW_MACINFO_start_file = 3, 842 + DW_MACINFO_end_file = 4, 843 + DW_MACINFO_vendor_ext = 255 844 + }; 845 + 846 + /* @@@ For use with GNU frame unwind information. */ 847 + 848 + #define DW_EH_PE_absptr 0x00 849 + #define DW_EH_PE_omit 0xff 850 + 851 + #define DW_EH_PE_uleb128 0x01 852 + #define DW_EH_PE_udata2 0x02 853 + #define DW_EH_PE_udata4 0x03 854 + #define DW_EH_PE_udata8 0x04 855 + #define DW_EH_PE_sleb128 0x09 856 + #define DW_EH_PE_sdata2 0x0A 857 + #define DW_EH_PE_sdata4 0x0B 858 + #define DW_EH_PE_sdata8 0x0C 859 + #define DW_EH_PE_signed 0x08 860 + 861 + #define DW_EH_PE_pcrel 0x10 862 + #define DW_EH_PE_textrel 0x20 863 + #define DW_EH_PE_datarel 0x30 864 + #define DW_EH_PE_funcrel 0x40 865 + #define DW_EH_PE_aligned 0x50 866 + 867 + #define DW_EH_PE_indirect 0x80 868 + 869 + #endif /* _DWARF2_H */
+202
src/libunwind-darwin/emutls.c
··· 1 + /* TLS emulation. 2 + Copyright (C) 2006, 2008, 2009 Free Software Foundation, Inc. 3 + Contributed by Jakub Jelinek <jakub@redhat.com>. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it under 8 + the terms of the GNU General Public License as published by the Free 9 + Software Foundation; either version 3, or (at your option) any later 10 + version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT ANY 13 + WARRANTY; without even the implied warranty of MERCHANTABILITY or 14 + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15 + for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #include "tconfig.h" 27 + #include "tsystem.h" 28 + #include "coretypes.h" 29 + #include "tm.h" 30 + #include "gthr.h" 31 + 32 + typedef unsigned int word __attribute__((mode(word))); 33 + typedef unsigned int pointer __attribute__((mode(pointer))); 34 + 35 + struct __emutls_object 36 + { 37 + word size; 38 + word align; 39 + union { 40 + pointer offset; 41 + void *ptr; 42 + } loc; 43 + void *templ; 44 + }; 45 + 46 + struct __emutls_array 47 + { 48 + pointer size; 49 + void **data[]; 50 + }; 51 + 52 + void *__emutls_get_address (struct __emutls_object *); 53 + void __emutls_register_common (struct __emutls_object *, word, word, void *); 54 + 55 + #ifdef __GTHREADS 56 + #ifdef __GTHREAD_MUTEX_INIT 57 + static __gthread_mutex_t emutls_mutex = __GTHREAD_MUTEX_INIT; 58 + #else 59 + static __gthread_mutex_t emutls_mutex; 60 + #endif 61 + static __gthread_key_t emutls_key; 62 + static pointer emutls_size; 63 + 64 + static void 65 + emutls_destroy (void *ptr) 66 + { 67 + struct __emutls_array *arr = ptr; 68 + pointer size = arr->size; 69 + pointer i; 70 + 71 + for (i = 0; i < size; ++i) 72 + { 73 + if (arr->data[i]) 74 + free (arr->data[i][-1]); 75 + } 76 + 77 + free (ptr); 78 + } 79 + 80 + static void 81 + emutls_init (void) 82 + { 83 + #ifndef __GTHREAD_MUTEX_INIT 84 + __GTHREAD_MUTEX_INIT_FUNCTION (&emutls_mutex); 85 + #endif 86 + if (__gthread_key_create (&emutls_key, emutls_destroy) != 0) 87 + abort (); 88 + } 89 + #endif 90 + 91 + static void * 92 + emutls_alloc (struct __emutls_object *obj) 93 + { 94 + void *ptr; 95 + void *ret; 96 + 97 + /* We could use here posix_memalign if available and adjust 98 + emutls_destroy accordingly. */ 99 + if (obj->align <= sizeof (void *)) 100 + { 101 + ptr = malloc (obj->size + sizeof (void *)); 102 + if (ptr == NULL) 103 + abort (); 104 + ((void **) ptr)[0] = ptr; 105 + ret = ptr + sizeof (void *); 106 + } 107 + else 108 + { 109 + ptr = malloc (obj->size + sizeof (void *) + obj->align - 1); 110 + if (ptr == NULL) 111 + abort (); 112 + ret = (void *) (((pointer) (ptr + sizeof (void *) + obj->align - 1)) 113 + & ~(pointer)(obj->align - 1)); 114 + ((void **) ret)[-1] = ptr; 115 + } 116 + 117 + if (obj->templ) 118 + memcpy (ret, obj->templ, obj->size); 119 + else 120 + memset (ret, 0, obj->size); 121 + 122 + return ret; 123 + } 124 + 125 + void * 126 + __emutls_get_address (struct __emutls_object *obj) 127 + { 128 + if (! __gthread_active_p ()) 129 + { 130 + if (__builtin_expect (obj->loc.ptr == NULL, 0)) 131 + obj->loc.ptr = emutls_alloc (obj); 132 + return obj->loc.ptr; 133 + } 134 + 135 + #ifndef __GTHREADS 136 + abort (); 137 + #else 138 + pointer offset = obj->loc.offset; 139 + 140 + if (__builtin_expect (offset == 0, 0)) 141 + { 142 + static __gthread_once_t once = __GTHREAD_ONCE_INIT; 143 + __gthread_once (&once, emutls_init); 144 + __gthread_mutex_lock (&emutls_mutex); 145 + offset = obj->loc.offset; 146 + if (offset == 0) 147 + { 148 + offset = ++emutls_size; 149 + obj->loc.offset = offset; 150 + } 151 + __gthread_mutex_unlock (&emutls_mutex); 152 + } 153 + 154 + struct __emutls_array *arr = __gthread_getspecific (emutls_key); 155 + if (__builtin_expect (arr == NULL, 0)) 156 + { 157 + pointer size = offset + 32; 158 + arr = calloc (size + 1, sizeof (void *)); 159 + if (arr == NULL) 160 + abort (); 161 + arr->size = size; 162 + __gthread_setspecific (emutls_key, (void *) arr); 163 + } 164 + else if (__builtin_expect (offset > arr->size, 0)) 165 + { 166 + pointer orig_size = arr->size; 167 + pointer size = orig_size * 2; 168 + if (offset > size) 169 + size = offset + 32; 170 + arr = realloc (arr, (size + 1) * sizeof (void *)); 171 + if (arr == NULL) 172 + abort (); 173 + arr->size = size; 174 + memset (arr->data + orig_size, 0, 175 + (size - orig_size) * sizeof (void *)); 176 + __gthread_setspecific (emutls_key, (void *) arr); 177 + } 178 + 179 + void *ret = arr->data[offset - 1]; 180 + if (__builtin_expect (ret == NULL, 0)) 181 + { 182 + ret = emutls_alloc (obj); 183 + arr->data[offset - 1] = ret; 184 + } 185 + return ret; 186 + #endif 187 + } 188 + 189 + void 190 + __emutls_register_common (struct __emutls_object *obj, 191 + word size, word align, void *templ) 192 + { 193 + if (obj->size < size) 194 + { 195 + obj->size = size; 196 + obj->templ = NULL; 197 + } 198 + if (obj->align < align) 199 + obj->align = align; 200 + if (templ && size == obj->size) 201 + obj->templ = templ; 202 + }
src/libunwind-darwin/gthr.h

This is a binary file and will not be displayed.

+2
src/libunwind-darwin/link.cmd
··· 1 + __darwin_Unwind_RaiseException = _Unwind_RaiseException ; 2 +
+851
src/libunwind-darwin/mcore.h
··· 1 + /* Definitions of target machine for GNU compiler, 2 + for Motorola M*CORE Processor. 3 + Copyright (C) 1993, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 4 + 2008, 2009, 2010 Free Software Foundation, Inc. 5 + 6 + This file is part of GCC. 7 + 8 + GCC is free software; you can redistribute it and/or modify it 9 + under the terms of the GNU General Public License as published 10 + by the Free Software Foundation; either version 3, or (at your 11 + option) any later version. 12 + 13 + GCC is distributed in the hope that it will be useful, but WITHOUT 14 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 15 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 16 + License for more details. 17 + 18 + You should have received a copy of the GNU General Public License 19 + along with GCC; see the file COPYING3. If not see 20 + <http://www.gnu.org/licenses/>. */ 21 + 22 + #ifndef GCC_MCORE_H 23 + #define GCC_MCORE_H 24 + 25 + /* RBE: need to move these elsewhere. */ 26 + #undef LIKE_PPC_ABI 27 + #define MCORE_STRUCT_ARGS 28 + /* RBE: end of "move elsewhere". */ 29 + 30 + /* Run-time Target Specification. */ 31 + #define TARGET_MCORE 32 + 33 + /* Get tree.c to declare a target-specific specialization of 34 + merge_decl_attributes. */ 35 + #define TARGET_DLLIMPORT_DECL_ATTRIBUTES 1 36 + 37 + #define TARGET_CPU_CPP_BUILTINS() \ 38 + do \ 39 + { \ 40 + builtin_define ("__mcore__"); \ 41 + builtin_define ("__MCORE__"); \ 42 + if (TARGET_LITTLE_END) \ 43 + builtin_define ("__MCORELE__"); \ 44 + else \ 45 + builtin_define ("__MCOREBE__"); \ 46 + if (TARGET_M340) \ 47 + builtin_define ("__M340__"); \ 48 + else \ 49 + builtin_define ("__M210__"); \ 50 + } \ 51 + while (0) 52 + 53 + #undef CPP_SPEC 54 + #define CPP_SPEC "%{m210:%{mlittle-endian:%ethe m210 does not have little endian support}}" 55 + 56 + /* We don't have a -lg library, so don't put it in the list. */ 57 + #undef LIB_SPEC 58 + #define LIB_SPEC "%{!shared: %{!p:%{!pg:-lc}}%{p:-lc_p}%{pg:-lc_p}}" 59 + 60 + #undef ASM_SPEC 61 + #define ASM_SPEC "%{mbig-endian:-EB} %{m210:-cpu=210 -EB}" 62 + 63 + #undef LINK_SPEC 64 + #define LINK_SPEC "%{mbig-endian:-EB} %{m210:-EB} -X" 65 + 66 + #define TARGET_DEFAULT \ 67 + (MASK_HARDLIT \ 68 + | MASK_DIV \ 69 + | MASK_RELAX_IMM \ 70 + | MASK_M340 \ 71 + | MASK_LITTLE_END) 72 + 73 + #ifndef MULTILIB_DEFAULTS 74 + #define MULTILIB_DEFAULTS { "mlittle-endian", "m340" } 75 + #endif 76 + 77 + /* The ability to have 4 byte alignment is being suppressed for now. 78 + If this ability is reenabled, you must disable the definition below 79 + *and* edit t-mcore to enable multilibs for 4 byte alignment code. */ 80 + #undef TARGET_8ALIGN 81 + #define TARGET_8ALIGN 1 82 + 83 + extern char * mcore_current_function_name; 84 + 85 + /* The MCore ABI says that bitfields are unsigned by default. */ 86 + #define CC1_SPEC "-funsigned-bitfields" 87 + 88 + /* Target machine storage Layout. */ 89 + 90 + #define PROMOTE_MODE(MODE,UNSIGNEDP,TYPE) \ 91 + if (GET_MODE_CLASS (MODE) == MODE_INT \ 92 + && GET_MODE_SIZE (MODE) < UNITS_PER_WORD) \ 93 + { \ 94 + (MODE) = SImode; \ 95 + (UNSIGNEDP) = 1; \ 96 + } 97 + 98 + /* Define this if most significant bit is lowest numbered 99 + in instructions that operate on numbered bit-fields. */ 100 + #define BITS_BIG_ENDIAN 0 101 + 102 + /* Define this if most significant byte of a word is the lowest numbered. */ 103 + #define BYTES_BIG_ENDIAN (! TARGET_LITTLE_END) 104 + 105 + /* Define this if most significant word of a multiword number is the lowest 106 + numbered. */ 107 + #define WORDS_BIG_ENDIAN (! TARGET_LITTLE_END) 108 + 109 + #define MAX_BITS_PER_WORD 32 110 + 111 + /* Width of a word, in units (bytes). */ 112 + #define UNITS_PER_WORD 4 113 + 114 + /* A C expression for the size in bits of the type `long long' on the 115 + target machine. If you don't define this, the default is two 116 + words. */ 117 + #define LONG_LONG_TYPE_SIZE 64 118 + 119 + /* Allocation boundary (in *bits*) for storing arguments in argument list. */ 120 + #define PARM_BOUNDARY 32 121 + 122 + /* Boundary (in *bits*) on which stack pointer should be aligned. */ 123 + #define STACK_BOUNDARY (TARGET_8ALIGN ? 64 : 32) 124 + 125 + /* Largest increment in UNITS we allow the stack to grow in a single operation. */ 126 + #define STACK_UNITS_MAXSTEP 4096 127 + 128 + /* Allocation boundary (in *bits*) for the code of a function. */ 129 + #define FUNCTION_BOUNDARY ((TARGET_OVERALIGN_FUNC) ? 32 : 16) 130 + 131 + /* Alignment of field after `int : 0' in a structure. */ 132 + #define EMPTY_FIELD_BOUNDARY 32 133 + 134 + /* No data type wants to be aligned rounder than this. */ 135 + #define BIGGEST_ALIGNMENT (TARGET_8ALIGN ? 64 : 32) 136 + 137 + /* The best alignment to use in cases where we have a choice. */ 138 + #define FASTEST_ALIGNMENT 32 139 + 140 + /* Every structures size must be a multiple of 8 bits. */ 141 + #define STRUCTURE_SIZE_BOUNDARY 8 142 + 143 + /* Look at the fundamental type that is used for a bit-field and use 144 + that to impose alignment on the enclosing structure. 145 + struct s {int a:8}; should have same alignment as "int", not "char". */ 146 + #define PCC_BITFIELD_TYPE_MATTERS 1 147 + 148 + /* Largest integer machine mode for structures. If undefined, the default 149 + is GET_MODE_SIZE(DImode). */ 150 + #define MAX_FIXED_MODE_SIZE 32 151 + 152 + /* Make strings word-aligned so strcpy from constants will be faster. */ 153 + #define CONSTANT_ALIGNMENT(EXP, ALIGN) \ 154 + ((TREE_CODE (EXP) == STRING_CST \ 155 + && (ALIGN) < FASTEST_ALIGNMENT) \ 156 + ? FASTEST_ALIGNMENT : (ALIGN)) 157 + 158 + /* Make arrays of chars word-aligned for the same reasons. */ 159 + #define DATA_ALIGNMENT(TYPE, ALIGN) \ 160 + (TREE_CODE (TYPE) == ARRAY_TYPE \ 161 + && TYPE_MODE (TREE_TYPE (TYPE)) == QImode \ 162 + && (ALIGN) < FASTEST_ALIGNMENT ? FASTEST_ALIGNMENT : (ALIGN)) 163 + 164 + /* Set this nonzero if move instructions will actually fail to work 165 + when given unaligned data. */ 166 + #define STRICT_ALIGNMENT 1 167 + 168 + /* Standard register usage. */ 169 + 170 + /* Register allocation for our first guess 171 + 172 + r0 stack pointer 173 + r1 scratch, target reg for xtrb? 174 + r2-r7 arguments. 175 + r8-r14 call saved 176 + r15 link register 177 + ap arg pointer (doesn't really exist, always eliminated) 178 + c c bit 179 + fp frame pointer (doesn't really exist, always eliminated) 180 + x19 two control registers. */ 181 + 182 + /* Number of actual hardware registers. 183 + The hardware registers are assigned numbers for the compiler 184 + from 0 to just below FIRST_PSEUDO_REGISTER. 185 + All registers that the compiler knows about must be given numbers, 186 + even those that are not normally considered general registers. 187 + 188 + MCore has 16 integer registers and 2 control registers + the arg 189 + pointer. */ 190 + 191 + #define FIRST_PSEUDO_REGISTER 20 192 + 193 + #define R1_REG 1 /* Where literals are forced. */ 194 + #define LK_REG 15 /* Overloaded on general register. */ 195 + #define AP_REG 16 /* Fake arg pointer register. */ 196 + /* RBE: mcore.md depends on CC_REG being set to 17. */ 197 + #define CC_REG 17 /* Can't name it C_REG. */ 198 + #define FP_REG 18 /* Fake frame pointer register. */ 199 + 200 + /* Specify the registers used for certain standard purposes. 201 + The values of these macros are register numbers. */ 202 + 203 + 204 + #undef PC_REGNUM /* Define this if the program counter is overloaded on a register. */ 205 + #define STACK_POINTER_REGNUM 0 /* Register to use for pushing function arguments. */ 206 + #define FRAME_POINTER_REGNUM 8 /* When we need FP, use r8. */ 207 + 208 + /* The assembler's names for the registers. RFP need not always be used as 209 + the Real framepointer; it can also be used as a normal general register. 210 + Note that the name `fp' is horribly misleading since `fp' is in fact only 211 + the argument-and-return-context pointer. */ 212 + #define REGISTER_NAMES \ 213 + { \ 214 + "sp", "r1", "r2", "r3", "r4", "r5", "r6", "r7", \ 215 + "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", \ 216 + "apvirtual", "c", "fpvirtual", "x19" \ 217 + } 218 + 219 + /* 1 for registers that have pervasive standard uses 220 + and are not available for the register allocator. */ 221 + #define FIXED_REGISTERS \ 222 + /* r0 r1 r2 r3 r4 r5 r6 r7 r8 r9 r10 r11 r12 r13 r14 r15 ap c fp x19 */ \ 223 + { 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1} 224 + 225 + /* 1 for registers not available across function calls. 226 + These must include the FIXED_REGISTERS and also any 227 + registers that can be used without being saved. 228 + The latter must include the registers where values are returned 229 + and the register where structure-value addresses are passed. 230 + Aside from that, you can include as many other registers as you like. */ 231 + 232 + /* RBE: r15 {link register} not available across calls, 233 + But we don't mark it that way here.... */ 234 + #define CALL_USED_REGISTERS \ 235 + /* r0 r1 r2 r3 r4 r5 r6 r7 r8 r9 r10 r11 r12 r13 r14 r15 ap c fp x19 */ \ 236 + { 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1} 237 + 238 + /* The order in which register should be allocated. */ 239 + #define REG_ALLOC_ORDER \ 240 + /* r7 r6 r5 r4 r3 r2 r15 r14 r13 r12 r11 r10 r9 r8 r1 r0 ap c fp x19*/ \ 241 + { 7, 6, 5, 4, 3, 2, 15, 14, 13, 12, 11, 10, 9, 8, 1, 0, 16, 17, 18, 19} 242 + 243 + /* Return number of consecutive hard regs needed starting at reg REGNO 244 + to hold something of mode MODE. 245 + This is ordinarily the length in words of a value of mode MODE 246 + but can be less for certain modes in special long registers. 247 + 248 + On the MCore regs are UNITS_PER_WORD bits wide; */ 249 + #define HARD_REGNO_NREGS(REGNO, MODE) \ 250 + (((GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD)) 251 + 252 + /* Value is 1 if hard register REGNO can hold a value of machine-mode MODE. 253 + We may keep double values in even registers. */ 254 + #define HARD_REGNO_MODE_OK(REGNO, MODE) \ 255 + ((TARGET_8ALIGN && GET_MODE_SIZE (MODE) > UNITS_PER_WORD) ? (((REGNO) & 1) == 0) : (REGNO < 18)) 256 + 257 + /* Value is 1 if it is a good idea to tie two pseudo registers 258 + when one has mode MODE1 and one has mode MODE2. 259 + If HARD_REGNO_MODE_OK could produce different values for MODE1 and MODE2, 260 + for any hard reg, then this must be 0 for correct output. */ 261 + #define MODES_TIEABLE_P(MODE1, MODE2) \ 262 + ((MODE1) == (MODE2) || GET_MODE_CLASS (MODE1) == GET_MODE_CLASS (MODE2)) 263 + 264 + /* Definitions for register eliminations. 265 + 266 + We have two registers that can be eliminated on the MCore. First, the 267 + frame pointer register can often be eliminated in favor of the stack 268 + pointer register. Secondly, the argument pointer register can always be 269 + eliminated; it is replaced with either the stack or frame pointer. */ 270 + 271 + /* Base register for access to arguments of the function. */ 272 + #define ARG_POINTER_REGNUM 16 273 + 274 + /* Register in which the static-chain is passed to a function. */ 275 + #define STATIC_CHAIN_REGNUM 1 276 + 277 + /* This is an array of structures. Each structure initializes one pair 278 + of eliminable registers. The "from" register number is given first, 279 + followed by "to". Eliminations of the same "from" register are listed 280 + in order of preference. */ 281 + #define ELIMINABLE_REGS \ 282 + {{ FRAME_POINTER_REGNUM, STACK_POINTER_REGNUM}, \ 283 + { ARG_POINTER_REGNUM, STACK_POINTER_REGNUM}, \ 284 + { ARG_POINTER_REGNUM, FRAME_POINTER_REGNUM},} 285 + 286 + /* Define the offset between two registers, one to be eliminated, and the other 287 + its replacement, at the start of a routine. */ 288 + #define INITIAL_ELIMINATION_OFFSET(FROM, TO, OFFSET) \ 289 + OFFSET = mcore_initial_elimination_offset (FROM, TO) 290 + 291 + /* Define the classes of registers for register constraints in the 292 + machine description. Also define ranges of constants. 293 + 294 + One of the classes must always be named ALL_REGS and include all hard regs. 295 + If there is more than one class, another class must be named NO_REGS 296 + and contain no registers. 297 + 298 + The name GENERAL_REGS must be the name of a class (or an alias for 299 + another name such as ALL_REGS). This is the class of registers 300 + that is allowed by "g" or "r" in a register constraint. 301 + Also, registers outside this class are allocated only when 302 + instructions express preferences for them. 303 + 304 + The classes must be numbered in nondecreasing order; that is, 305 + a larger-numbered class must never be contained completely 306 + in a smaller-numbered class. 307 + 308 + For any two classes, it is very desirable that there be another 309 + class that represents their union. */ 310 + 311 + /* The MCore has only general registers. There are 312 + also some special purpose registers: the T bit register, the 313 + procedure Link and the Count Registers. */ 314 + enum reg_class 315 + { 316 + NO_REGS, 317 + ONLYR1_REGS, 318 + LRW_REGS, 319 + GENERAL_REGS, 320 + C_REGS, 321 + ALL_REGS, 322 + LIM_REG_CLASSES 323 + }; 324 + 325 + #define N_REG_CLASSES (int) LIM_REG_CLASSES 326 + 327 + #define IRA_COVER_CLASSES \ 328 + { \ 329 + GENERAL_REGS, C_REGS, LIM_REG_CLASSES \ 330 + } 331 + 332 + 333 + /* Give names of register classes as strings for dump file. */ 334 + #define REG_CLASS_NAMES \ 335 + { \ 336 + "NO_REGS", \ 337 + "ONLYR1_REGS", \ 338 + "LRW_REGS", \ 339 + "GENERAL_REGS", \ 340 + "C_REGS", \ 341 + "ALL_REGS", \ 342 + } 343 + 344 + /* Define which registers fit in which classes. 345 + This is an initializer for a vector of HARD_REG_SET 346 + of length N_REG_CLASSES. */ 347 + 348 + /* ??? STACK_POINTER_REGNUM should be excluded from LRW_REGS. */ 349 + #define REG_CLASS_CONTENTS \ 350 + { \ 351 + {0x000000}, /* NO_REGS */ \ 352 + {0x000002}, /* ONLYR1_REGS */ \ 353 + {0x007FFE}, /* LRW_REGS */ \ 354 + {0x01FFFF}, /* GENERAL_REGS */ \ 355 + {0x020000}, /* C_REGS */ \ 356 + {0x0FFFFF} /* ALL_REGS */ \ 357 + } 358 + 359 + /* The same information, inverted: 360 + Return the class number of the smallest class containing 361 + reg number REGNO. This could be a conditional expression 362 + or could index an array. */ 363 + 364 + extern const enum reg_class regno_reg_class[FIRST_PSEUDO_REGISTER]; 365 + #define REGNO_REG_CLASS(REGNO) regno_reg_class[REGNO] 366 + 367 + /* When this hook returns true for MODE, the compiler allows 368 + registers explicitly used in the rtl to be used as spill registers 369 + but prevents the compiler from extending the lifetime of these 370 + registers. */ 371 + #define TARGET_SMALL_REGISTER_CLASSES_FOR_MODE_P hook_bool_mode_true 372 + 373 + /* The class value for index registers, and the one for base regs. */ 374 + #define INDEX_REG_CLASS NO_REGS 375 + #define BASE_REG_CLASS GENERAL_REGS 376 + 377 + /* Convenience wrappers around insn_const_int_ok_for_constraint. */ 378 + #define CONST_OK_FOR_I(VALUE) \ 379 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_I) 380 + #define CONST_OK_FOR_J(VALUE) \ 381 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_J) 382 + #define CONST_OK_FOR_L(VALUE) \ 383 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_L) 384 + #define CONST_OK_FOR_K(VALUE) \ 385 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_K) 386 + #define CONST_OK_FOR_M(VALUE) \ 387 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_M) 388 + #define CONST_OK_FOR_N(VALUE) \ 389 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_N) 390 + #define CONST_OK_FOR_O(VALUE) \ 391 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_O) 392 + #define CONST_OK_FOR_P(VALUE) \ 393 + insn_const_int_ok_for_constraint (VALUE, CONSTRAINT_P) 394 + 395 + /* Given an rtx X being reloaded into a reg required to be 396 + in class CLASS, return the class of reg to actually use. 397 + In general this is just CLASS; but on some machines 398 + in some cases it is preferable to use a more restrictive class. */ 399 + #define PREFERRED_RELOAD_CLASS(X, CLASS) mcore_reload_class (X, CLASS) 400 + 401 + /* Return the register class of a scratch register needed to copy IN into 402 + or out of a register in CLASS in MODE. If it can be done directly, 403 + NO_REGS is returned. */ 404 + #define SECONDARY_RELOAD_CLASS(CLASS, MODE, X) \ 405 + mcore_secondary_reload_class (CLASS, MODE, X) 406 + 407 + /* Return the maximum number of consecutive registers 408 + needed to represent mode MODE in a register of class CLASS. 409 + 410 + On MCore this is the size of MODE in words. */ 411 + #define CLASS_MAX_NREGS(CLASS, MODE) \ 412 + (ROUND_ADVANCE (GET_MODE_SIZE (MODE))) 413 + 414 + /* Stack layout; function entry, exit and calling. */ 415 + 416 + /* Define the number of register that can hold parameters. 417 + These two macros are used only in other macro definitions below. */ 418 + #define NPARM_REGS 6 419 + #define FIRST_PARM_REG 2 420 + #define FIRST_RET_REG 2 421 + 422 + /* Define this if pushing a word on the stack 423 + makes the stack pointer a smaller address. */ 424 + #define STACK_GROWS_DOWNWARD 425 + 426 + /* Offset within stack frame to start allocating local variables at. 427 + If FRAME_GROWS_DOWNWARD, this is the offset to the END of the 428 + first local allocated. Otherwise, it is the offset to the BEGINNING 429 + of the first local allocated. */ 430 + #define STARTING_FRAME_OFFSET 0 431 + 432 + /* If defined, the maximum amount of space required for outgoing arguments 433 + will be computed and placed into the variable 434 + `crtl->outgoing_args_size'. No space will be pushed 435 + onto the stack for each call; instead, the function prologue should 436 + increase the stack frame size by this amount. */ 437 + #define ACCUMULATE_OUTGOING_ARGS 1 438 + 439 + /* Offset of first parameter from the argument pointer register value. */ 440 + #define FIRST_PARM_OFFSET(FNDECL) 0 441 + 442 + /* Define how to find the value returned by a function. 443 + VALTYPE is the data type of the value (as a tree). 444 + If the precise function being called is known, FUNC is its FUNCTION_DECL; 445 + otherwise, FUNC is 0. */ 446 + #define FUNCTION_VALUE(VALTYPE, FUNC) mcore_function_value (VALTYPE, FUNC) 447 + 448 + /* Don't default to pcc-struct-return, because gcc is the only compiler, and 449 + we want to retain compatibility with older gcc versions. */ 450 + #define DEFAULT_PCC_STRUCT_RETURN 0 451 + 452 + /* Define how to find the value returned by a library function 453 + assuming the value has mode MODE. */ 454 + #define LIBCALL_VALUE(MODE) gen_rtx_REG (MODE, FIRST_RET_REG) 455 + 456 + /* 1 if N is a possible register number for a function value. 457 + On the MCore, only r4 can return results. */ 458 + #define FUNCTION_VALUE_REGNO_P(REGNO) ((REGNO) == FIRST_RET_REG) 459 + 460 + /* 1 if N is a possible register number for function argument passing. */ 461 + #define FUNCTION_ARG_REGNO_P(REGNO) \ 462 + ((REGNO) >= FIRST_PARM_REG && (REGNO) < (NPARM_REGS + FIRST_PARM_REG)) 463 + 464 + /* Define a data type for recording info about an argument list 465 + during the scan of that argument list. This data type should 466 + hold all necessary information about the function itself 467 + and about the args processed so far, enough to enable macros 468 + such as FUNCTION_ARG to determine where the next arg should go. 469 + 470 + On MCore, this is a single integer, which is a number of words 471 + of arguments scanned so far (including the invisible argument, 472 + if any, which holds the structure-value-address). 473 + Thus NARGREGS or more means all following args should go on the stack. */ 474 + #define CUMULATIVE_ARGS int 475 + 476 + #define ROUND_ADVANCE(SIZE) \ 477 + ((SIZE + UNITS_PER_WORD - 1) / UNITS_PER_WORD) 478 + 479 + /* Round a register number up to a proper boundary for an arg of mode 480 + MODE. 481 + 482 + We round to an even reg for things larger than a word. */ 483 + #define ROUND_REG(X, MODE) \ 484 + ((TARGET_8ALIGN \ 485 + && GET_MODE_UNIT_SIZE ((MODE)) > UNITS_PER_WORD) \ 486 + ? ((X) + ((X) & 1)) : (X)) 487 + 488 + 489 + /* Initialize a variable CUM of type CUMULATIVE_ARGS 490 + for a call to a function whose data type is FNTYPE. 491 + For a library call, FNTYPE is 0. 492 + 493 + On MCore, the offset always starts at 0: the first parm reg is always 494 + the same reg. */ 495 + #define INIT_CUMULATIVE_ARGS(CUM, FNTYPE, LIBNAME, INDIRECT, N_NAMED_ARGS) \ 496 + ((CUM) = 0) 497 + 498 + /* Call the function profiler with a given profile label. */ 499 + #define FUNCTION_PROFILER(STREAM,LABELNO) \ 500 + { \ 501 + fprintf (STREAM, " trap 1\n"); \ 502 + fprintf (STREAM, " .align 2\n"); \ 503 + fprintf (STREAM, " .long LP%d\n", (LABELNO)); \ 504 + } 505 + 506 + /* EXIT_IGNORE_STACK should be nonzero if, when returning from a function, 507 + the stack pointer does not matter. The value is tested only in 508 + functions that have frame pointers. 509 + No definition is equivalent to always zero. */ 510 + #define EXIT_IGNORE_STACK 0 511 + 512 + /* Length in units of the trampoline for entering a nested function. */ 513 + #define TRAMPOLINE_SIZE 12 514 + 515 + /* Alignment required for a trampoline in bits. */ 516 + #define TRAMPOLINE_ALIGNMENT 32 517 + 518 + /* Macros to check register numbers against specific register classes. */ 519 + 520 + /* These assume that REGNO is a hard or pseudo reg number. 521 + They give nonzero only if REGNO is a hard reg of the suitable class 522 + or a pseudo reg currently allocated to a suitable hard reg. 523 + Since they use reg_renumber, they are safe only once reg_renumber 524 + has been allocated, which happens in local-alloc.c. */ 525 + #define REGNO_OK_FOR_BASE_P(REGNO) \ 526 + ((REGNO) < AP_REG || (unsigned) reg_renumber[(REGNO)] < AP_REG) 527 + 528 + #define REGNO_OK_FOR_INDEX_P(REGNO) 0 529 + 530 + /* Maximum number of registers that can appear in a valid memory 531 + address. */ 532 + #define MAX_REGS_PER_ADDRESS 1 533 + 534 + /* Recognize any constant value that is a valid address. */ 535 + #define CONSTANT_ADDRESS_P(X) (GET_CODE (X) == LABEL_REF) 536 + 537 + /* Nonzero if the constant value X is a legitimate general operand. 538 + It is given that X satisfies CONSTANT_P or is a CONST_DOUBLE. 539 + 540 + On the MCore, allow anything but a double. */ 541 + #define LEGITIMATE_CONSTANT_P(X) (GET_CODE(X) != CONST_DOUBLE \ 542 + && CONSTANT_P (X)) 543 + 544 + /* The macros REG_OK_FOR..._P assume that the arg is a REG rtx 545 + and check its validity for a certain class. 546 + We have two alternate definitions for each of them. 547 + The usual definition accepts all pseudo regs; the other rejects 548 + them unless they have been allocated suitable hard regs. 549 + The symbol REG_OK_STRICT causes the latter definition to be used. */ 550 + #ifndef REG_OK_STRICT 551 + 552 + /* Nonzero if X is a hard reg that can be used as a base reg 553 + or if it is a pseudo reg. */ 554 + #define REG_OK_FOR_BASE_P(X) \ 555 + (REGNO (X) <= 16 || REGNO (X) >= FIRST_PSEUDO_REGISTER) 556 + 557 + /* Nonzero if X is a hard reg that can be used as an index 558 + or if it is a pseudo reg. */ 559 + #define REG_OK_FOR_INDEX_P(X) 0 560 + 561 + #else 562 + 563 + /* Nonzero if X is a hard reg that can be used as a base reg. */ 564 + #define REG_OK_FOR_BASE_P(X) \ 565 + REGNO_OK_FOR_BASE_P (REGNO (X)) 566 + 567 + /* Nonzero if X is a hard reg that can be used as an index. */ 568 + #define REG_OK_FOR_INDEX_P(X) 0 569 + 570 + #endif 571 + /* GO_IF_LEGITIMATE_ADDRESS recognizes an RTL expression 572 + that is a valid memory address for an instruction. 573 + The MODE argument is the machine mode for the MEM expression 574 + that wants to use this address. 575 + 576 + The other macros defined here are used only in GO_IF_LEGITIMATE_ADDRESS. */ 577 + #define BASE_REGISTER_RTX_P(X) \ 578 + (GET_CODE (X) == REG && REG_OK_FOR_BASE_P (X)) 579 + 580 + #define INDEX_REGISTER_RTX_P(X) \ 581 + (GET_CODE (X) == REG && REG_OK_FOR_INDEX_P (X)) 582 + 583 + 584 + /* Jump to LABEL if X is a valid address RTX. This must also take 585 + REG_OK_STRICT into account when deciding about valid registers, but it uses 586 + the above macros so we are in luck. 587 + 588 + Allow REG 589 + REG+disp 590 + 591 + A legitimate index for a QI is 0..15, for HI is 0..30, for SI is 0..60, 592 + and for DI is 0..56 because we use two SI loads, etc. */ 593 + #define GO_IF_LEGITIMATE_INDEX(MODE, REGNO, OP, LABEL) \ 594 + do \ 595 + { \ 596 + if (GET_CODE (OP) == CONST_INT) \ 597 + { \ 598 + if (GET_MODE_SIZE (MODE) >= 4 \ 599 + && (((unsigned HOST_WIDE_INT) INTVAL (OP)) % 4) == 0 \ 600 + && ((unsigned HOST_WIDE_INT) INTVAL (OP)) \ 601 + <= (unsigned HOST_WIDE_INT) 64 - GET_MODE_SIZE (MODE)) \ 602 + goto LABEL; \ 603 + if (GET_MODE_SIZE (MODE) == 2 \ 604 + && (((unsigned HOST_WIDE_INT) INTVAL (OP)) % 2) == 0 \ 605 + && ((unsigned HOST_WIDE_INT) INTVAL (OP)) <= 30) \ 606 + goto LABEL; \ 607 + if (GET_MODE_SIZE (MODE) == 1 \ 608 + && ((unsigned HOST_WIDE_INT) INTVAL (OP)) <= 15) \ 609 + goto LABEL; \ 610 + } \ 611 + } \ 612 + while (0) 613 + 614 + #define GO_IF_LEGITIMATE_ADDRESS(MODE, X, LABEL) \ 615 + { \ 616 + if (BASE_REGISTER_RTX_P (X)) \ 617 + goto LABEL; \ 618 + else if (GET_CODE (X) == PLUS || GET_CODE (X) == LO_SUM) \ 619 + { \ 620 + rtx xop0 = XEXP (X,0); \ 621 + rtx xop1 = XEXP (X,1); \ 622 + if (BASE_REGISTER_RTX_P (xop0)) \ 623 + GO_IF_LEGITIMATE_INDEX (MODE, REGNO (xop0), xop1, LABEL); \ 624 + if (BASE_REGISTER_RTX_P (xop1)) \ 625 + GO_IF_LEGITIMATE_INDEX (MODE, REGNO (xop1), xop0, LABEL); \ 626 + } \ 627 + } 628 + 629 + /* Specify the machine mode that this machine uses 630 + for the index in the tablejump instruction. */ 631 + #define CASE_VECTOR_MODE SImode 632 + 633 + /* 'char' is signed by default. */ 634 + #define DEFAULT_SIGNED_CHAR 0 635 + 636 + #undef SIZE_TYPE 637 + #define SIZE_TYPE "unsigned int" 638 + 639 + #undef PTRDIFF_TYPE 640 + #define PTRDIFF_TYPE "int" 641 + 642 + #undef WCHAR_TYPE 643 + #define WCHAR_TYPE "long int" 644 + 645 + #undef WCHAR_TYPE_SIZE 646 + #define WCHAR_TYPE_SIZE BITS_PER_WORD 647 + 648 + /* Max number of bytes we can move from memory to memory 649 + in one reasonably fast instruction. */ 650 + #define MOVE_MAX 4 651 + 652 + /* Define if operations between registers always perform the operation 653 + on the full register even if a narrower mode is specified. */ 654 + #define WORD_REGISTER_OPERATIONS 655 + 656 + /* Define if loading in MODE, an integral mode narrower than BITS_PER_WORD 657 + will either zero-extend or sign-extend. The value of this macro should 658 + be the code that says which one of the two operations is implicitly 659 + done, UNKNOWN if none. */ 660 + #define LOAD_EXTEND_OP(MODE) ZERO_EXTEND 661 + 662 + /* Nonzero if access to memory by bytes is slow and undesirable. */ 663 + #define SLOW_BYTE_ACCESS TARGET_SLOW_BYTES 664 + 665 + /* Shift counts are truncated to 6-bits (0 to 63) instead of the expected 666 + 5-bits, so we can not define SHIFT_COUNT_TRUNCATED to true for this 667 + target. */ 668 + #define SHIFT_COUNT_TRUNCATED 0 669 + 670 + /* All integers have the same format so truncation is easy. */ 671 + #define TRULY_NOOP_TRUNCATION(OUTPREC,INPREC) 1 672 + 673 + /* Define this if addresses of constant functions 674 + shouldn't be put through pseudo regs where they can be cse'd. 675 + Desirable on machines where ordinary constants are expensive 676 + but a CALL with constant address is cheap. */ 677 + /* Why is this defined??? -- dac */ 678 + #define NO_FUNCTION_CSE 1 679 + 680 + /* The machine modes of pointers and functions. */ 681 + #define Pmode SImode 682 + #define FUNCTION_MODE Pmode 683 + 684 + /* Compute extra cost of moving data between one register class 685 + and another. All register moves are cheap. */ 686 + #define REGISTER_MOVE_COST(MODE, SRCCLASS, DSTCLASS) 2 687 + 688 + #define WORD_REGISTER_OPERATIONS 689 + 690 + /* Assembler output control. */ 691 + #define ASM_COMMENT_START "\t//" 692 + 693 + #define ASM_APP_ON "// inline asm begin\n" 694 + #define ASM_APP_OFF "// inline asm end\n" 695 + 696 + #define FILE_ASM_OP "\t.file\n" 697 + 698 + /* Switch to the text or data segment. */ 699 + #define TEXT_SECTION_ASM_OP "\t.text" 700 + #define DATA_SECTION_ASM_OP "\t.data" 701 + 702 + /* Switch into a generic section. */ 703 + #undef TARGET_ASM_NAMED_SECTION 704 + #define TARGET_ASM_NAMED_SECTION mcore_asm_named_section 705 + 706 + #define INCOMING_RETURN_ADDR_RTX gen_rtx_REG (SImode, LK_REG) 707 + 708 + /* This is how to output an insn to push a register on the stack. 709 + It need not be very fast code. */ 710 + #define ASM_OUTPUT_REG_PUSH(FILE,REGNO) \ 711 + fprintf (FILE, "\tsubi\t %s,%d\n\tstw\t %s,(%s)\n", \ 712 + reg_names[STACK_POINTER_REGNUM], \ 713 + (STACK_BOUNDARY / BITS_PER_UNIT), \ 714 + reg_names[REGNO], \ 715 + reg_names[STACK_POINTER_REGNUM]) 716 + 717 + /* Length in instructions of the code output by ASM_OUTPUT_REG_PUSH. */ 718 + #define REG_PUSH_LENGTH 2 719 + 720 + /* This is how to output an insn to pop a register from the stack. */ 721 + #define ASM_OUTPUT_REG_POP(FILE,REGNO) \ 722 + fprintf (FILE, "\tldw\t %s,(%s)\n\taddi\t %s,%d\n", \ 723 + reg_names[REGNO], \ 724 + reg_names[STACK_POINTER_REGNUM], \ 725 + reg_names[STACK_POINTER_REGNUM], \ 726 + (STACK_BOUNDARY / BITS_PER_UNIT)) 727 + 728 + 729 + /* Output a reference to a label. */ 730 + #undef ASM_OUTPUT_LABELREF 731 + #define ASM_OUTPUT_LABELREF(STREAM, NAME) \ 732 + fprintf (STREAM, "%s%s", USER_LABEL_PREFIX, \ 733 + (* targetm.strip_name_encoding) (NAME)) 734 + 735 + /* This is how to output an assembler line 736 + that says to advance the location counter 737 + to a multiple of 2**LOG bytes. */ 738 + #define ASM_OUTPUT_ALIGN(FILE,LOG) \ 739 + if ((LOG) != 0) \ 740 + fprintf (FILE, "\t.align\t%d\n", LOG) 741 + 742 + #ifndef ASM_DECLARE_RESULT 743 + #define ASM_DECLARE_RESULT(FILE, RESULT) 744 + #endif 745 + 746 + #define MULTIPLE_SYMBOL_SPACES 1 747 + 748 + #define SUPPORTS_ONE_ONLY 1 749 + 750 + /* A pair of macros to output things for the callgraph data. 751 + VALUE means (to the tools that reads this info later): 752 + 0 a call from src to dst 753 + 1 the call is special (e.g. dst is "unknown" or "alloca") 754 + 2 the call is special (e.g., the src is a table instead of routine) 755 + 756 + Frame sizes are augmented with timestamps to help later tools 757 + differentiate between static entities with same names in different 758 + files. */ 759 + extern long mcore_current_compilation_timestamp; 760 + #define ASM_OUTPUT_CG_NODE(FILE,SRCNAME,VALUE) \ 761 + do \ 762 + { \ 763 + if (mcore_current_compilation_timestamp == 0) \ 764 + mcore_current_compilation_timestamp = time (0); \ 765 + fprintf ((FILE),"\t.equ\t__$frame$size$_%s_$_%08lx,%d\n", \ 766 + (SRCNAME), mcore_current_compilation_timestamp, (VALUE)); \ 767 + } \ 768 + while (0) 769 + 770 + #define ASM_OUTPUT_CG_EDGE(FILE,SRCNAME,DSTNAME,VALUE) \ 771 + do \ 772 + { \ 773 + fprintf ((FILE),"\t.equ\t__$function$call$_%s_$_%s,%d\n", \ 774 + (SRCNAME), (DSTNAME), (VALUE)); \ 775 + } \ 776 + while (0) 777 + 778 + /* Globalizing directive for a label. */ 779 + #define GLOBAL_ASM_OP "\t.export\t" 780 + 781 + /* The prefix to add to user-visible assembler symbols. */ 782 + #undef USER_LABEL_PREFIX 783 + #define USER_LABEL_PREFIX "" 784 + 785 + /* Make an internal label into a string. */ 786 + #undef ASM_GENERATE_INTERNAL_LABEL 787 + #define ASM_GENERATE_INTERNAL_LABEL(STRING, PREFIX, NUM) \ 788 + sprintf (STRING, "*.%s%ld", PREFIX, (long) NUM) 789 + 790 + /* Jump tables must be 32 bit aligned. */ 791 + #undef ASM_OUTPUT_CASE_LABEL 792 + #define ASM_OUTPUT_CASE_LABEL(STREAM,PREFIX,NUM,TABLE) \ 793 + fprintf (STREAM, "\t.align 2\n.%s%d:\n", PREFIX, NUM); 794 + 795 + /* Output a relative address. Not needed since jump tables are absolute 796 + but we must define it anyway. */ 797 + #define ASM_OUTPUT_ADDR_DIFF_ELT(STREAM,BODY,VALUE,REL) \ 798 + fputs ("- - - ASM_OUTPUT_ADDR_DIFF_ELT called!\n", STREAM) 799 + 800 + /* Output an element of a dispatch table. */ 801 + #define ASM_OUTPUT_ADDR_VEC_ELT(STREAM,VALUE) \ 802 + fprintf (STREAM, "\t.long\t.L%d\n", VALUE) 803 + 804 + /* Output various types of constants. */ 805 + 806 + /* This is how to output an assembler line 807 + that says to advance the location counter by SIZE bytes. */ 808 + #undef ASM_OUTPUT_SKIP 809 + #define ASM_OUTPUT_SKIP(FILE,SIZE) \ 810 + fprintf (FILE, "\t.fill %d, 1\n", (int)(SIZE)) 811 + 812 + /* This says how to output an assembler line 813 + to define a global common symbol, with alignment information. */ 814 + /* XXX - for now we ignore the alignment. */ 815 + #undef ASM_OUTPUT_ALIGNED_COMMON 816 + #define ASM_OUTPUT_ALIGNED_COMMON(FILE, NAME, SIZE, ALIGN) \ 817 + do \ 818 + { \ 819 + if (mcore_dllexport_name_p (NAME)) \ 820 + MCORE_EXPORT_NAME (FILE, NAME) \ 821 + if (! mcore_dllimport_name_p (NAME)) \ 822 + { \ 823 + fputs ("\t.comm\t", FILE); \ 824 + assemble_name (FILE, NAME); \ 825 + fprintf (FILE, ",%lu\n", (unsigned long)(SIZE)); \ 826 + } \ 827 + } \ 828 + while (0) 829 + 830 + /* This says how to output an assembler line 831 + to define a local common symbol.... */ 832 + #undef ASM_OUTPUT_LOCAL 833 + #define ASM_OUTPUT_LOCAL(FILE, NAME, SIZE, ROUNDED) \ 834 + (fputs ("\t.lcomm\t", FILE), \ 835 + assemble_name (FILE, NAME), \ 836 + fprintf (FILE, ",%d\n", (int)SIZE)) 837 + 838 + /* ... and how to define a local common symbol whose alignment 839 + we wish to specify. ALIGN comes in as bits, we have to turn 840 + it into bytes. */ 841 + #undef ASM_OUTPUT_ALIGNED_LOCAL 842 + #define ASM_OUTPUT_ALIGNED_LOCAL(FILE, NAME, SIZE, ALIGN) \ 843 + do \ 844 + { \ 845 + fputs ("\t.bss\t", (FILE)); \ 846 + assemble_name ((FILE), (NAME)); \ 847 + fprintf ((FILE), ",%d,%d\n", (int)(SIZE), (ALIGN) / BITS_PER_UNIT);\ 848 + } \ 849 + while (0) 850 + 851 + #endif /* ! GCC_MCORE_H */
+29
src/libunwind-darwin/tconfig.h
··· 1 + #define ATTRIBUTE_UNUSED 2 + #include <stdlib.h> 3 + #include <string.h> 4 + #include "mcore.h" 5 + #define SHARED 6 + 7 + 8 + #if 0 9 + #define _Unwind_GetTextRelBase __darwin__Unwind_GetTextRelBase 10 + #define _Unwind_GetDataRelBase __darwin__Unwind_GetDataRelBase 11 + #define _Unwind_GetRegionStart __darwin__Unwind_GetRegionStart 12 + #define _Unwind_GetGR __darwin__Unwind_GetGR 13 + #define _Unwind_GetCFA __darwin__Unwind_GetCFA 14 + #define _Unwind_SetGR __darwin__Unwind_SetGR 15 + #define _Unwind_GetIP __darwin__Unwind_GetIP 16 + #define _Unwind_GetIPInfo __darwin__Unwind_GetIPInfo 17 + #define _Unwind_SetIP __darwin__Unwind_SetIP 18 + #define _Unwind_GetLanguageSpecificData __darwin__Unwind_GetLanguageSpecificData 19 + #define _Unwind_FindEnclosingFunction __darwin__Unwind_FindEnclosingFunction 20 + #define _Unwind_Find_FDE __darwin__Unwind_Find_FDE 21 + #define _Unwind_RaiseException __darwin__Unwind_RaiseException 22 + #define _Unwind_ForcedUnwind __darwin__Unwind_ForcedUnwind 23 + #define _Unwind_Resume __darwin__Unwind_Resume 24 + #define _Unwind_Resume_or_Rethrow __darwin__Unwind_Resume_or_Rethrow 25 + #define _Unwind_DeleteException __darwin__Unwind_DeleteException 26 + #define _Unwind_Backtrace __darwin__Unwind_Backtrace 27 + #define _Unwind_Find_FDE __darwin__Unwind_Find_FDE 28 + 29 + #endif
+39
src/libunwind-darwin/tm.h
··· 1 + #ifndef GCC_TM_H 2 + #define GCC_TM_H 3 + #ifndef LIBC_GLIBC 4 + # define LIBC_GLIBC 1 5 + #endif 6 + #ifndef LIBC_UCLIBC 7 + # define LIBC_UCLIBC 2 8 + #endif 9 + #ifndef LIBC_BIONIC 10 + # define LIBC_BIONIC 3 11 + #endif 12 + #ifndef DEFAULT_LIBC 13 + # define DEFAULT_LIBC LIBC_GLIBC 14 + #endif 15 + #ifndef ANDROID_DEFAULT 16 + # define ANDROID_DEFAULT 0 17 + #endif 18 + #ifdef IN_GCC 19 + # include "options.h" 20 + # include "insn-constants.h" 21 + # include "config/vxworks-dummy.h" 22 + # include "config/i386/biarch64.h" 23 + # include "config/i386/i386.h" 24 + # include "config/linux-android.h" 25 + # include "config/i386/unix.h" 26 + # include "config/i386/att.h" 27 + # include "config/dbxelf.h" 28 + # include "config/elfos.h" 29 + # include "config/gnu-user.h" 30 + # include "config/linux.h" 31 + # include "config/glibc-stdint.h" 32 + # include "config/i386/x86-64.h" 33 + # include "config/i386/linux64.h" 34 + #endif 35 + #if defined IN_GCC && !defined GENERATOR_FILE && !defined USED_FOR_TARGET 36 + # include "insn-flags.h" 37 + #endif 38 + # include "defaults.h" 39 + #endif /* GCC_TM_H */
src/libunwind-darwin/tsystem.h

This is a binary file and will not be displayed.

+229
src/libunwind-darwin/unwind-c.c
··· 1 + /* Supporting functions for C exception handling. 2 + Copyright (C) 2002, 2003, 2009 Free Software Foundation, Inc. 3 + Contributed by Aldy Hernandez <aldy@quesejoda.com>. 4 + Shamelessly stolen from the Java front end. 5 + 6 + This file is part of GCC. 7 + 8 + GCC is free software; you can redistribute it and/or modify it under 9 + the terms of the GNU General Public License as published by the Free 10 + Software Foundation; either version 3, or (at your option) any later 11 + version. 12 + 13 + GCC is distributed in the hope that it will be useful, but WITHOUT ANY 14 + WARRANTY; without even the implied warranty of MERCHANTABILITY or 15 + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16 + for more details. 17 + 18 + Under Section 7 of GPL version 3, you are granted additional 19 + permissions described in the GCC Runtime Library Exception, version 20 + 3.1, as published by the Free Software Foundation. 21 + 22 + You should have received a copy of the GNU General Public License and 23 + a copy of the GCC Runtime Library Exception along with this program; 24 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 25 + <http://www.gnu.org/licenses/>. */ 26 + 27 + #include "tconfig.h" 28 + #include "tsystem.h" 29 + #include "unwind.h" 30 + #define NO_SIZE_OF_ENCODED_VALUE 31 + #include "unwind-pe.h" 32 + 33 + typedef struct 34 + { 35 + _Unwind_Ptr Start; 36 + _Unwind_Ptr LPStart; 37 + _Unwind_Ptr ttype_base; 38 + const unsigned char *TType; 39 + const unsigned char *action_table; 40 + unsigned char ttype_encoding; 41 + unsigned char call_site_encoding; 42 + } lsda_header_info; 43 + 44 + static const unsigned char * 45 + parse_lsda_header (struct _Unwind_Context *context, const unsigned char *p, 46 + lsda_header_info *info) 47 + { 48 + _uleb128_t tmp; 49 + unsigned char lpstart_encoding; 50 + 51 + info->Start = (context ? _Unwind_GetRegionStart (context) : 0); 52 + 53 + /* Find @LPStart, the base to which landing pad offsets are relative. */ 54 + lpstart_encoding = *p++; 55 + if (lpstart_encoding != DW_EH_PE_omit) 56 + p = read_encoded_value (context, lpstart_encoding, p, &info->LPStart); 57 + else 58 + info->LPStart = info->Start; 59 + 60 + /* Find @TType, the base of the handler and exception spec type data. */ 61 + info->ttype_encoding = *p++; 62 + if (info->ttype_encoding != DW_EH_PE_omit) 63 + { 64 + p = read_uleb128 (p, &tmp); 65 + info->TType = p + tmp; 66 + } 67 + else 68 + info->TType = 0; 69 + 70 + /* The encoding and length of the call-site table; the action table 71 + immediately follows. */ 72 + info->call_site_encoding = *p++; 73 + p = read_uleb128 (p, &tmp); 74 + info->action_table = p + tmp; 75 + 76 + return p; 77 + } 78 + 79 + #ifdef __ARM_EABI_UNWINDER__ 80 + /* ARM EABI personality routines must also unwind the stack. */ 81 + #define CONTINUE_UNWINDING \ 82 + do \ 83 + { \ 84 + if (__gnu_unwind_frame (ue_header, context) != _URC_OK) \ 85 + return _URC_FAILURE; \ 86 + return _URC_CONTINUE_UNWIND; \ 87 + } \ 88 + while (0) 89 + #else 90 + #define CONTINUE_UNWINDING return _URC_CONTINUE_UNWIND 91 + #endif 92 + 93 + #ifdef __USING_SJLJ_EXCEPTIONS__ 94 + #define PERSONALITY_FUNCTION __gcc_personality_sj0 95 + #define __builtin_eh_return_data_regno(x) x 96 + #else 97 + #define PERSONALITY_FUNCTION __gcc_personality_v0 98 + #endif 99 + 100 + #ifdef __ARM_EABI_UNWINDER__ 101 + _Unwind_Reason_Code 102 + PERSONALITY_FUNCTION (_Unwind_State, struct _Unwind_Exception *, 103 + struct _Unwind_Context *); 104 + 105 + _Unwind_Reason_Code 106 + PERSONALITY_FUNCTION (_Unwind_State state, 107 + struct _Unwind_Exception * ue_header, 108 + struct _Unwind_Context * context) 109 + #else 110 + _Unwind_Reason_Code 111 + PERSONALITY_FUNCTION (int, _Unwind_Action, _Unwind_Exception_Class, 112 + struct _Unwind_Exception *, struct _Unwind_Context *); 113 + 114 + _Unwind_Reason_Code 115 + PERSONALITY_FUNCTION (int version, 116 + _Unwind_Action actions, 117 + _Unwind_Exception_Class exception_class ATTRIBUTE_UNUSED, 118 + struct _Unwind_Exception *ue_header, 119 + struct _Unwind_Context *context) 120 + #endif 121 + { 122 + lsda_header_info info; 123 + const unsigned char *language_specific_data, *p; 124 + _Unwind_Ptr landing_pad, ip; 125 + int ip_before_insn = 0; 126 + 127 + #ifdef __ARM_EABI_UNWINDER__ 128 + if ((state & _US_ACTION_MASK) != _US_UNWIND_FRAME_STARTING) 129 + CONTINUE_UNWINDING; 130 + 131 + /* The dwarf unwinder assumes the context structure holds things like the 132 + function and LSDA pointers. The ARM implementation caches these in 133 + the exception header (UCB). To avoid rewriting everything we make the 134 + virtual IP register point at the UCB. */ 135 + ip = (_Unwind_Ptr) ue_header; 136 + _Unwind_SetGR (context, 12, ip); 137 + #else 138 + if (version != 1) 139 + return _URC_FATAL_PHASE1_ERROR; 140 + 141 + /* Currently we only support cleanups for C. */ 142 + if ((actions & _UA_CLEANUP_PHASE) == 0) 143 + CONTINUE_UNWINDING; 144 + #endif 145 + 146 + language_specific_data = (const unsigned char *) 147 + _Unwind_GetLanguageSpecificData (context); 148 + 149 + /* If no LSDA, then there are no handlers or cleanups. */ 150 + if (! language_specific_data) 151 + CONTINUE_UNWINDING; 152 + 153 + /* Parse the LSDA header. */ 154 + p = parse_lsda_header (context, language_specific_data, &info); 155 + #ifdef HAVE_GETIPINFO 156 + ip = _Unwind_GetIPInfo (context, &ip_before_insn); 157 + #else 158 + ip = _Unwind_GetIP (context); 159 + #endif 160 + if (! ip_before_insn) 161 + --ip; 162 + landing_pad = 0; 163 + 164 + #ifdef __USING_SJLJ_EXCEPTIONS__ 165 + /* The given "IP" is an index into the call-site table, with two 166 + exceptions -- -1 means no-action, and 0 means terminate. But 167 + since we're using uleb128 values, we've not got random access 168 + to the array. */ 169 + if ((int) ip <= 0) 170 + return _URC_CONTINUE_UNWIND; 171 + else 172 + { 173 + _uleb128_t cs_lp, cs_action; 174 + do 175 + { 176 + p = read_uleb128 (p, &cs_lp); 177 + p = read_uleb128 (p, &cs_action); 178 + } 179 + while (--ip); 180 + 181 + /* Can never have null landing pad for sjlj -- that would have 182 + been indicated by a -1 call site index. */ 183 + landing_pad = (_Unwind_Ptr)cs_lp + 1; 184 + goto found_something; 185 + } 186 + #else 187 + /* Search the call-site table for the action associated with this IP. */ 188 + while (p < info.action_table) 189 + { 190 + _Unwind_Ptr cs_start, cs_len, cs_lp; 191 + _uleb128_t cs_action; 192 + 193 + /* Note that all call-site encodings are "absolute" displacements. */ 194 + p = read_encoded_value (0, info.call_site_encoding, p, &cs_start); 195 + p = read_encoded_value (0, info.call_site_encoding, p, &cs_len); 196 + p = read_encoded_value (0, info.call_site_encoding, p, &cs_lp); 197 + p = read_uleb128 (p, &cs_action); 198 + 199 + /* The table is sorted, so if we've passed the ip, stop. */ 200 + if (ip < info.Start + cs_start) 201 + p = info.action_table; 202 + else if (ip < info.Start + cs_start + cs_len) 203 + { 204 + if (cs_lp) 205 + landing_pad = info.LPStart + cs_lp; 206 + goto found_something; 207 + } 208 + } 209 + #endif 210 + 211 + /* IP is not in table. No associated cleanups. */ 212 + /* ??? This is where C++ calls std::terminate to catch throw 213 + from a destructor. */ 214 + CONTINUE_UNWINDING; 215 + 216 + found_something: 217 + if (landing_pad == 0) 218 + { 219 + /* IP is present, but has a null landing pad. 220 + No handler to be run. */ 221 + CONTINUE_UNWINDING; 222 + } 223 + 224 + _Unwind_SetGR (context, __builtin_eh_return_data_regno (0), 225 + (_Unwind_Ptr) ue_header); 226 + _Unwind_SetGR (context, __builtin_eh_return_data_regno (1), 0); 227 + _Unwind_SetIP (context, landing_pad); 228 + return _URC_INSTALL_CONTEXT; 229 + }
+210
src/libunwind-darwin/unwind-compat.c
··· 1 + /* Backward compatibility unwind routines. 2 + Copyright (C) 2004, 2005, 2006, 2009 3 + Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #if defined (USE_GAS_SYMVER) && defined (USE_LIBUNWIND_EXCEPTIONS) 27 + #include "tconfig.h" 28 + #include "tsystem.h" 29 + #include "unwind.h" 30 + #include "unwind-dw2-fde.h" 31 + #include "unwind-compat.h" 32 + 33 + extern _Unwind_Reason_Code __libunwind_Unwind_Backtrace 34 + (_Unwind_Trace_Fn, void *); 35 + 36 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 37 + _Unwind_Backtrace (_Unwind_Trace_Fn trace, void *trace_argument) 38 + { 39 + return __libunwind_Unwind_Backtrace (trace, trace_argument); 40 + } 41 + symver (_Unwind_Backtrace, GCC_3.3); 42 + 43 + extern void __libunwind_Unwind_DeleteException 44 + (struct _Unwind_Exception *); 45 + 46 + void 47 + _Unwind_DeleteException (struct _Unwind_Exception *exc) 48 + { 49 + return __libunwind_Unwind_DeleteException (exc); 50 + } 51 + symver (_Unwind_DeleteException, GCC_3.0); 52 + 53 + extern void * __libunwind_Unwind_FindEnclosingFunction (void *); 54 + 55 + void * 56 + _Unwind_FindEnclosingFunction (void *pc) 57 + { 58 + return __libunwind_Unwind_FindEnclosingFunction (pc); 59 + } 60 + symver (_Unwind_FindEnclosingFunction, GCC_3.3); 61 + 62 + extern _Unwind_Reason_Code __libunwind_Unwind_ForcedUnwind 63 + (struct _Unwind_Exception *, _Unwind_Stop_Fn, void *); 64 + 65 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 66 + _Unwind_ForcedUnwind (struct _Unwind_Exception *exc, 67 + _Unwind_Stop_Fn stop, void * stop_argument) 68 + { 69 + return __libunwind_Unwind_ForcedUnwind (exc, stop, stop_argument); 70 + } 71 + symver (_Unwind_ForcedUnwind, GCC_3.0); 72 + 73 + extern _Unwind_Word __libunwind_Unwind_GetCFA 74 + (struct _Unwind_Context *); 75 + 76 + _Unwind_Word 77 + _Unwind_GetCFA (struct _Unwind_Context *context) 78 + { 79 + return __libunwind_Unwind_GetCFA (context); 80 + } 81 + symver (_Unwind_GetCFA, GCC_3.3); 82 + 83 + #ifdef __ia64__ 84 + extern _Unwind_Word __libunwind_Unwind_GetBSP 85 + (struct _Unwind_Context *); 86 + 87 + _Unwind_Word 88 + _Unwind_GetBSP (struct _Unwind_Context * context) 89 + { 90 + return __libunwind_Unwind_GetBSP (context); 91 + } 92 + symver (_Unwind_GetBSP, GCC_3.3.2); 93 + #else 94 + extern _Unwind_Ptr __libunwind_Unwind_GetDataRelBase 95 + (struct _Unwind_Context *); 96 + 97 + _Unwind_Ptr 98 + _Unwind_GetDataRelBase (struct _Unwind_Context *context) 99 + { 100 + return __libunwind_Unwind_GetDataRelBase (context); 101 + } 102 + symver (_Unwind_GetDataRelBase, GCC_3.0); 103 + 104 + extern _Unwind_Ptr __libunwind_Unwind_GetTextRelBase 105 + (struct _Unwind_Context *); 106 + 107 + _Unwind_Ptr 108 + _Unwind_GetTextRelBase (struct _Unwind_Context *context) 109 + { 110 + return __libunwind_Unwind_GetTextRelBase (context); 111 + } 112 + symver (_Unwind_GetTextRelBase, GCC_3.0); 113 + #endif 114 + 115 + extern _Unwind_Word __libunwind_Unwind_GetGR 116 + (struct _Unwind_Context *, int ); 117 + 118 + _Unwind_Word 119 + _Unwind_GetGR (struct _Unwind_Context *context, int index) 120 + { 121 + return __libunwind_Unwind_GetGR (context, index); 122 + } 123 + symver (_Unwind_GetGR, GCC_3.0); 124 + 125 + extern _Unwind_Ptr __libunwind_Unwind_GetIP (struct _Unwind_Context *); 126 + 127 + _Unwind_Ptr 128 + _Unwind_GetIP (struct _Unwind_Context *context) 129 + { 130 + return __libunwind_Unwind_GetIP (context); 131 + } 132 + symver (_Unwind_GetIP, GCC_3.0); 133 + 134 + _Unwind_Ptr 135 + _Unwind_GetIPInfo (struct _Unwind_Context *context, int *ip_before_insn) 136 + { 137 + *ip_before_insn = 0; 138 + return __libunwind_Unwind_GetIP (context); 139 + } 140 + 141 + extern void *__libunwind_Unwind_GetLanguageSpecificData 142 + (struct _Unwind_Context *); 143 + 144 + void * 145 + _Unwind_GetLanguageSpecificData (struct _Unwind_Context *context) 146 + { 147 + return __libunwind_Unwind_GetLanguageSpecificData (context); 148 + } 149 + symver (_Unwind_GetLanguageSpecificData, GCC_3.0); 150 + 151 + extern _Unwind_Ptr __libunwind_Unwind_GetRegionStart 152 + (struct _Unwind_Context *); 153 + 154 + _Unwind_Ptr 155 + _Unwind_GetRegionStart (struct _Unwind_Context *context) 156 + { 157 + return __libunwind_Unwind_GetRegionStart (context); 158 + } 159 + symver (_Unwind_GetRegionStart, GCC_3.0); 160 + 161 + extern _Unwind_Reason_Code __libunwind_Unwind_RaiseException 162 + (struct _Unwind_Exception *); 163 + 164 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 165 + _Unwind_RaiseException(struct _Unwind_Exception *exc) 166 + { 167 + return __libunwind_Unwind_RaiseException (exc); 168 + } 169 + symver (_Unwind_RaiseException, GCC_3.0); 170 + 171 + extern void __libunwind_Unwind_Resume (struct _Unwind_Exception *); 172 + 173 + void LIBGCC2_UNWIND_ATTRIBUTE 174 + _Unwind_Resume (struct _Unwind_Exception *exc) 175 + { 176 + __libunwind_Unwind_Resume (exc); 177 + } 178 + symver (_Unwind_Resume, GCC_3.0); 179 + 180 + extern _Unwind_Reason_Code __libunwind_Unwind_Resume_or_Rethrow 181 + (struct _Unwind_Exception *); 182 + 183 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 184 + _Unwind_Resume_or_Rethrow (struct _Unwind_Exception *exc) 185 + { 186 + return __libunwind_Unwind_Resume_or_Rethrow (exc); 187 + } 188 + symver (_Unwind_Resume_or_Rethrow, GCC_3.3); 189 + 190 + extern void __libunwind_Unwind_SetGR 191 + (struct _Unwind_Context *, int, _Unwind_Word); 192 + 193 + void 194 + _Unwind_SetGR (struct _Unwind_Context *context, int index, 195 + _Unwind_Word val) 196 + { 197 + __libunwind_Unwind_SetGR (context, index, val); 198 + } 199 + symver (_Unwind_SetGR, GCC_3.0); 200 + 201 + extern void __libunwind_Unwind_SetIP 202 + (struct _Unwind_Context *, _Unwind_Ptr); 203 + 204 + void 205 + _Unwind_SetIP (struct _Unwind_Context *context, _Unwind_Ptr val) 206 + { 207 + return __libunwind_Unwind_SetIP (context, val); 208 + } 209 + symver (_Unwind_SetIP, GCC_3.0); 210 + #endif
+30
src/libunwind-darwin/unwind-compat.h
··· 1 + /* Backward compatibility unwind routines. 2 + Copyright (C) 2004, 2009 3 + Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #define symver(name, version) \ 27 + __asm__ (".symver " #name"," #name "@" #version) 28 + 29 + #define alias(name) \ 30 + __typeof(name) __libunwind##name __attribute__ ((alias (#name)))
+43
src/libunwind-darwin/unwind-dw2-fde-compat.c
··· 1 + /* Backward compatibility unwind routines. 2 + Copyright (C) 2004, 2005, 2009 3 + Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #if defined (USE_GAS_SYMVER) && defined (USE_LIBUNWIND_EXCEPTIONS) 27 + #include "tconfig.h" 28 + #include "tsystem.h" 29 + #include "unwind.h" 30 + #include "unwind-dw2-fde.h" 31 + #include "unwind-compat.h" 32 + 33 + extern const fde * __libunwind__Unwind_Find_FDE 34 + (void *, struct dwarf_eh_bases *); 35 + 36 + const fde * 37 + _Unwind_Find_FDE (void *pc, struct dwarf_eh_bases *bases) 38 + { 39 + __libunwind__Unwind_Find_FDE (pc, bases); 40 + } 41 + 42 + symver (_Unwind_Find_FDE, GCC_3.0); 43 + #endif
+289
src/libunwind-darwin/unwind-dw2-fde-darwin.c
··· 1 + /* Copyright (C) 2001, 2002, 2003, 2005, 2009, 2010 2 + Free Software Foundation, Inc. 3 + 4 + This file is part of GCC. 5 + 6 + GCC is free software; you can redistribute it and/or modify 7 + it under the terms of the GNU General Public License as published by 8 + the Free Software Foundation; either version 3, or (at your option) 9 + any later version. 10 + 11 + GCC is distributed in the hope that it will be useful, 12 + but WITHOUT ANY WARRANTY; without even the implied warranty of 13 + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 + GNU General Public License for more details. 15 + 16 + Under Section 7 of GPL version 3, you are granted additional 17 + permissions described in the GCC Runtime Library Exception, version 18 + 3.1, as published by the Free Software Foundation. 19 + 20 + You should have received a copy of the GNU General Public License and 21 + a copy of the GCC Runtime Library Exception along with this program; 22 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 + <http://www.gnu.org/licenses/>. */ 24 + 25 + /* Locate the FDE entry for a given address, using Darwin's keymgr support. */ 26 + 27 + #include "tconfig.h" 28 + #include "tsystem.h" 29 + #include <string.h> 30 + #include <stdlib.h> 31 + #include "dwarf2.h" 32 + #include "unwind.h" 33 + #define NO_BASE_OF_ENCODED_VALUE 34 + #define DWARF2_OBJECT_END_PTR_EXTENSION 35 + #include "unwind-pe.h" 36 + #include "unwind-dw2-fde.h" 37 + /* Carefully don't include gthr.h. */ 38 + 39 + typedef int __gthread_mutex_t; 40 + #define __gthread_mutex_lock(x) (void)(x) 41 + #define __gthread_mutex_unlock(x) (void)(x) 42 + 43 + static const fde * _Unwind_Find_registered_FDE (void *pc, 44 + struct dwarf_eh_bases *bases); 45 + 46 + #define _Unwind_Find_FDE _Unwind_Find_registered_FDE 47 + #include "unwind-dw2-fde.c" 48 + #undef _Unwind_Find_FDE 49 + 50 + /* KeyMgr stuff. */ 51 + #define KEYMGR_GCC3_LIVE_IMAGE_LIST 301 /* loaded images */ 52 + #define KEYMGR_GCC3_DW2_OBJ_LIST 302 /* Dwarf2 object list */ 53 + 54 + extern void *_keymgr_get_and_lock_processwide_ptr (int); 55 + extern void _keymgr_set_and_unlock_processwide_ptr (int, void *); 56 + extern void _keymgr_unlock_processwide_ptr (int); 57 + 58 + struct mach_header; 59 + struct mach_header_64; 60 + extern char *getsectdatafromheader (struct mach_header*, const char*, 61 + const char *, unsigned long *); 62 + extern char *getsectdatafromheader_64 (struct mach_header_64*, const char*, 63 + const char *, unsigned long *); 64 + 65 + /* This is referenced from KEYMGR_GCC3_DW2_OBJ_LIST. */ 66 + struct km_object_info { 67 + struct object *seen_objects; 68 + struct object *unseen_objects; 69 + unsigned spare[2]; 70 + }; 71 + 72 + /* Node of KEYMGR_GCC3_LIVE_IMAGE_LIST. Info about each resident image. */ 73 + struct live_images { 74 + unsigned long this_size; /* sizeof (live_images) */ 75 + struct mach_header *mh; /* the image info */ 76 + unsigned long vm_slide; 77 + void (*destructor)(struct live_images *); /* destructor for this */ 78 + struct live_images *next; 79 + unsigned int examined_p; 80 + void *fde; 81 + void *object_info; 82 + unsigned long info[2]; /* Future use. */ 83 + }; 84 + 85 + /* Bits in the examined_p field of struct live_images. */ 86 + enum { 87 + EXAMINED_IMAGE_MASK = 1, /* We've seen this one. */ 88 + ALLOCED_IMAGE_MASK = 2, /* The FDE entries were allocated by 89 + malloc, and must be freed. This isn't 90 + used by newer libgcc versions. */ 91 + IMAGE_IS_TEXT_MASK = 4, /* This image is in the TEXT segment. */ 92 + DESTRUCTOR_MAY_BE_CALLED_LIVE = 8 /* The destructor may be called on an 93 + object that's part of the live 94 + image list. */ 95 + }; 96 + 97 + /* Delete any data we allocated on a live_images structure. Either 98 + IMAGE has already been removed from the 99 + KEYMGR_GCC3_LIVE_IMAGE_LIST and the struct will be deleted 100 + after we return, or that list is locked and we're being called 101 + because this object might be about to be unloaded. Called by 102 + KeyMgr. */ 103 + 104 + static void 105 + live_image_destructor (struct live_images *image) 106 + { 107 + if (image->object_info) 108 + { 109 + struct km_object_info *the_obj_info; 110 + 111 + the_obj_info = 112 + _keymgr_get_and_lock_processwide_ptr (KEYMGR_GCC3_DW2_OBJ_LIST); 113 + if (the_obj_info) 114 + { 115 + seen_objects = the_obj_info->seen_objects; 116 + unseen_objects = the_obj_info->unseen_objects; 117 + 118 + /* Free any sorted arrays. */ 119 + __deregister_frame_info_bases (image->fde); 120 + 121 + the_obj_info->seen_objects = seen_objects; 122 + the_obj_info->unseen_objects = unseen_objects; 123 + } 124 + _keymgr_set_and_unlock_processwide_ptr (KEYMGR_GCC3_DW2_OBJ_LIST, 125 + the_obj_info); 126 + 127 + free (image->object_info); 128 + image->object_info = NULL; 129 + if (image->examined_p & ALLOCED_IMAGE_MASK) 130 + free (image->fde); 131 + image->fde = NULL; 132 + } 133 + image->examined_p = 0; 134 + image->destructor = NULL; 135 + } 136 + 137 + /* Run through the list of live images. If we can allocate memory, 138 + give each unseen image a new `struct object'. Even if we can't, 139 + check whether the PC is inside the FDE of each unseen image. 140 + */ 141 + 142 + static inline const fde * 143 + examine_objects (void *pc, struct dwarf_eh_bases *bases, int dont_alloc) 144 + { 145 + const fde *result = NULL; 146 + struct live_images *image; 147 + 148 + image = _keymgr_get_and_lock_processwide_ptr (KEYMGR_GCC3_LIVE_IMAGE_LIST); 149 + 150 + for (; image != NULL; image = image->next) 151 + if ((image->examined_p & EXAMINED_IMAGE_MASK) == 0) 152 + { 153 + char *fde = NULL; 154 + unsigned long sz; 155 + 156 + /* For ppc only check whether or not we have __DATA eh frames. */ 157 + #ifdef __ppc__ 158 + fde = getsectdatafromheader (image->mh, "__DATA", "__eh_frame", &sz); 159 + #endif 160 + 161 + if (fde == NULL) 162 + { 163 + #if __LP64__ 164 + fde = getsectdatafromheader_64 ((struct mach_header_64 *) image->mh, 165 + "__TEXT", "__eh_frame", &sz); 166 + #else 167 + fde = getsectdatafromheader (image->mh, "__TEXT", 168 + "__eh_frame", &sz); 169 + #endif 170 + if (fde != NULL) 171 + image->examined_p |= IMAGE_IS_TEXT_MASK; 172 + } 173 + 174 + /* If .eh_frame is empty, don't register at all. */ 175 + if (fde != NULL && sz > 0) 176 + { 177 + char *real_fde = (fde + image->vm_slide); 178 + struct object *ob = NULL; 179 + struct object panicob; 180 + 181 + if (! dont_alloc) 182 + ob = calloc (1, sizeof (struct object)); 183 + dont_alloc |= ob == NULL; 184 + if (dont_alloc) 185 + ob = &panicob; 186 + 187 + ob->pc_begin = (void *)-1; 188 + ob->tbase = 0; 189 + ob->dbase = 0; 190 + ob->u.single = (struct dwarf_fde *)real_fde; 191 + ob->s.i = 0; 192 + ob->s.b.encoding = DW_EH_PE_omit; 193 + ob->fde_end = real_fde + sz; 194 + 195 + image->fde = real_fde; 196 + 197 + result = search_object (ob, pc); 198 + 199 + if (! dont_alloc) 200 + { 201 + struct object **p; 202 + 203 + image->destructor = live_image_destructor; 204 + image->object_info = ob; 205 + 206 + image->examined_p |= (EXAMINED_IMAGE_MASK 207 + | DESTRUCTOR_MAY_BE_CALLED_LIVE); 208 + 209 + /* Insert the object into the classified list. */ 210 + for (p = &seen_objects; *p ; p = &(*p)->next) 211 + if ((*p)->pc_begin < ob->pc_begin) 212 + break; 213 + ob->next = *p; 214 + *p = ob; 215 + } 216 + 217 + if (result) 218 + { 219 + int encoding; 220 + _Unwind_Ptr func; 221 + 222 + bases->tbase = ob->tbase; 223 + bases->dbase = ob->dbase; 224 + 225 + encoding = ob->s.b.encoding; 226 + if (ob->s.b.mixed_encoding) 227 + encoding = get_fde_encoding (result); 228 + read_encoded_value_with_base (encoding, 229 + base_from_object (encoding, ob), 230 + result->pc_begin, &func); 231 + bases->func = (void *) func; 232 + break; 233 + } 234 + } 235 + else 236 + image->examined_p |= EXAMINED_IMAGE_MASK; 237 + } 238 + 239 + _keymgr_unlock_processwide_ptr (KEYMGR_GCC3_LIVE_IMAGE_LIST); 240 + 241 + return result; 242 + } 243 + 244 + const fde * 245 + _Unwind_Find_FDE (void *pc, struct dwarf_eh_bases *bases) 246 + { 247 + struct km_object_info *the_obj_info; 248 + const fde *ret = NULL; 249 + 250 + the_obj_info = 251 + _keymgr_get_and_lock_processwide_ptr (KEYMGR_GCC3_DW2_OBJ_LIST); 252 + if (! the_obj_info) 253 + the_obj_info = calloc (1, sizeof (*the_obj_info)); 254 + 255 + if (the_obj_info != NULL) 256 + { 257 + seen_objects = the_obj_info->seen_objects; 258 + unseen_objects = the_obj_info->unseen_objects; 259 + 260 + ret = _Unwind_Find_registered_FDE (pc, bases); 261 + } 262 + 263 + /* OK, didn't find it in the list of FDEs we've seen before, 264 + so go through and look at the new ones. */ 265 + if (ret == NULL) 266 + ret = examine_objects (pc, bases, the_obj_info == NULL); 267 + 268 + if (the_obj_info != NULL) 269 + { 270 + the_obj_info->seen_objects = seen_objects; 271 + the_obj_info->unseen_objects = unseen_objects; 272 + } 273 + _keymgr_set_and_unlock_processwide_ptr (KEYMGR_GCC3_DW2_OBJ_LIST, 274 + the_obj_info); 275 + return ret; 276 + } 277 + 278 + void * 279 + _darwin10_Unwind_FindEnclosingFunction (void *pc ATTRIBUTE_UNUSED) 280 + { 281 + #if __MACH__ && (__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ >= 1060) 282 + struct dwarf_eh_bases bases; 283 + const struct dwarf_fde *fde = _Unwind_Find_FDE (pc-1, &bases); 284 + if (fde) 285 + return bases.func; 286 + #endif 287 + return NULL; 288 + } 289 +
+1054
src/libunwind-darwin/unwind-dw2-fde.c
··· 1 + /* Subroutines needed for unwinding stack frames for exception handling. */ 2 + /* Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2008, 3 + 2009, 2010 Free Software Foundation, Inc. 4 + Contributed by Jason Merrill <jason@cygnus.com>. 5 + 6 + This file is part of GCC. 7 + 8 + GCC is free software; you can redistribute it and/or modify it under 9 + the terms of the GNU General Public License as published by the Free 10 + Software Foundation; either version 3, or (at your option) any later 11 + version. 12 + 13 + GCC is distributed in the hope that it will be useful, but WITHOUT ANY 14 + WARRANTY; without even the implied warranty of MERCHANTABILITY or 15 + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16 + for more details. 17 + 18 + Under Section 7 of GPL version 3, you are granted additional 19 + permissions described in the GCC Runtime Library Exception, version 20 + 3.1, as published by the Free Software Foundation. 21 + 22 + You should have received a copy of the GNU General Public License and 23 + a copy of the GCC Runtime Library Exception along with this program; 24 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 25 + <http://www.gnu.org/licenses/>. */ 26 + 27 + #ifndef _Unwind_Find_FDE 28 + #include "tconfig.h" 29 + #include "tsystem.h" 30 + #include "coretypes.h" 31 + #include "tm.h" 32 + #include "dwarf2.h" 33 + #include "unwind.h" 34 + #define NO_BASE_OF_ENCODED_VALUE 35 + #include "unwind-pe.h" 36 + #include "unwind-dw2-fde.h" 37 + #include "gthr.h" 38 + #endif 39 + 40 + /* The unseen_objects list contains objects that have been registered 41 + but not yet categorized in any way. The seen_objects list has had 42 + its pc_begin and count fields initialized at minimum, and is sorted 43 + by decreasing value of pc_begin. */ 44 + static struct object *unseen_objects; 45 + static struct object *seen_objects; 46 + 47 + #ifdef __GTHREAD_MUTEX_INIT 48 + static __gthread_mutex_t object_mutex = __GTHREAD_MUTEX_INIT; 49 + #else 50 + static __gthread_mutex_t object_mutex; 51 + #endif 52 + 53 + #ifdef __GTHREAD_MUTEX_INIT_FUNCTION 54 + static void 55 + init_object_mutex (void) 56 + { 57 + __GTHREAD_MUTEX_INIT_FUNCTION (&object_mutex); 58 + } 59 + 60 + static void 61 + init_object_mutex_once (void) 62 + { 63 + static __gthread_once_t once = __GTHREAD_ONCE_INIT; 64 + __gthread_once (&once, init_object_mutex); 65 + } 66 + #else 67 + #define init_object_mutex_once() 68 + #endif 69 + 70 + /* Called from crtbegin.o to register the unwind info for an object. */ 71 + 72 + void 73 + __register_frame_info_bases (const void *begin, struct object *ob, 74 + void *tbase, void *dbase) 75 + { 76 + /* If .eh_frame is empty, don't register at all. */ 77 + if ((const uword *) begin == 0 || *(const uword *) begin == 0) 78 + return; 79 + 80 + ob->pc_begin = (void *)-1; 81 + ob->tbase = tbase; 82 + ob->dbase = dbase; 83 + ob->u.single = begin; 84 + ob->s.i = 0; 85 + ob->s.b.encoding = DW_EH_PE_omit; 86 + #ifdef DWARF2_OBJECT_END_PTR_EXTENSION 87 + ob->fde_end = NULL; 88 + #endif 89 + 90 + init_object_mutex_once (); 91 + __gthread_mutex_lock (&object_mutex); 92 + 93 + ob->next = unseen_objects; 94 + unseen_objects = ob; 95 + 96 + __gthread_mutex_unlock (&object_mutex); 97 + } 98 + 99 + void 100 + __register_frame_info (const void *begin, struct object *ob) 101 + { 102 + __register_frame_info_bases (begin, ob, 0, 0); 103 + } 104 + 105 + void 106 + __register_frame (void *begin) 107 + { 108 + struct object *ob; 109 + 110 + /* If .eh_frame is empty, don't register at all. */ 111 + if (*(uword *) begin == 0) 112 + return; 113 + 114 + ob = malloc (sizeof (struct object)); 115 + __register_frame_info (begin, ob); 116 + } 117 + 118 + /* Similar, but BEGIN is actually a pointer to a table of unwind entries 119 + for different translation units. Called from the file generated by 120 + collect2. */ 121 + 122 + void 123 + __register_frame_info_table_bases (void *begin, struct object *ob, 124 + void *tbase, void *dbase) 125 + { 126 + ob->pc_begin = (void *)-1; 127 + ob->tbase = tbase; 128 + ob->dbase = dbase; 129 + ob->u.array = begin; 130 + ob->s.i = 0; 131 + ob->s.b.from_array = 1; 132 + ob->s.b.encoding = DW_EH_PE_omit; 133 + 134 + init_object_mutex_once (); 135 + __gthread_mutex_lock (&object_mutex); 136 + 137 + ob->next = unseen_objects; 138 + unseen_objects = ob; 139 + 140 + __gthread_mutex_unlock (&object_mutex); 141 + } 142 + 143 + void 144 + __register_frame_info_table (void *begin, struct object *ob) 145 + { 146 + __register_frame_info_table_bases (begin, ob, 0, 0); 147 + } 148 + 149 + void 150 + __register_frame_table (void *begin) 151 + { 152 + struct object *ob = malloc (sizeof (struct object)); 153 + __register_frame_info_table (begin, ob); 154 + } 155 + 156 + /* Called from crtbegin.o to deregister the unwind info for an object. */ 157 + /* ??? Glibc has for a while now exported __register_frame_info and 158 + __deregister_frame_info. If we call __register_frame_info_bases 159 + from crtbegin (wherein it is declared weak), and this object does 160 + not get pulled from libgcc.a for other reasons, then the 161 + invocation of __deregister_frame_info will be resolved from glibc. 162 + Since the registration did not happen there, we'll die. 163 + 164 + Therefore, declare a new deregistration entry point that does the 165 + exact same thing, but will resolve to the same library as 166 + implements __register_frame_info_bases. */ 167 + 168 + void * 169 + __deregister_frame_info_bases (const void *begin) 170 + { 171 + struct object **p; 172 + struct object *ob = 0; 173 + 174 + /* If .eh_frame is empty, we haven't registered. */ 175 + if ((const uword *) begin == 0 || *(const uword *) begin == 0) 176 + return ob; 177 + 178 + init_object_mutex_once (); 179 + __gthread_mutex_lock (&object_mutex); 180 + 181 + for (p = &unseen_objects; *p ; p = &(*p)->next) 182 + if ((*p)->u.single == begin) 183 + { 184 + ob = *p; 185 + *p = ob->next; 186 + goto out; 187 + } 188 + 189 + for (p = &seen_objects; *p ; p = &(*p)->next) 190 + if ((*p)->s.b.sorted) 191 + { 192 + if ((*p)->u.sort->orig_data == begin) 193 + { 194 + ob = *p; 195 + *p = ob->next; 196 + free (ob->u.sort); 197 + goto out; 198 + } 199 + } 200 + else 201 + { 202 + if ((*p)->u.single == begin) 203 + { 204 + ob = *p; 205 + *p = ob->next; 206 + goto out; 207 + } 208 + } 209 + 210 + out: 211 + __gthread_mutex_unlock (&object_mutex); 212 + gcc_assert (ob); 213 + return (void *) ob; 214 + } 215 + 216 + void * 217 + __deregister_frame_info (const void *begin) 218 + { 219 + return __deregister_frame_info_bases (begin); 220 + } 221 + 222 + void 223 + __deregister_frame (void *begin) 224 + { 225 + /* If .eh_frame is empty, we haven't registered. */ 226 + if (*(uword *) begin != 0) 227 + free (__deregister_frame_info (begin)); 228 + } 229 + 230 + 231 + /* Like base_of_encoded_value, but take the base from a struct object 232 + instead of an _Unwind_Context. */ 233 + 234 + static _Unwind_Ptr 235 + base_from_object (unsigned char encoding, struct object *ob) 236 + { 237 + if (encoding == DW_EH_PE_omit) 238 + return 0; 239 + 240 + switch (encoding & 0x70) 241 + { 242 + case DW_EH_PE_absptr: 243 + case DW_EH_PE_pcrel: 244 + case DW_EH_PE_aligned: 245 + return 0; 246 + 247 + case DW_EH_PE_textrel: 248 + return (_Unwind_Ptr) ob->tbase; 249 + case DW_EH_PE_datarel: 250 + return (_Unwind_Ptr) ob->dbase; 251 + default: 252 + gcc_unreachable (); 253 + } 254 + } 255 + 256 + /* Return the FDE pointer encoding from the CIE. */ 257 + /* ??? This is a subset of extract_cie_info from unwind-dw2.c. */ 258 + 259 + static int 260 + get_cie_encoding (const struct dwarf_cie *cie) 261 + { 262 + const unsigned char *aug, *p; 263 + _Unwind_Ptr dummy; 264 + _uleb128_t utmp; 265 + _sleb128_t stmp; 266 + 267 + aug = cie->augmentation; 268 + p = aug + strlen ((const char *)aug) + 1; /* Skip the augmentation string. */ 269 + if (__builtin_expect (cie->version >= 4, 0)) 270 + { 271 + if (p[0] != sizeof (void *) || p[1] != 0) 272 + return DW_EH_PE_omit; /* We are not prepared to handle unexpected 273 + address sizes or segment selectors. */ 274 + p += 2; /* Skip address size and segment size. */ 275 + } 276 + 277 + if (aug[0] != 'z') 278 + return DW_EH_PE_absptr; 279 + 280 + p = read_uleb128 (p, &utmp); /* Skip code alignment. */ 281 + p = read_sleb128 (p, &stmp); /* Skip data alignment. */ 282 + if (cie->version == 1) /* Skip return address column. */ 283 + p++; 284 + else 285 + p = read_uleb128 (p, &utmp); 286 + 287 + aug++; /* Skip 'z' */ 288 + p = read_uleb128 (p, &utmp); /* Skip augmentation length. */ 289 + while (1) 290 + { 291 + /* This is what we're looking for. */ 292 + if (*aug == 'R') 293 + return *p; 294 + /* Personality encoding and pointer. */ 295 + else if (*aug == 'P') 296 + { 297 + /* ??? Avoid dereferencing indirect pointers, since we're 298 + faking the base address. Gotta keep DW_EH_PE_aligned 299 + intact, however. */ 300 + p = read_encoded_value_with_base (*p & 0x7F, 0, p + 1, &dummy); 301 + } 302 + /* LSDA encoding. */ 303 + else if (*aug == 'L') 304 + p++; 305 + /* Otherwise end of string, or unknown augmentation. */ 306 + else 307 + return DW_EH_PE_absptr; 308 + aug++; 309 + } 310 + } 311 + 312 + static inline int 313 + get_fde_encoding (const struct dwarf_fde *f) 314 + { 315 + return get_cie_encoding (get_cie (f)); 316 + } 317 + 318 + 319 + /* Sorting an array of FDEs by address. 320 + (Ideally we would have the linker sort the FDEs so we don't have to do 321 + it at run time. But the linkers are not yet prepared for this.) */ 322 + 323 + /* Comparison routines. Three variants of increasing complexity. */ 324 + 325 + static int 326 + fde_unencoded_compare (struct object *ob __attribute__((unused)), 327 + const fde *x, const fde *y) 328 + { 329 + _Unwind_Ptr x_ptr, y_ptr; 330 + memcpy (&x_ptr, x->pc_begin, sizeof (_Unwind_Ptr)); 331 + memcpy (&y_ptr, y->pc_begin, sizeof (_Unwind_Ptr)); 332 + 333 + if (x_ptr > y_ptr) 334 + return 1; 335 + if (x_ptr < y_ptr) 336 + return -1; 337 + return 0; 338 + } 339 + 340 + static int 341 + fde_single_encoding_compare (struct object *ob, const fde *x, const fde *y) 342 + { 343 + _Unwind_Ptr base, x_ptr, y_ptr; 344 + 345 + base = base_from_object (ob->s.b.encoding, ob); 346 + read_encoded_value_with_base (ob->s.b.encoding, base, x->pc_begin, &x_ptr); 347 + read_encoded_value_with_base (ob->s.b.encoding, base, y->pc_begin, &y_ptr); 348 + 349 + if (x_ptr > y_ptr) 350 + return 1; 351 + if (x_ptr < y_ptr) 352 + return -1; 353 + return 0; 354 + } 355 + 356 + static int 357 + fde_mixed_encoding_compare (struct object *ob, const fde *x, const fde *y) 358 + { 359 + int x_encoding, y_encoding; 360 + _Unwind_Ptr x_ptr, y_ptr; 361 + 362 + x_encoding = get_fde_encoding (x); 363 + read_encoded_value_with_base (x_encoding, base_from_object (x_encoding, ob), 364 + x->pc_begin, &x_ptr); 365 + 366 + y_encoding = get_fde_encoding (y); 367 + read_encoded_value_with_base (y_encoding, base_from_object (y_encoding, ob), 368 + y->pc_begin, &y_ptr); 369 + 370 + if (x_ptr > y_ptr) 371 + return 1; 372 + if (x_ptr < y_ptr) 373 + return -1; 374 + return 0; 375 + } 376 + 377 + typedef int (*fde_compare_t) (struct object *, const fde *, const fde *); 378 + 379 + 380 + /* This is a special mix of insertion sort and heap sort, optimized for 381 + the data sets that actually occur. They look like 382 + 101 102 103 127 128 105 108 110 190 111 115 119 125 160 126 129 130. 383 + I.e. a linearly increasing sequence (coming from functions in the text 384 + section), with additionally a few unordered elements (coming from functions 385 + in gnu_linkonce sections) whose values are higher than the values in the 386 + surrounding linear sequence (but not necessarily higher than the values 387 + at the end of the linear sequence!). 388 + The worst-case total run time is O(N) + O(n log (n)), where N is the 389 + total number of FDEs and n is the number of erratic ones. */ 390 + 391 + struct fde_accumulator 392 + { 393 + struct fde_vector *linear; 394 + struct fde_vector *erratic; 395 + }; 396 + 397 + static inline int 398 + start_fde_sort (struct fde_accumulator *accu, size_t count) 399 + { 400 + size_t size; 401 + if (! count) 402 + return 0; 403 + 404 + size = sizeof (struct fde_vector) + sizeof (const fde *) * count; 405 + if ((accu->linear = malloc (size))) 406 + { 407 + accu->linear->count = 0; 408 + if ((accu->erratic = malloc (size))) 409 + accu->erratic->count = 0; 410 + return 1; 411 + } 412 + else 413 + return 0; 414 + } 415 + 416 + static inline void 417 + fde_insert (struct fde_accumulator *accu, const fde *this_fde) 418 + { 419 + if (accu->linear) 420 + accu->linear->array[accu->linear->count++] = this_fde; 421 + } 422 + 423 + /* Split LINEAR into a linear sequence with low values and an erratic 424 + sequence with high values, put the linear one (of longest possible 425 + length) into LINEAR and the erratic one into ERRATIC. This is O(N). 426 + 427 + Because the longest linear sequence we are trying to locate within the 428 + incoming LINEAR array can be interspersed with (high valued) erratic 429 + entries. We construct a chain indicating the sequenced entries. 430 + To avoid having to allocate this chain, we overlay it onto the space of 431 + the ERRATIC array during construction. A final pass iterates over the 432 + chain to determine what should be placed in the ERRATIC array, and 433 + what is the linear sequence. This overlay is safe from aliasing. */ 434 + 435 + static inline void 436 + fde_split (struct object *ob, fde_compare_t fde_compare, 437 + struct fde_vector *linear, struct fde_vector *erratic) 438 + { 439 + static const fde *marker; 440 + size_t count = linear->count; 441 + const fde *const *chain_end = &marker; 442 + size_t i, j, k; 443 + 444 + /* This should optimize out, but it is wise to make sure this assumption 445 + is correct. Should these have different sizes, we cannot cast between 446 + them and the overlaying onto ERRATIC will not work. */ 447 + gcc_assert (sizeof (const fde *) == sizeof (const fde **)); 448 + 449 + for (i = 0; i < count; i++) 450 + { 451 + const fde *const *probe; 452 + 453 + for (probe = chain_end; 454 + probe != &marker && fde_compare (ob, linear->array[i], *probe) < 0; 455 + probe = chain_end) 456 + { 457 + chain_end = (const fde *const*) erratic->array[probe - linear->array]; 458 + erratic->array[probe - linear->array] = NULL; 459 + } 460 + erratic->array[i] = (const fde *) chain_end; 461 + chain_end = &linear->array[i]; 462 + } 463 + 464 + /* Each entry in LINEAR which is part of the linear sequence we have 465 + discovered will correspond to a non-NULL entry in the chain we built in 466 + the ERRATIC array. */ 467 + for (i = j = k = 0; i < count; i++) 468 + if (erratic->array[i]) 469 + linear->array[j++] = linear->array[i]; 470 + else 471 + erratic->array[k++] = linear->array[i]; 472 + linear->count = j; 473 + erratic->count = k; 474 + } 475 + 476 + #define SWAP(x,y) do { const fde * tmp = x; x = y; y = tmp; } while (0) 477 + 478 + /* Convert a semi-heap to a heap. A semi-heap is a heap except possibly 479 + for the first (root) node; push it down to its rightful place. */ 480 + 481 + static void 482 + frame_downheap (struct object *ob, fde_compare_t fde_compare, const fde **a, 483 + int lo, int hi) 484 + { 485 + int i, j; 486 + 487 + for (i = lo, j = 2*i+1; 488 + j < hi; 489 + j = 2*i+1) 490 + { 491 + if (j+1 < hi && fde_compare (ob, a[j], a[j+1]) < 0) 492 + ++j; 493 + 494 + if (fde_compare (ob, a[i], a[j]) < 0) 495 + { 496 + SWAP (a[i], a[j]); 497 + i = j; 498 + } 499 + else 500 + break; 501 + } 502 + } 503 + 504 + /* This is O(n log(n)). BSD/OS defines heapsort in stdlib.h, so we must 505 + use a name that does not conflict. */ 506 + 507 + static void 508 + frame_heapsort (struct object *ob, fde_compare_t fde_compare, 509 + struct fde_vector *erratic) 510 + { 511 + /* For a description of this algorithm, see: 512 + Samuel P. Harbison, Guy L. Steele Jr.: C, a reference manual, 2nd ed., 513 + p. 60-61. */ 514 + const fde ** a = erratic->array; 515 + /* A portion of the array is called a "heap" if for all i>=0: 516 + If i and 2i+1 are valid indices, then a[i] >= a[2i+1]. 517 + If i and 2i+2 are valid indices, then a[i] >= a[2i+2]. */ 518 + size_t n = erratic->count; 519 + int m; 520 + 521 + /* Expand our heap incrementally from the end of the array, heapifying 522 + each resulting semi-heap as we go. After each step, a[m] is the top 523 + of a heap. */ 524 + for (m = n/2-1; m >= 0; --m) 525 + frame_downheap (ob, fde_compare, a, m, n); 526 + 527 + /* Shrink our heap incrementally from the end of the array, first 528 + swapping out the largest element a[0] and then re-heapifying the 529 + resulting semi-heap. After each step, a[0..m) is a heap. */ 530 + for (m = n-1; m >= 1; --m) 531 + { 532 + SWAP (a[0], a[m]); 533 + frame_downheap (ob, fde_compare, a, 0, m); 534 + } 535 + #undef SWAP 536 + } 537 + 538 + /* Merge V1 and V2, both sorted, and put the result into V1. */ 539 + static inline void 540 + fde_merge (struct object *ob, fde_compare_t fde_compare, 541 + struct fde_vector *v1, struct fde_vector *v2) 542 + { 543 + size_t i1, i2; 544 + const fde * fde2; 545 + 546 + i2 = v2->count; 547 + if (i2 > 0) 548 + { 549 + i1 = v1->count; 550 + do 551 + { 552 + i2--; 553 + fde2 = v2->array[i2]; 554 + while (i1 > 0 && fde_compare (ob, v1->array[i1-1], fde2) > 0) 555 + { 556 + v1->array[i1+i2] = v1->array[i1-1]; 557 + i1--; 558 + } 559 + v1->array[i1+i2] = fde2; 560 + } 561 + while (i2 > 0); 562 + v1->count += v2->count; 563 + } 564 + } 565 + 566 + static inline void 567 + end_fde_sort (struct object *ob, struct fde_accumulator *accu, size_t count) 568 + { 569 + fde_compare_t fde_compare; 570 + 571 + gcc_assert (!accu->linear || accu->linear->count == count); 572 + 573 + if (ob->s.b.mixed_encoding) 574 + fde_compare = fde_mixed_encoding_compare; 575 + else if (ob->s.b.encoding == DW_EH_PE_absptr) 576 + fde_compare = fde_unencoded_compare; 577 + else 578 + fde_compare = fde_single_encoding_compare; 579 + 580 + if (accu->erratic) 581 + { 582 + fde_split (ob, fde_compare, accu->linear, accu->erratic); 583 + gcc_assert (accu->linear->count + accu->erratic->count == count); 584 + frame_heapsort (ob, fde_compare, accu->erratic); 585 + fde_merge (ob, fde_compare, accu->linear, accu->erratic); 586 + free (accu->erratic); 587 + } 588 + else 589 + { 590 + /* We've not managed to malloc an erratic array, 591 + so heap sort in the linear one. */ 592 + frame_heapsort (ob, fde_compare, accu->linear); 593 + } 594 + } 595 + 596 + 597 + /* Update encoding, mixed_encoding, and pc_begin for OB for the 598 + fde array beginning at THIS_FDE. Return the number of fdes 599 + encountered along the way. */ 600 + 601 + static size_t 602 + classify_object_over_fdes (struct object *ob, const fde *this_fde) 603 + { 604 + const struct dwarf_cie *last_cie = 0; 605 + size_t count = 0; 606 + int encoding = DW_EH_PE_absptr; 607 + _Unwind_Ptr base = 0; 608 + 609 + for (; ! last_fde (ob, this_fde); this_fde = next_fde (this_fde)) 610 + { 611 + const struct dwarf_cie *this_cie; 612 + _Unwind_Ptr mask, pc_begin; 613 + 614 + /* Skip CIEs. */ 615 + if (this_fde->CIE_delta == 0) 616 + continue; 617 + 618 + /* Determine the encoding for this FDE. Note mixed encoded 619 + objects for later. */ 620 + this_cie = get_cie (this_fde); 621 + if (this_cie != last_cie) 622 + { 623 + last_cie = this_cie; 624 + encoding = get_cie_encoding (this_cie); 625 + if (encoding == DW_EH_PE_omit) 626 + return -1; 627 + base = base_from_object (encoding, ob); 628 + if (ob->s.b.encoding == DW_EH_PE_omit) 629 + ob->s.b.encoding = encoding; 630 + else if (ob->s.b.encoding != encoding) 631 + ob->s.b.mixed_encoding = 1; 632 + } 633 + 634 + read_encoded_value_with_base (encoding, base, this_fde->pc_begin, 635 + &pc_begin); 636 + 637 + /* Take care to ignore link-once functions that were removed. 638 + In these cases, the function address will be NULL, but if 639 + the encoding is smaller than a pointer a true NULL may not 640 + be representable. Assume 0 in the representable bits is NULL. */ 641 + mask = size_of_encoded_value (encoding); 642 + if (mask < sizeof (void *)) 643 + mask = (((_Unwind_Ptr) 1) << (mask << 3)) - 1; 644 + else 645 + mask = -1; 646 + 647 + if ((pc_begin & mask) == 0) 648 + continue; 649 + 650 + count += 1; 651 + if ((void *) pc_begin < ob->pc_begin) 652 + ob->pc_begin = (void *) pc_begin; 653 + } 654 + 655 + return count; 656 + } 657 + 658 + static void 659 + add_fdes (struct object *ob, struct fde_accumulator *accu, const fde *this_fde) 660 + { 661 + const struct dwarf_cie *last_cie = 0; 662 + int encoding = ob->s.b.encoding; 663 + _Unwind_Ptr base = base_from_object (ob->s.b.encoding, ob); 664 + 665 + for (; ! last_fde (ob, this_fde); this_fde = next_fde (this_fde)) 666 + { 667 + const struct dwarf_cie *this_cie; 668 + 669 + /* Skip CIEs. */ 670 + if (this_fde->CIE_delta == 0) 671 + continue; 672 + 673 + if (ob->s.b.mixed_encoding) 674 + { 675 + /* Determine the encoding for this FDE. Note mixed encoded 676 + objects for later. */ 677 + this_cie = get_cie (this_fde); 678 + if (this_cie != last_cie) 679 + { 680 + last_cie = this_cie; 681 + encoding = get_cie_encoding (this_cie); 682 + base = base_from_object (encoding, ob); 683 + } 684 + } 685 + 686 + if (encoding == DW_EH_PE_absptr) 687 + { 688 + _Unwind_Ptr ptr; 689 + memcpy (&ptr, this_fde->pc_begin, sizeof (_Unwind_Ptr)); 690 + if (ptr == 0) 691 + continue; 692 + } 693 + else 694 + { 695 + _Unwind_Ptr pc_begin, mask; 696 + 697 + read_encoded_value_with_base (encoding, base, this_fde->pc_begin, 698 + &pc_begin); 699 + 700 + /* Take care to ignore link-once functions that were removed. 701 + In these cases, the function address will be NULL, but if 702 + the encoding is smaller than a pointer a true NULL may not 703 + be representable. Assume 0 in the representable bits is NULL. */ 704 + mask = size_of_encoded_value (encoding); 705 + if (mask < sizeof (void *)) 706 + mask = (((_Unwind_Ptr) 1) << (mask << 3)) - 1; 707 + else 708 + mask = -1; 709 + 710 + if ((pc_begin & mask) == 0) 711 + continue; 712 + } 713 + 714 + fde_insert (accu, this_fde); 715 + } 716 + } 717 + 718 + /* Set up a sorted array of pointers to FDEs for a loaded object. We 719 + count up the entries before allocating the array because it's likely to 720 + be faster. We can be called multiple times, should we have failed to 721 + allocate a sorted fde array on a previous occasion. */ 722 + 723 + static inline void 724 + init_object (struct object* ob) 725 + { 726 + struct fde_accumulator accu; 727 + size_t count; 728 + 729 + count = ob->s.b.count; 730 + if (count == 0) 731 + { 732 + if (ob->s.b.from_array) 733 + { 734 + fde **p = ob->u.array; 735 + for (count = 0; *p; ++p) 736 + { 737 + size_t cur_count = classify_object_over_fdes (ob, *p); 738 + if (cur_count == (size_t) -1) 739 + goto unhandled_fdes; 740 + count += cur_count; 741 + } 742 + } 743 + else 744 + { 745 + count = classify_object_over_fdes (ob, ob->u.single); 746 + if (count == (size_t) -1) 747 + { 748 + static const fde terminator; 749 + unhandled_fdes: 750 + ob->s.i = 0; 751 + ob->s.b.encoding = DW_EH_PE_omit; 752 + ob->u.single = &terminator; 753 + return; 754 + } 755 + } 756 + 757 + /* The count field we have in the main struct object is somewhat 758 + limited, but should suffice for virtually all cases. If the 759 + counted value doesn't fit, re-write a zero. The worst that 760 + happens is that we re-count next time -- admittedly non-trivial 761 + in that this implies some 2M fdes, but at least we function. */ 762 + ob->s.b.count = count; 763 + if (ob->s.b.count != count) 764 + ob->s.b.count = 0; 765 + } 766 + 767 + if (!start_fde_sort (&accu, count)) 768 + return; 769 + 770 + if (ob->s.b.from_array) 771 + { 772 + fde **p; 773 + for (p = ob->u.array; *p; ++p) 774 + add_fdes (ob, &accu, *p); 775 + } 776 + else 777 + add_fdes (ob, &accu, ob->u.single); 778 + 779 + end_fde_sort (ob, &accu, count); 780 + 781 + /* Save the original fde pointer, since this is the key by which the 782 + DSO will deregister the object. */ 783 + accu.linear->orig_data = ob->u.single; 784 + ob->u.sort = accu.linear; 785 + 786 + ob->s.b.sorted = 1; 787 + } 788 + 789 + /* A linear search through a set of FDEs for the given PC. This is 790 + used when there was insufficient memory to allocate and sort an 791 + array. */ 792 + 793 + static const fde * 794 + linear_search_fdes (struct object *ob, const fde *this_fde, void *pc) 795 + { 796 + const struct dwarf_cie *last_cie = 0; 797 + int encoding = ob->s.b.encoding; 798 + _Unwind_Ptr base = base_from_object (ob->s.b.encoding, ob); 799 + 800 + for (; ! last_fde (ob, this_fde); this_fde = next_fde (this_fde)) 801 + { 802 + const struct dwarf_cie *this_cie; 803 + _Unwind_Ptr pc_begin, pc_range; 804 + 805 + /* Skip CIEs. */ 806 + if (this_fde->CIE_delta == 0) 807 + continue; 808 + 809 + if (ob->s.b.mixed_encoding) 810 + { 811 + /* Determine the encoding for this FDE. Note mixed encoded 812 + objects for later. */ 813 + this_cie = get_cie (this_fde); 814 + if (this_cie != last_cie) 815 + { 816 + last_cie = this_cie; 817 + encoding = get_cie_encoding (this_cie); 818 + base = base_from_object (encoding, ob); 819 + } 820 + } 821 + 822 + if (encoding == DW_EH_PE_absptr) 823 + { 824 + const _Unwind_Ptr *pc_array = (const _Unwind_Ptr *) this_fde->pc_begin; 825 + pc_begin = pc_array[0]; 826 + pc_range = pc_array[1]; 827 + if (pc_begin == 0) 828 + continue; 829 + } 830 + else 831 + { 832 + _Unwind_Ptr mask; 833 + const unsigned char *p; 834 + 835 + p = read_encoded_value_with_base (encoding, base, 836 + this_fde->pc_begin, &pc_begin); 837 + read_encoded_value_with_base (encoding & 0x0F, 0, p, &pc_range); 838 + 839 + /* Take care to ignore link-once functions that were removed. 840 + In these cases, the function address will be NULL, but if 841 + the encoding is smaller than a pointer a true NULL may not 842 + be representable. Assume 0 in the representable bits is NULL. */ 843 + mask = size_of_encoded_value (encoding); 844 + if (mask < sizeof (void *)) 845 + mask = (((_Unwind_Ptr) 1) << (mask << 3)) - 1; 846 + else 847 + mask = -1; 848 + 849 + if ((pc_begin & mask) == 0) 850 + continue; 851 + } 852 + 853 + if ((_Unwind_Ptr) pc - pc_begin < pc_range) 854 + return this_fde; 855 + } 856 + 857 + return NULL; 858 + } 859 + 860 + /* Binary search for an FDE containing the given PC. Here are three 861 + implementations of increasing complexity. */ 862 + 863 + static inline const fde * 864 + binary_search_unencoded_fdes (struct object *ob, void *pc) 865 + { 866 + struct fde_vector *vec = ob->u.sort; 867 + size_t lo, hi; 868 + 869 + for (lo = 0, hi = vec->count; lo < hi; ) 870 + { 871 + size_t i = (lo + hi) / 2; 872 + const fde *const f = vec->array[i]; 873 + void *pc_begin; 874 + uaddr pc_range; 875 + memcpy (&pc_begin, (const void * const *) f->pc_begin, sizeof (void *)); 876 + memcpy (&pc_range, (const uaddr *) f->pc_begin + 1, sizeof (uaddr)); 877 + 878 + if (pc < pc_begin) 879 + hi = i; 880 + else if (pc >= pc_begin + pc_range) 881 + lo = i + 1; 882 + else 883 + return f; 884 + } 885 + 886 + return NULL; 887 + } 888 + 889 + static inline const fde * 890 + binary_search_single_encoding_fdes (struct object *ob, void *pc) 891 + { 892 + struct fde_vector *vec = ob->u.sort; 893 + int encoding = ob->s.b.encoding; 894 + _Unwind_Ptr base = base_from_object (encoding, ob); 895 + size_t lo, hi; 896 + 897 + for (lo = 0, hi = vec->count; lo < hi; ) 898 + { 899 + size_t i = (lo + hi) / 2; 900 + const fde *f = vec->array[i]; 901 + _Unwind_Ptr pc_begin, pc_range; 902 + const unsigned char *p; 903 + 904 + p = read_encoded_value_with_base (encoding, base, f->pc_begin, 905 + &pc_begin); 906 + read_encoded_value_with_base (encoding & 0x0F, 0, p, &pc_range); 907 + 908 + if ((_Unwind_Ptr) pc < pc_begin) 909 + hi = i; 910 + else if ((_Unwind_Ptr) pc >= pc_begin + pc_range) 911 + lo = i + 1; 912 + else 913 + return f; 914 + } 915 + 916 + return NULL; 917 + } 918 + 919 + static inline const fde * 920 + binary_search_mixed_encoding_fdes (struct object *ob, void *pc) 921 + { 922 + struct fde_vector *vec = ob->u.sort; 923 + size_t lo, hi; 924 + 925 + for (lo = 0, hi = vec->count; lo < hi; ) 926 + { 927 + size_t i = (lo + hi) / 2; 928 + const fde *f = vec->array[i]; 929 + _Unwind_Ptr pc_begin, pc_range; 930 + const unsigned char *p; 931 + int encoding; 932 + 933 + encoding = get_fde_encoding (f); 934 + p = read_encoded_value_with_base (encoding, 935 + base_from_object (encoding, ob), 936 + f->pc_begin, &pc_begin); 937 + read_encoded_value_with_base (encoding & 0x0F, 0, p, &pc_range); 938 + 939 + if ((_Unwind_Ptr) pc < pc_begin) 940 + hi = i; 941 + else if ((_Unwind_Ptr) pc >= pc_begin + pc_range) 942 + lo = i + 1; 943 + else 944 + return f; 945 + } 946 + 947 + return NULL; 948 + } 949 + 950 + static const fde * 951 + search_object (struct object* ob, void *pc) 952 + { 953 + /* If the data hasn't been sorted, try to do this now. We may have 954 + more memory available than last time we tried. */ 955 + if (! ob->s.b.sorted) 956 + { 957 + init_object (ob); 958 + 959 + /* Despite the above comment, the normal reason to get here is 960 + that we've not processed this object before. A quick range 961 + check is in order. */ 962 + if (pc < ob->pc_begin) 963 + return NULL; 964 + } 965 + 966 + if (ob->s.b.sorted) 967 + { 968 + if (ob->s.b.mixed_encoding) 969 + return binary_search_mixed_encoding_fdes (ob, pc); 970 + else if (ob->s.b.encoding == DW_EH_PE_absptr) 971 + return binary_search_unencoded_fdes (ob, pc); 972 + else 973 + return binary_search_single_encoding_fdes (ob, pc); 974 + } 975 + else 976 + { 977 + /* Long slow laborious linear search, cos we've no memory. */ 978 + if (ob->s.b.from_array) 979 + { 980 + fde **p; 981 + for (p = ob->u.array; *p ; p++) 982 + { 983 + const fde *f = linear_search_fdes (ob, *p, pc); 984 + if (f) 985 + return f; 986 + } 987 + return NULL; 988 + } 989 + else 990 + return linear_search_fdes (ob, ob->u.single, pc); 991 + } 992 + } 993 + 994 + const fde * 995 + _Unwind_Find_FDE (void *pc, struct dwarf_eh_bases *bases) 996 + { 997 + struct object *ob; 998 + const fde *f = NULL; 999 + 1000 + init_object_mutex_once (); 1001 + __gthread_mutex_lock (&object_mutex); 1002 + 1003 + /* Linear search through the classified objects, to find the one 1004 + containing the pc. Note that pc_begin is sorted descending, and 1005 + we expect objects to be non-overlapping. */ 1006 + for (ob = seen_objects; ob; ob = ob->next) 1007 + if (pc >= ob->pc_begin) 1008 + { 1009 + f = search_object (ob, pc); 1010 + if (f) 1011 + goto fini; 1012 + break; 1013 + } 1014 + 1015 + /* Classify and search the objects we've not yet processed. */ 1016 + while ((ob = unseen_objects)) 1017 + { 1018 + struct object **p; 1019 + 1020 + unseen_objects = ob->next; 1021 + f = search_object (ob, pc); 1022 + 1023 + /* Insert the object into the classified list. */ 1024 + for (p = &seen_objects; *p ; p = &(*p)->next) 1025 + if ((*p)->pc_begin < ob->pc_begin) 1026 + break; 1027 + ob->next = *p; 1028 + *p = ob; 1029 + 1030 + if (f) 1031 + goto fini; 1032 + } 1033 + 1034 + fini: 1035 + __gthread_mutex_unlock (&object_mutex); 1036 + 1037 + if (f) 1038 + { 1039 + int encoding; 1040 + _Unwind_Ptr func; 1041 + 1042 + bases->tbase = ob->tbase; 1043 + bases->dbase = ob->dbase; 1044 + 1045 + encoding = ob->s.b.encoding; 1046 + if (ob->s.b.mixed_encoding) 1047 + encoding = get_fde_encoding (f); 1048 + read_encoded_value_with_base (encoding, base_from_object (encoding, ob), 1049 + f->pc_begin, &func); 1050 + bases->func = (void *) func; 1051 + } 1052 + 1053 + return f; 1054 + }
+183
src/libunwind-darwin/unwind-dw2-fde.h
··· 1 + /* Subroutines needed for unwinding stack frames for exception handling. */ 2 + /* Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2004, 2009 3 + Free Software Foundation, Inc. 4 + Contributed by Jason Merrill <jason@cygnus.com>. 5 + 6 + This file is part of GCC. 7 + 8 + GCC is free software; you can redistribute it and/or modify it under 9 + the terms of the GNU General Public License as published by the Free 10 + Software Foundation; either version 3, or (at your option) any later 11 + version. 12 + 13 + GCC is distributed in the hope that it will be useful, but WITHOUT ANY 14 + WARRANTY; without even the implied warranty of MERCHANTABILITY or 15 + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16 + for more details. 17 + 18 + Under Section 7 of GPL version 3, you are granted additional 19 + permissions described in the GCC Runtime Library Exception, version 20 + 3.1, as published by the Free Software Foundation. 21 + 22 + You should have received a copy of the GNU General Public License and 23 + a copy of the GCC Runtime Library Exception along with this program; 24 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 25 + <http://www.gnu.org/licenses/>. */ 26 + 27 + #ifndef GCC_UNWIND_DW2_FDE_H 28 + #define GCC_UNWIND_DW2_FDE_H 29 + 30 + #ifndef HIDE_EXPORTS 31 + #pragma GCC visibility push(default) 32 + #endif 33 + 34 + struct fde_vector 35 + { 36 + const void *orig_data; 37 + size_t count; 38 + const struct dwarf_fde *array[]; 39 + }; 40 + 41 + struct object 42 + { 43 + void *pc_begin; 44 + void *tbase; 45 + void *dbase; 46 + union { 47 + const struct dwarf_fde *single; 48 + struct dwarf_fde **array; 49 + struct fde_vector *sort; 50 + } u; 51 + 52 + union { 53 + struct { 54 + unsigned long sorted : 1; 55 + unsigned long from_array : 1; 56 + unsigned long mixed_encoding : 1; 57 + unsigned long encoding : 8; 58 + /* ??? Wish there was an easy way to detect a 64-bit host here; 59 + we've got 32 bits left to play with... */ 60 + unsigned long count : 21; 61 + } b; 62 + size_t i; 63 + } s; 64 + 65 + #ifdef DWARF2_OBJECT_END_PTR_EXTENSION 66 + char *fde_end; 67 + #endif 68 + 69 + struct object *next; 70 + }; 71 + 72 + /* This is the original definition of struct object. While the struct 73 + itself was opaque to users, they did know how large it was, and 74 + allocate one statically in crtbegin for each DSO. Keep this around 75 + so that we're aware of the static size limitations for the new struct. */ 76 + struct old_object 77 + { 78 + void *pc_begin; 79 + void *pc_end; 80 + struct dwarf_fde *fde_begin; 81 + struct dwarf_fde **fde_array; 82 + size_t count; 83 + struct old_object *next; 84 + }; 85 + 86 + struct dwarf_eh_bases 87 + { 88 + void *tbase; 89 + void *dbase; 90 + void *func; 91 + }; 92 + 93 + 94 + extern void __register_frame_info_bases (const void *, struct object *, 95 + void *, void *); 96 + extern void __register_frame_info (const void *, struct object *); 97 + extern void __register_frame (void *); 98 + extern void __register_frame_info_table_bases (void *, struct object *, 99 + void *, void *); 100 + extern void __register_frame_info_table (void *, struct object *); 101 + extern void __register_frame_table (void *); 102 + extern void *__deregister_frame_info (const void *); 103 + extern void *__deregister_frame_info_bases (const void *); 104 + extern void __deregister_frame (void *); 105 + 106 + 107 + typedef int sword __attribute__ ((mode (SI))); 108 + typedef unsigned int uword __attribute__ ((mode (SI))); 109 + typedef unsigned int uaddr __attribute__ ((mode (pointer))); 110 + typedef int saddr __attribute__ ((mode (pointer))); 111 + typedef unsigned char ubyte; 112 + 113 + /* Terminology: 114 + CIE - Common Information Element 115 + FDE - Frame Descriptor Element 116 + 117 + There is one per function, and it describes where the function code 118 + is located, and what the register lifetimes and stack layout are 119 + within the function. 120 + 121 + The data structures are defined in the DWARF specification, although 122 + not in a very readable way (see LITERATURE). 123 + 124 + Every time an exception is thrown, the code needs to locate the FDE 125 + for the current function, and starts to look for exception regions 126 + from that FDE. This works in a two-level search: 127 + a) in a linear search, find the shared image (i.e. DLL) containing 128 + the PC 129 + b) using the FDE table for that shared object, locate the FDE using 130 + binary search (which requires the sorting). */ 131 + 132 + /* The first few fields of a CIE. The CIE_id field is 0 for a CIE, 133 + to distinguish it from a valid FDE. FDEs are aligned to an addressing 134 + unit boundary, but the fields within are unaligned. */ 135 + struct dwarf_cie 136 + { 137 + uword length; 138 + sword CIE_id; 139 + ubyte version; 140 + unsigned char augmentation[]; 141 + } __attribute__ ((packed, aligned (__alignof__ (void *)))); 142 + 143 + /* The first few fields of an FDE. */ 144 + struct dwarf_fde 145 + { 146 + uword length; 147 + sword CIE_delta; 148 + unsigned char pc_begin[]; 149 + } __attribute__ ((packed, aligned (__alignof__ (void *)))); 150 + 151 + typedef struct dwarf_fde fde; 152 + 153 + /* Locate the CIE for a given FDE. */ 154 + 155 + static inline const struct dwarf_cie * 156 + get_cie (const struct dwarf_fde *f) 157 + { 158 + return (const void *)&f->CIE_delta - f->CIE_delta; 159 + } 160 + 161 + static inline const fde * 162 + next_fde (const fde *f) 163 + { 164 + return (const fde *) ((const char *) f + f->length + sizeof (f->length)); 165 + } 166 + 167 + extern const fde * _Unwind_Find_FDE (void *, struct dwarf_eh_bases *); 168 + 169 + static inline int 170 + last_fde (struct object *obj __attribute__ ((__unused__)), const fde *f) 171 + { 172 + #ifdef DWARF2_OBJECT_END_PTR_EXTENSION 173 + return (char *)f == obj->fde_end || f->length == 0; 174 + #else 175 + return f->length == 0; 176 + #endif 177 + } 178 + 179 + #ifndef HIDE_EXPORTS 180 + #pragma GCC visibility pop 181 + #endif 182 + 183 + #endif /* unwind-dw2-fde.h */
+1603
src/libunwind-darwin/unwind-dw2.c
··· 1 + /* DWARF2 exception handling and frame unwind runtime interface routines. 2 + Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 3 + 2008, 2009, 2010 Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #include "tconfig.h" 27 + #include "tsystem.h" 28 + #include "coretypes.h" 29 + #include "tm.h" 30 + #include "dwarf2.h" 31 + #include "unwind.h" 32 + #ifdef __USING_SJLJ_EXCEPTIONS__ 33 + # define NO_SIZE_OF_ENCODED_VALUE 34 + #endif 35 + #include "unwind-pe.h" 36 + #include "unwind-dw2-fde.h" 37 + #include "gthr.h" 38 + #include "unwind-dw2.h" 39 + 40 + #ifndef __USING_SJLJ_EXCEPTIONS__ 41 + 42 + #ifndef STACK_GROWS_DOWNWARD 43 + #define STACK_GROWS_DOWNWARD 0 44 + #else 45 + #undef STACK_GROWS_DOWNWARD 46 + #define STACK_GROWS_DOWNWARD 1 47 + #endif 48 + 49 + /* Dwarf frame registers used for pre gcc 3.0 compiled glibc. */ 50 + #ifndef PRE_GCC3_DWARF_FRAME_REGISTERS 51 + #define PRE_GCC3_DWARF_FRAME_REGISTERS DWARF_FRAME_REGISTERS 52 + #endif 53 + 54 + #ifndef DWARF_REG_TO_UNWIND_COLUMN 55 + #define DWARF_REG_TO_UNWIND_COLUMN(REGNO) (REGNO) 56 + #endif 57 + 58 + /* This is the register and unwind state for a particular frame. This 59 + provides the information necessary to unwind up past a frame and return 60 + to its caller. */ 61 + struct _Unwind_Context 62 + { 63 + void *reg[DWARF_FRAME_REGISTERS+1]; 64 + void *cfa; 65 + void *ra; 66 + void *lsda; 67 + struct dwarf_eh_bases bases; 68 + /* Signal frame context. */ 69 + #define SIGNAL_FRAME_BIT ((~(_Unwind_Word) 0 >> 1) + 1) 70 + /* Context which has version/args_size/by_value fields. */ 71 + #define EXTENDED_CONTEXT_BIT ((~(_Unwind_Word) 0 >> 2) + 1) 72 + _Unwind_Word flags; 73 + /* 0 for now, can be increased when further fields are added to 74 + struct _Unwind_Context. */ 75 + _Unwind_Word version; 76 + _Unwind_Word args_size; 77 + char by_value[DWARF_FRAME_REGISTERS+1]; 78 + }; 79 + 80 + /* Byte size of every register managed by these routines. */ 81 + static unsigned char dwarf_reg_size_table[DWARF_FRAME_REGISTERS+1]; 82 + 83 + 84 + /* Read unaligned data from the instruction buffer. */ 85 + 86 + union unaligned 87 + { 88 + void *p; 89 + unsigned u2 __attribute__ ((mode (HI))); 90 + unsigned u4 __attribute__ ((mode (SI))); 91 + unsigned u8 __attribute__ ((mode (DI))); 92 + signed s2 __attribute__ ((mode (HI))); 93 + signed s4 __attribute__ ((mode (SI))); 94 + signed s8 __attribute__ ((mode (DI))); 95 + } __attribute__ ((packed)); 96 + 97 + static void uw_update_context (struct _Unwind_Context *, _Unwind_FrameState *); 98 + static _Unwind_Reason_Code uw_frame_state_for (struct _Unwind_Context *, 99 + _Unwind_FrameState *); 100 + 101 + static inline void * 102 + read_pointer (const void *p) { const union unaligned *up = p; return up->p; } 103 + 104 + static inline int 105 + read_1u (const void *p) { return *(const unsigned char *) p; } 106 + 107 + static inline int 108 + read_1s (const void *p) { return *(const signed char *) p; } 109 + 110 + static inline int 111 + read_2u (const void *p) { const union unaligned *up = p; return up->u2; } 112 + 113 + static inline int 114 + read_2s (const void *p) { const union unaligned *up = p; return up->s2; } 115 + 116 + static inline unsigned int 117 + read_4u (const void *p) { const union unaligned *up = p; return up->u4; } 118 + 119 + static inline int 120 + read_4s (const void *p) { const union unaligned *up = p; return up->s4; } 121 + 122 + static inline unsigned long 123 + read_8u (const void *p) { const union unaligned *up = p; return up->u8; } 124 + 125 + static inline unsigned long 126 + read_8s (const void *p) { const union unaligned *up = p; return up->s8; } 127 + 128 + static inline _Unwind_Word 129 + _Unwind_IsSignalFrame (struct _Unwind_Context *context) 130 + { 131 + return (context->flags & SIGNAL_FRAME_BIT) ? 1 : 0; 132 + } 133 + 134 + static inline void 135 + _Unwind_SetSignalFrame (struct _Unwind_Context *context, int val) 136 + { 137 + if (val) 138 + context->flags |= SIGNAL_FRAME_BIT; 139 + else 140 + context->flags &= ~SIGNAL_FRAME_BIT; 141 + } 142 + 143 + static inline _Unwind_Word 144 + _Unwind_IsExtendedContext (struct _Unwind_Context *context) 145 + { 146 + return context->flags & EXTENDED_CONTEXT_BIT; 147 + } 148 + 149 + /* Get the value of register INDEX as saved in CONTEXT. */ 150 + 151 + inline _Unwind_Word 152 + _Unwind_GetGR (struct _Unwind_Context *context, int index) 153 + { 154 + int size; 155 + void *ptr; 156 + 157 + #ifdef DWARF_ZERO_REG 158 + if (index == DWARF_ZERO_REG) 159 + return 0; 160 + #endif 161 + 162 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 163 + gcc_assert (index < (int) sizeof(dwarf_reg_size_table)); 164 + size = dwarf_reg_size_table[index]; 165 + ptr = context->reg[index]; 166 + 167 + if (_Unwind_IsExtendedContext (context) && context->by_value[index]) 168 + return (_Unwind_Word) (_Unwind_Internal_Ptr) ptr; 169 + 170 + /* This will segfault if the register hasn't been saved. */ 171 + if (size == sizeof(_Unwind_Ptr)) 172 + return * (_Unwind_Ptr *) ptr; 173 + else 174 + { 175 + gcc_assert (size == sizeof(_Unwind_Word)); 176 + return * (_Unwind_Word *) ptr; 177 + } 178 + } 179 + 180 + static inline void * 181 + _Unwind_GetPtr (struct _Unwind_Context *context, int index) 182 + { 183 + return (void *)(_Unwind_Ptr) _Unwind_GetGR (context, index); 184 + } 185 + 186 + /* Get the value of the CFA as saved in CONTEXT. */ 187 + 188 + _Unwind_Word 189 + _Unwind_GetCFA (struct _Unwind_Context *context) 190 + { 191 + return (_Unwind_Ptr) context->cfa; 192 + } 193 + 194 + /* Overwrite the saved value for register INDEX in CONTEXT with VAL. */ 195 + 196 + inline void 197 + _Unwind_SetGR (struct _Unwind_Context *context, int index, _Unwind_Word val) 198 + { 199 + int size; 200 + void *ptr; 201 + 202 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 203 + gcc_assert (index < (int) sizeof(dwarf_reg_size_table)); 204 + size = dwarf_reg_size_table[index]; 205 + 206 + if (_Unwind_IsExtendedContext (context) && context->by_value[index]) 207 + { 208 + context->reg[index] = (void *) (_Unwind_Internal_Ptr) val; 209 + return; 210 + } 211 + 212 + ptr = context->reg[index]; 213 + 214 + if (size == sizeof(_Unwind_Ptr)) 215 + * (_Unwind_Ptr *) ptr = val; 216 + else 217 + { 218 + gcc_assert (size == sizeof(_Unwind_Word)); 219 + * (_Unwind_Word *) ptr = val; 220 + } 221 + } 222 + 223 + /* Get the pointer to a register INDEX as saved in CONTEXT. */ 224 + 225 + static inline void * 226 + _Unwind_GetGRPtr (struct _Unwind_Context *context, int index) 227 + { 228 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 229 + if (_Unwind_IsExtendedContext (context) && context->by_value[index]) 230 + return &context->reg[index]; 231 + return context->reg[index]; 232 + } 233 + 234 + /* Set the pointer to a register INDEX as saved in CONTEXT. */ 235 + 236 + static inline void 237 + _Unwind_SetGRPtr (struct _Unwind_Context *context, int index, void *p) 238 + { 239 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 240 + if (_Unwind_IsExtendedContext (context)) 241 + context->by_value[index] = 0; 242 + context->reg[index] = p; 243 + } 244 + 245 + /* Overwrite the saved value for register INDEX in CONTEXT with VAL. */ 246 + 247 + static inline void 248 + _Unwind_SetGRValue (struct _Unwind_Context *context, int index, 249 + _Unwind_Word val) 250 + { 251 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 252 + gcc_assert (index < (int) sizeof(dwarf_reg_size_table)); 253 + gcc_assert (dwarf_reg_size_table[index] == sizeof (_Unwind_Ptr)); 254 + 255 + context->by_value[index] = 1; 256 + context->reg[index] = (void *) (_Unwind_Internal_Ptr) val; 257 + } 258 + 259 + /* Return nonzero if register INDEX is stored by value rather than 260 + by reference. */ 261 + 262 + static inline int 263 + _Unwind_GRByValue (struct _Unwind_Context *context, int index) 264 + { 265 + index = DWARF_REG_TO_UNWIND_COLUMN (index); 266 + return context->by_value[index]; 267 + } 268 + 269 + /* Retrieve the return address for CONTEXT. */ 270 + 271 + inline _Unwind_Ptr 272 + _Unwind_GetIP (struct _Unwind_Context *context) 273 + { 274 + return (_Unwind_Ptr) context->ra; 275 + } 276 + 277 + /* Retrieve the return address and flag whether that IP is before 278 + or after first not yet fully executed instruction. */ 279 + 280 + inline _Unwind_Ptr 281 + _Unwind_GetIPInfo (struct _Unwind_Context *context, int *ip_before_insn) 282 + { 283 + *ip_before_insn = _Unwind_IsSignalFrame (context); 284 + return (_Unwind_Ptr) context->ra; 285 + } 286 + 287 + /* Overwrite the return address for CONTEXT with VAL. */ 288 + 289 + inline void 290 + _Unwind_SetIP (struct _Unwind_Context *context, _Unwind_Ptr val) 291 + { 292 + context->ra = (void *) val; 293 + } 294 + 295 + void * 296 + _Unwind_GetLanguageSpecificData (struct _Unwind_Context *context) 297 + { 298 + return context->lsda; 299 + } 300 + 301 + _Unwind_Ptr 302 + _Unwind_GetRegionStart (struct _Unwind_Context *context) 303 + { 304 + return (_Unwind_Ptr) context->bases.func; 305 + } 306 + 307 + void * 308 + _Unwind_FindEnclosingFunction (void *pc) 309 + { 310 + struct dwarf_eh_bases bases; 311 + const struct dwarf_fde *fde = _Unwind_Find_FDE (pc-1, &bases); 312 + if (fde) 313 + return bases.func; 314 + else 315 + return NULL; 316 + } 317 + 318 + #ifndef __ia64__ 319 + _Unwind_Ptr 320 + _Unwind_GetDataRelBase (struct _Unwind_Context *context) 321 + { 322 + return (_Unwind_Ptr) context->bases.dbase; 323 + } 324 + 325 + _Unwind_Ptr 326 + _Unwind_GetTextRelBase (struct _Unwind_Context *context) 327 + { 328 + return (_Unwind_Ptr) context->bases.tbase; 329 + } 330 + #endif 331 + 332 + #ifdef MD_UNWIND_SUPPORT 333 + #include MD_UNWIND_SUPPORT 334 + #endif 335 + 336 + /* Extract any interesting information from the CIE for the translation 337 + unit F belongs to. Return a pointer to the byte after the augmentation, 338 + or NULL if we encountered an undecipherable augmentation. */ 339 + 340 + static const unsigned char * 341 + extract_cie_info (const struct dwarf_cie *cie, struct _Unwind_Context *context, 342 + _Unwind_FrameState *fs) 343 + { 344 + const unsigned char *aug = cie->augmentation; 345 + const unsigned char *p = aug + strlen ((const char *)aug) + 1; 346 + const unsigned char *ret = NULL; 347 + _uleb128_t utmp; 348 + _sleb128_t stmp; 349 + 350 + /* g++ v2 "eh" has pointer immediately following augmentation string, 351 + so it must be handled first. */ 352 + if (aug[0] == 'e' && aug[1] == 'h') 353 + { 354 + fs->eh_ptr = read_pointer (p); 355 + p += sizeof (void *); 356 + aug += 2; 357 + } 358 + 359 + /* After the augmentation resp. pointer for "eh" augmentation 360 + follows for CIE version >= 4 address size byte and 361 + segment size byte. */ 362 + if (__builtin_expect (cie->version >= 4, 0)) 363 + { 364 + if (p[0] != sizeof (void *) || p[1] != 0) 365 + return NULL; 366 + p += 2; 367 + } 368 + /* Immediately following this are the code and 369 + data alignment and return address column. */ 370 + p = read_uleb128 (p, &utmp); 371 + fs->code_align = (_Unwind_Word)utmp; 372 + p = read_sleb128 (p, &stmp); 373 + fs->data_align = (_Unwind_Sword)stmp; 374 + if (cie->version == 1) 375 + fs->retaddr_column = *p++; 376 + else 377 + { 378 + p = read_uleb128 (p, &utmp); 379 + fs->retaddr_column = (_Unwind_Word)utmp; 380 + } 381 + fs->lsda_encoding = DW_EH_PE_omit; 382 + 383 + /* If the augmentation starts with 'z', then a uleb128 immediately 384 + follows containing the length of the augmentation field following 385 + the size. */ 386 + if (*aug == 'z') 387 + { 388 + p = read_uleb128 (p, &utmp); 389 + ret = p + utmp; 390 + 391 + fs->saw_z = 1; 392 + ++aug; 393 + } 394 + 395 + /* Iterate over recognized augmentation subsequences. */ 396 + while (*aug != '\0') 397 + { 398 + /* "L" indicates a byte showing how the LSDA pointer is encoded. */ 399 + if (aug[0] == 'L') 400 + { 401 + fs->lsda_encoding = *p++; 402 + aug += 1; 403 + } 404 + 405 + /* "R" indicates a byte indicating how FDE addresses are encoded. */ 406 + else if (aug[0] == 'R') 407 + { 408 + fs->fde_encoding = *p++; 409 + aug += 1; 410 + } 411 + 412 + /* "P" indicates a personality routine in the CIE augmentation. */ 413 + else if (aug[0] == 'P') 414 + { 415 + _Unwind_Ptr personality; 416 + 417 + p = read_encoded_value (context, *p, p + 1, &personality); 418 + fs->personality = (_Unwind_Personality_Fn) personality; 419 + aug += 1; 420 + } 421 + 422 + /* "S" indicates a signal frame. */ 423 + else if (aug[0] == 'S') 424 + { 425 + fs->signal_frame = 1; 426 + aug += 1; 427 + } 428 + 429 + /* Otherwise we have an unknown augmentation string. 430 + Bail unless we saw a 'z' prefix. */ 431 + else 432 + return ret; 433 + } 434 + 435 + return ret ? ret : p; 436 + } 437 + 438 + 439 + /* Decode a DW_OP stack program. Return the top of stack. Push INITIAL 440 + onto the stack to start. */ 441 + 442 + static _Unwind_Word 443 + execute_stack_op (const unsigned char *op_ptr, const unsigned char *op_end, 444 + struct _Unwind_Context *context, _Unwind_Word initial) 445 + { 446 + _Unwind_Word stack[64]; /* ??? Assume this is enough. */ 447 + int stack_elt; 448 + 449 + stack[0] = initial; 450 + stack_elt = 1; 451 + 452 + while (op_ptr < op_end) 453 + { 454 + enum dwarf_location_atom op = *op_ptr++; 455 + _Unwind_Word result; 456 + _uleb128_t reg, utmp; 457 + _sleb128_t offset, stmp; 458 + 459 + switch (op) 460 + { 461 + case DW_OP_lit0: 462 + case DW_OP_lit1: 463 + case DW_OP_lit2: 464 + case DW_OP_lit3: 465 + case DW_OP_lit4: 466 + case DW_OP_lit5: 467 + case DW_OP_lit6: 468 + case DW_OP_lit7: 469 + case DW_OP_lit8: 470 + case DW_OP_lit9: 471 + case DW_OP_lit10: 472 + case DW_OP_lit11: 473 + case DW_OP_lit12: 474 + case DW_OP_lit13: 475 + case DW_OP_lit14: 476 + case DW_OP_lit15: 477 + case DW_OP_lit16: 478 + case DW_OP_lit17: 479 + case DW_OP_lit18: 480 + case DW_OP_lit19: 481 + case DW_OP_lit20: 482 + case DW_OP_lit21: 483 + case DW_OP_lit22: 484 + case DW_OP_lit23: 485 + case DW_OP_lit24: 486 + case DW_OP_lit25: 487 + case DW_OP_lit26: 488 + case DW_OP_lit27: 489 + case DW_OP_lit28: 490 + case DW_OP_lit29: 491 + case DW_OP_lit30: 492 + case DW_OP_lit31: 493 + result = op - DW_OP_lit0; 494 + break; 495 + 496 + case DW_OP_addr: 497 + result = (_Unwind_Word) (_Unwind_Ptr) read_pointer (op_ptr); 498 + op_ptr += sizeof (void *); 499 + break; 500 + 501 + case DW_OP_GNU_encoded_addr: 502 + { 503 + _Unwind_Ptr presult; 504 + op_ptr = read_encoded_value (context, *op_ptr, op_ptr+1, &presult); 505 + result = presult; 506 + } 507 + break; 508 + 509 + case DW_OP_const1u: 510 + result = read_1u (op_ptr); 511 + op_ptr += 1; 512 + break; 513 + case DW_OP_const1s: 514 + result = read_1s (op_ptr); 515 + op_ptr += 1; 516 + break; 517 + case DW_OP_const2u: 518 + result = read_2u (op_ptr); 519 + op_ptr += 2; 520 + break; 521 + case DW_OP_const2s: 522 + result = read_2s (op_ptr); 523 + op_ptr += 2; 524 + break; 525 + case DW_OP_const4u: 526 + result = read_4u (op_ptr); 527 + op_ptr += 4; 528 + break; 529 + case DW_OP_const4s: 530 + result = read_4s (op_ptr); 531 + op_ptr += 4; 532 + break; 533 + case DW_OP_const8u: 534 + result = read_8u (op_ptr); 535 + op_ptr += 8; 536 + break; 537 + case DW_OP_const8s: 538 + result = read_8s (op_ptr); 539 + op_ptr += 8; 540 + break; 541 + case DW_OP_constu: 542 + op_ptr = read_uleb128 (op_ptr, &utmp); 543 + result = (_Unwind_Word)utmp; 544 + break; 545 + case DW_OP_consts: 546 + op_ptr = read_sleb128 (op_ptr, &stmp); 547 + result = (_Unwind_Sword)stmp; 548 + break; 549 + 550 + case DW_OP_reg0: 551 + case DW_OP_reg1: 552 + case DW_OP_reg2: 553 + case DW_OP_reg3: 554 + case DW_OP_reg4: 555 + case DW_OP_reg5: 556 + case DW_OP_reg6: 557 + case DW_OP_reg7: 558 + case DW_OP_reg8: 559 + case DW_OP_reg9: 560 + case DW_OP_reg10: 561 + case DW_OP_reg11: 562 + case DW_OP_reg12: 563 + case DW_OP_reg13: 564 + case DW_OP_reg14: 565 + case DW_OP_reg15: 566 + case DW_OP_reg16: 567 + case DW_OP_reg17: 568 + case DW_OP_reg18: 569 + case DW_OP_reg19: 570 + case DW_OP_reg20: 571 + case DW_OP_reg21: 572 + case DW_OP_reg22: 573 + case DW_OP_reg23: 574 + case DW_OP_reg24: 575 + case DW_OP_reg25: 576 + case DW_OP_reg26: 577 + case DW_OP_reg27: 578 + case DW_OP_reg28: 579 + case DW_OP_reg29: 580 + case DW_OP_reg30: 581 + case DW_OP_reg31: 582 + result = _Unwind_GetGR (context, op - DW_OP_reg0); 583 + break; 584 + case DW_OP_regx: 585 + op_ptr = read_uleb128 (op_ptr, &reg); 586 + result = _Unwind_GetGR (context, reg); 587 + break; 588 + 589 + case DW_OP_breg0: 590 + case DW_OP_breg1: 591 + case DW_OP_breg2: 592 + case DW_OP_breg3: 593 + case DW_OP_breg4: 594 + case DW_OP_breg5: 595 + case DW_OP_breg6: 596 + case DW_OP_breg7: 597 + case DW_OP_breg8: 598 + case DW_OP_breg9: 599 + case DW_OP_breg10: 600 + case DW_OP_breg11: 601 + case DW_OP_breg12: 602 + case DW_OP_breg13: 603 + case DW_OP_breg14: 604 + case DW_OP_breg15: 605 + case DW_OP_breg16: 606 + case DW_OP_breg17: 607 + case DW_OP_breg18: 608 + case DW_OP_breg19: 609 + case DW_OP_breg20: 610 + case DW_OP_breg21: 611 + case DW_OP_breg22: 612 + case DW_OP_breg23: 613 + case DW_OP_breg24: 614 + case DW_OP_breg25: 615 + case DW_OP_breg26: 616 + case DW_OP_breg27: 617 + case DW_OP_breg28: 618 + case DW_OP_breg29: 619 + case DW_OP_breg30: 620 + case DW_OP_breg31: 621 + op_ptr = read_sleb128 (op_ptr, &offset); 622 + result = _Unwind_GetGR (context, op - DW_OP_breg0) + offset; 623 + break; 624 + case DW_OP_bregx: 625 + op_ptr = read_uleb128 (op_ptr, &reg); 626 + op_ptr = read_sleb128 (op_ptr, &offset); 627 + result = _Unwind_GetGR (context, reg) + (_Unwind_Word)offset; 628 + break; 629 + 630 + case DW_OP_dup: 631 + gcc_assert (stack_elt); 632 + result = stack[stack_elt - 1]; 633 + break; 634 + 635 + case DW_OP_drop: 636 + gcc_assert (stack_elt); 637 + stack_elt -= 1; 638 + goto no_push; 639 + 640 + case DW_OP_pick: 641 + offset = *op_ptr++; 642 + gcc_assert (offset < stack_elt - 1); 643 + result = stack[stack_elt - 1 - offset]; 644 + break; 645 + 646 + case DW_OP_over: 647 + gcc_assert (stack_elt >= 2); 648 + result = stack[stack_elt - 2]; 649 + break; 650 + 651 + case DW_OP_swap: 652 + { 653 + _Unwind_Word t; 654 + gcc_assert (stack_elt >= 2); 655 + t = stack[stack_elt - 1]; 656 + stack[stack_elt - 1] = stack[stack_elt - 2]; 657 + stack[stack_elt - 2] = t; 658 + goto no_push; 659 + } 660 + 661 + case DW_OP_rot: 662 + { 663 + _Unwind_Word t1, t2, t3; 664 + 665 + gcc_assert (stack_elt >= 3); 666 + t1 = stack[stack_elt - 1]; 667 + t2 = stack[stack_elt - 2]; 668 + t3 = stack[stack_elt - 3]; 669 + stack[stack_elt - 1] = t2; 670 + stack[stack_elt - 2] = t3; 671 + stack[stack_elt - 3] = t1; 672 + goto no_push; 673 + } 674 + 675 + case DW_OP_deref: 676 + case DW_OP_deref_size: 677 + case DW_OP_abs: 678 + case DW_OP_neg: 679 + case DW_OP_not: 680 + case DW_OP_plus_uconst: 681 + /* Unary operations. */ 682 + gcc_assert (stack_elt); 683 + stack_elt -= 1; 684 + 685 + result = stack[stack_elt]; 686 + 687 + switch (op) 688 + { 689 + case DW_OP_deref: 690 + { 691 + void *ptr = (void *) (_Unwind_Ptr) result; 692 + result = (_Unwind_Ptr) read_pointer (ptr); 693 + } 694 + break; 695 + 696 + case DW_OP_deref_size: 697 + { 698 + void *ptr = (void *) (_Unwind_Ptr) result; 699 + switch (*op_ptr++) 700 + { 701 + case 1: 702 + result = read_1u (ptr); 703 + break; 704 + case 2: 705 + result = read_2u (ptr); 706 + break; 707 + case 4: 708 + result = read_4u (ptr); 709 + break; 710 + case 8: 711 + result = read_8u (ptr); 712 + break; 713 + default: 714 + gcc_unreachable (); 715 + } 716 + } 717 + break; 718 + 719 + case DW_OP_abs: 720 + if ((_Unwind_Sword) result < 0) 721 + result = -result; 722 + break; 723 + case DW_OP_neg: 724 + result = -result; 725 + break; 726 + case DW_OP_not: 727 + result = ~result; 728 + break; 729 + case DW_OP_plus_uconst: 730 + op_ptr = read_uleb128 (op_ptr, &utmp); 731 + result += (_Unwind_Word)utmp; 732 + break; 733 + 734 + default: 735 + gcc_unreachable (); 736 + } 737 + break; 738 + 739 + case DW_OP_and: 740 + case DW_OP_div: 741 + case DW_OP_minus: 742 + case DW_OP_mod: 743 + case DW_OP_mul: 744 + case DW_OP_or: 745 + case DW_OP_plus: 746 + case DW_OP_shl: 747 + case DW_OP_shr: 748 + case DW_OP_shra: 749 + case DW_OP_xor: 750 + case DW_OP_le: 751 + case DW_OP_ge: 752 + case DW_OP_eq: 753 + case DW_OP_lt: 754 + case DW_OP_gt: 755 + case DW_OP_ne: 756 + { 757 + /* Binary operations. */ 758 + _Unwind_Word first, second; 759 + gcc_assert (stack_elt >= 2); 760 + stack_elt -= 2; 761 + 762 + second = stack[stack_elt]; 763 + first = stack[stack_elt + 1]; 764 + 765 + switch (op) 766 + { 767 + case DW_OP_and: 768 + result = second & first; 769 + break; 770 + case DW_OP_div: 771 + result = (_Unwind_Sword) second / (_Unwind_Sword) first; 772 + break; 773 + case DW_OP_minus: 774 + result = second - first; 775 + break; 776 + case DW_OP_mod: 777 + result = second % first; 778 + break; 779 + case DW_OP_mul: 780 + result = second * first; 781 + break; 782 + case DW_OP_or: 783 + result = second | first; 784 + break; 785 + case DW_OP_plus: 786 + result = second + first; 787 + break; 788 + case DW_OP_shl: 789 + result = second << first; 790 + break; 791 + case DW_OP_shr: 792 + result = second >> first; 793 + break; 794 + case DW_OP_shra: 795 + result = (_Unwind_Sword) second >> first; 796 + break; 797 + case DW_OP_xor: 798 + result = second ^ first; 799 + break; 800 + case DW_OP_le: 801 + result = (_Unwind_Sword) second <= (_Unwind_Sword) first; 802 + break; 803 + case DW_OP_ge: 804 + result = (_Unwind_Sword) second >= (_Unwind_Sword) first; 805 + break; 806 + case DW_OP_eq: 807 + result = (_Unwind_Sword) second == (_Unwind_Sword) first; 808 + break; 809 + case DW_OP_lt: 810 + result = (_Unwind_Sword) second < (_Unwind_Sword) first; 811 + break; 812 + case DW_OP_gt: 813 + result = (_Unwind_Sword) second > (_Unwind_Sword) first; 814 + break; 815 + case DW_OP_ne: 816 + result = (_Unwind_Sword) second != (_Unwind_Sword) first; 817 + break; 818 + 819 + default: 820 + gcc_unreachable (); 821 + } 822 + } 823 + break; 824 + 825 + case DW_OP_skip: 826 + offset = read_2s (op_ptr); 827 + op_ptr += 2; 828 + op_ptr += offset; 829 + goto no_push; 830 + 831 + case DW_OP_bra: 832 + gcc_assert (stack_elt); 833 + stack_elt -= 1; 834 + 835 + offset = read_2s (op_ptr); 836 + op_ptr += 2; 837 + if (stack[stack_elt] != 0) 838 + op_ptr += offset; 839 + goto no_push; 840 + 841 + case DW_OP_nop: 842 + goto no_push; 843 + 844 + default: 845 + gcc_unreachable (); 846 + } 847 + 848 + /* Most things push a result value. */ 849 + gcc_assert ((size_t) stack_elt < sizeof(stack)/sizeof(*stack)); 850 + stack[stack_elt++] = result; 851 + no_push:; 852 + } 853 + 854 + /* We were executing this program to get a value. It should be 855 + at top of stack. */ 856 + gcc_assert (stack_elt); 857 + stack_elt -= 1; 858 + return stack[stack_elt]; 859 + } 860 + 861 + 862 + /* Decode DWARF 2 call frame information. Takes pointers the 863 + instruction sequence to decode, current register information and 864 + CIE info, and the PC range to evaluate. */ 865 + 866 + static void 867 + execute_cfa_program (const unsigned char *insn_ptr, 868 + const unsigned char *insn_end, 869 + struct _Unwind_Context *context, 870 + _Unwind_FrameState *fs) 871 + { 872 + struct frame_state_reg_info *unused_rs = NULL; 873 + 874 + /* Don't allow remember/restore between CIE and FDE programs. */ 875 + fs->regs.prev = NULL; 876 + 877 + /* The comparison with the return address uses < rather than <= because 878 + we are only interested in the effects of code before the call; for a 879 + noreturn function, the return address may point to unrelated code with 880 + a different stack configuration that we are not interested in. We 881 + assume that the call itself is unwind info-neutral; if not, or if 882 + there are delay instructions that adjust the stack, these must be 883 + reflected at the point immediately before the call insn. 884 + In signal frames, return address is after last completed instruction, 885 + so we add 1 to return address to make the comparison <=. */ 886 + while (insn_ptr < insn_end 887 + && fs->pc < context->ra + _Unwind_IsSignalFrame (context)) 888 + { 889 + unsigned char insn = *insn_ptr++; 890 + _uleb128_t reg, utmp; 891 + _sleb128_t offset, stmp; 892 + 893 + if ((insn & 0xc0) == DW_CFA_advance_loc) 894 + fs->pc += (insn & 0x3f) * fs->code_align; 895 + else if ((insn & 0xc0) == DW_CFA_offset) 896 + { 897 + reg = insn & 0x3f; 898 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 899 + offset = (_Unwind_Sword) utmp * fs->data_align; 900 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 901 + = REG_SAVED_OFFSET; 902 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = offset; 903 + } 904 + else if ((insn & 0xc0) == DW_CFA_restore) 905 + { 906 + reg = insn & 0x3f; 907 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how = REG_UNSAVED; 908 + } 909 + else switch (insn) 910 + { 911 + case DW_CFA_set_loc: 912 + { 913 + _Unwind_Ptr pc; 914 + 915 + insn_ptr = read_encoded_value (context, fs->fde_encoding, 916 + insn_ptr, &pc); 917 + fs->pc = (void *) pc; 918 + } 919 + break; 920 + 921 + case DW_CFA_advance_loc1: 922 + fs->pc += read_1u (insn_ptr) * fs->code_align; 923 + insn_ptr += 1; 924 + break; 925 + case DW_CFA_advance_loc2: 926 + fs->pc += read_2u (insn_ptr) * fs->code_align; 927 + insn_ptr += 2; 928 + break; 929 + case DW_CFA_advance_loc4: 930 + fs->pc += read_4u (insn_ptr) * fs->code_align; 931 + insn_ptr += 4; 932 + break; 933 + 934 + case DW_CFA_offset_extended: 935 + insn_ptr = read_uleb128 (insn_ptr, &reg); 936 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 937 + offset = (_Unwind_Sword) utmp * fs->data_align; 938 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 939 + = REG_SAVED_OFFSET; 940 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = offset; 941 + break; 942 + 943 + case DW_CFA_restore_extended: 944 + insn_ptr = read_uleb128 (insn_ptr, &reg); 945 + /* FIXME, this is wrong; the CIE might have said that the 946 + register was saved somewhere. */ 947 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN(reg)].how = REG_UNSAVED; 948 + break; 949 + 950 + case DW_CFA_same_value: 951 + insn_ptr = read_uleb128 (insn_ptr, &reg); 952 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN(reg)].how = REG_UNSAVED; 953 + break; 954 + 955 + case DW_CFA_undefined: 956 + insn_ptr = read_uleb128 (insn_ptr, &reg); 957 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN(reg)].how = REG_UNDEFINED; 958 + break; 959 + 960 + case DW_CFA_nop: 961 + break; 962 + 963 + case DW_CFA_register: 964 + { 965 + _uleb128_t reg2; 966 + insn_ptr = read_uleb128 (insn_ptr, &reg); 967 + insn_ptr = read_uleb128 (insn_ptr, &reg2); 968 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how = REG_SAVED_REG; 969 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.reg = 970 + (_Unwind_Word)reg2; 971 + } 972 + break; 973 + 974 + case DW_CFA_remember_state: 975 + { 976 + struct frame_state_reg_info *new_rs; 977 + if (unused_rs) 978 + { 979 + new_rs = unused_rs; 980 + unused_rs = unused_rs->prev; 981 + } 982 + else 983 + new_rs = alloca (sizeof (struct frame_state_reg_info)); 984 + 985 + *new_rs = fs->regs; 986 + fs->regs.prev = new_rs; 987 + } 988 + break; 989 + 990 + case DW_CFA_restore_state: 991 + { 992 + struct frame_state_reg_info *old_rs = fs->regs.prev; 993 + fs->regs = *old_rs; 994 + old_rs->prev = unused_rs; 995 + unused_rs = old_rs; 996 + } 997 + break; 998 + 999 + case DW_CFA_def_cfa: 1000 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1001 + fs->regs.cfa_reg = (_Unwind_Word)utmp; 1002 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1003 + fs->regs.cfa_offset = (_Unwind_Word)utmp; 1004 + fs->regs.cfa_how = CFA_REG_OFFSET; 1005 + break; 1006 + 1007 + case DW_CFA_def_cfa_register: 1008 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1009 + fs->regs.cfa_reg = (_Unwind_Word)utmp; 1010 + fs->regs.cfa_how = CFA_REG_OFFSET; 1011 + break; 1012 + 1013 + case DW_CFA_def_cfa_offset: 1014 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1015 + fs->regs.cfa_offset = utmp; 1016 + /* cfa_how deliberately not set. */ 1017 + break; 1018 + 1019 + case DW_CFA_def_cfa_expression: 1020 + fs->regs.cfa_exp = insn_ptr; 1021 + fs->regs.cfa_how = CFA_EXP; 1022 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1023 + insn_ptr += utmp; 1024 + break; 1025 + 1026 + case DW_CFA_expression: 1027 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1028 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how = REG_SAVED_EXP; 1029 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.exp = insn_ptr; 1030 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1031 + insn_ptr += utmp; 1032 + break; 1033 + 1034 + /* Dwarf3. */ 1035 + case DW_CFA_offset_extended_sf: 1036 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1037 + insn_ptr = read_sleb128 (insn_ptr, &stmp); 1038 + offset = stmp * fs->data_align; 1039 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 1040 + = REG_SAVED_OFFSET; 1041 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = offset; 1042 + break; 1043 + 1044 + case DW_CFA_def_cfa_sf: 1045 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1046 + fs->regs.cfa_reg = (_Unwind_Word)utmp; 1047 + insn_ptr = read_sleb128 (insn_ptr, &stmp); 1048 + fs->regs.cfa_offset = (_Unwind_Sword)stmp; 1049 + fs->regs.cfa_how = CFA_REG_OFFSET; 1050 + fs->regs.cfa_offset *= fs->data_align; 1051 + break; 1052 + 1053 + case DW_CFA_def_cfa_offset_sf: 1054 + insn_ptr = read_sleb128 (insn_ptr, &stmp); 1055 + fs->regs.cfa_offset = (_Unwind_Sword)stmp; 1056 + fs->regs.cfa_offset *= fs->data_align; 1057 + /* cfa_how deliberately not set. */ 1058 + break; 1059 + 1060 + case DW_CFA_val_offset: 1061 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1062 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1063 + offset = (_Unwind_Sword) utmp * fs->data_align; 1064 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 1065 + = REG_SAVED_VAL_OFFSET; 1066 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = offset; 1067 + break; 1068 + 1069 + case DW_CFA_val_offset_sf: 1070 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1071 + insn_ptr = read_sleb128 (insn_ptr, &stmp); 1072 + offset = stmp * fs->data_align; 1073 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 1074 + = REG_SAVED_VAL_OFFSET; 1075 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = offset; 1076 + break; 1077 + 1078 + case DW_CFA_val_expression: 1079 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1080 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 1081 + = REG_SAVED_VAL_EXP; 1082 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.exp = insn_ptr; 1083 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1084 + insn_ptr += utmp; 1085 + break; 1086 + 1087 + case DW_CFA_GNU_window_save: 1088 + /* ??? Hardcoded for SPARC register window configuration. */ 1089 + for (reg = 16; reg < 32; ++reg) 1090 + { 1091 + fs->regs.reg[reg].how = REG_SAVED_OFFSET; 1092 + fs->regs.reg[reg].loc.offset = (reg - 16) * sizeof (void *); 1093 + } 1094 + break; 1095 + 1096 + case DW_CFA_GNU_args_size: 1097 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1098 + context->args_size = (_Unwind_Word)utmp; 1099 + break; 1100 + 1101 + case DW_CFA_GNU_negative_offset_extended: 1102 + /* Obsoleted by DW_CFA_offset_extended_sf, but used by 1103 + older PowerPC code. */ 1104 + insn_ptr = read_uleb128 (insn_ptr, &reg); 1105 + insn_ptr = read_uleb128 (insn_ptr, &utmp); 1106 + offset = (_Unwind_Word) utmp * fs->data_align; 1107 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].how 1108 + = REG_SAVED_OFFSET; 1109 + fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (reg)].loc.offset = -offset; 1110 + break; 1111 + 1112 + default: 1113 + gcc_unreachable (); 1114 + } 1115 + } 1116 + } 1117 + 1118 + /* Given the _Unwind_Context CONTEXT for a stack frame, look up the FDE for 1119 + its caller and decode it into FS. This function also sets the 1120 + args_size and lsda members of CONTEXT, as they are really information 1121 + about the caller's frame. */ 1122 + 1123 + static _Unwind_Reason_Code 1124 + uw_frame_state_for (struct _Unwind_Context *context, _Unwind_FrameState *fs) 1125 + { 1126 + const struct dwarf_fde *fde; 1127 + const struct dwarf_cie *cie; 1128 + const unsigned char *aug, *insn, *end; 1129 + 1130 + memset (fs, 0, sizeof (*fs)); 1131 + context->args_size = 0; 1132 + context->lsda = 0; 1133 + 1134 + if (context->ra == 0) 1135 + return _URC_END_OF_STACK; 1136 + 1137 + fde = _Unwind_Find_FDE (context->ra + _Unwind_IsSignalFrame (context) - 1, 1138 + &context->bases); 1139 + if (fde == NULL) 1140 + { 1141 + #ifdef MD_FALLBACK_FRAME_STATE_FOR 1142 + /* Couldn't find frame unwind info for this function. Try a 1143 + target-specific fallback mechanism. This will necessarily 1144 + not provide a personality routine or LSDA. */ 1145 + return MD_FALLBACK_FRAME_STATE_FOR (context, fs); 1146 + #else 1147 + return _URC_END_OF_STACK; 1148 + #endif 1149 + } 1150 + 1151 + fs->pc = context->bases.func; 1152 + 1153 + cie = get_cie (fde); 1154 + insn = extract_cie_info (cie, context, fs); 1155 + if (insn == NULL) 1156 + /* CIE contained unknown augmentation. */ 1157 + return _URC_FATAL_PHASE1_ERROR; 1158 + 1159 + /* First decode all the insns in the CIE. */ 1160 + end = (const unsigned char *) next_fde ((const struct dwarf_fde *) cie); 1161 + execute_cfa_program (insn, end, context, fs); 1162 + 1163 + /* Locate augmentation for the fde. */ 1164 + aug = (const unsigned char *) fde + sizeof (*fde); 1165 + aug += 2 * size_of_encoded_value (fs->fde_encoding); 1166 + insn = NULL; 1167 + if (fs->saw_z) 1168 + { 1169 + _uleb128_t i; 1170 + aug = read_uleb128 (aug, &i); 1171 + insn = aug + i; 1172 + } 1173 + if (fs->lsda_encoding != DW_EH_PE_omit) 1174 + { 1175 + _Unwind_Ptr lsda; 1176 + 1177 + aug = read_encoded_value (context, fs->lsda_encoding, aug, &lsda); 1178 + context->lsda = (void *) lsda; 1179 + } 1180 + 1181 + /* Then the insns in the FDE up to our target PC. */ 1182 + if (insn == NULL) 1183 + insn = aug; 1184 + end = (const unsigned char *) next_fde (fde); 1185 + execute_cfa_program (insn, end, context, fs); 1186 + 1187 + return _URC_NO_REASON; 1188 + } 1189 + 1190 + typedef struct frame_state 1191 + { 1192 + void *cfa; 1193 + void *eh_ptr; 1194 + long cfa_offset; 1195 + long args_size; 1196 + long reg_or_offset[PRE_GCC3_DWARF_FRAME_REGISTERS+1]; 1197 + unsigned short cfa_reg; 1198 + unsigned short retaddr_column; 1199 + char saved[PRE_GCC3_DWARF_FRAME_REGISTERS+1]; 1200 + } frame_state; 1201 + 1202 + struct frame_state * __frame_state_for (void *, struct frame_state *); 1203 + 1204 + /* Called from pre-G++ 3.0 __throw to find the registers to restore for 1205 + a given PC_TARGET. The caller should allocate a local variable of 1206 + `struct frame_state' and pass its address to STATE_IN. */ 1207 + 1208 + struct frame_state * 1209 + __frame_state_for (void *pc_target, struct frame_state *state_in) 1210 + { 1211 + struct _Unwind_Context context; 1212 + _Unwind_FrameState fs; 1213 + int reg; 1214 + 1215 + memset (&context, 0, sizeof (struct _Unwind_Context)); 1216 + context.flags = EXTENDED_CONTEXT_BIT; 1217 + context.ra = pc_target + 1; 1218 + 1219 + if (uw_frame_state_for (&context, &fs) != _URC_NO_REASON) 1220 + return 0; 1221 + 1222 + /* We have no way to pass a location expression for the CFA to our 1223 + caller. It wouldn't understand it anyway. */ 1224 + if (fs.regs.cfa_how == CFA_EXP) 1225 + return 0; 1226 + 1227 + for (reg = 0; reg < PRE_GCC3_DWARF_FRAME_REGISTERS + 1; reg++) 1228 + { 1229 + state_in->saved[reg] = fs.regs.reg[reg].how; 1230 + switch (state_in->saved[reg]) 1231 + { 1232 + case REG_SAVED_REG: 1233 + state_in->reg_or_offset[reg] = fs.regs.reg[reg].loc.reg; 1234 + break; 1235 + case REG_SAVED_OFFSET: 1236 + state_in->reg_or_offset[reg] = fs.regs.reg[reg].loc.offset; 1237 + break; 1238 + default: 1239 + state_in->reg_or_offset[reg] = 0; 1240 + break; 1241 + } 1242 + } 1243 + 1244 + state_in->cfa_offset = fs.regs.cfa_offset; 1245 + state_in->cfa_reg = fs.regs.cfa_reg; 1246 + state_in->retaddr_column = fs.retaddr_column; 1247 + state_in->args_size = context.args_size; 1248 + state_in->eh_ptr = fs.eh_ptr; 1249 + 1250 + return state_in; 1251 + } 1252 + 1253 + typedef union { _Unwind_Ptr ptr; _Unwind_Word word; } _Unwind_SpTmp; 1254 + 1255 + static inline void 1256 + _Unwind_SetSpColumn (struct _Unwind_Context *context, void *cfa, 1257 + _Unwind_SpTmp *tmp_sp) 1258 + { 1259 + int size = dwarf_reg_size_table[__builtin_dwarf_sp_column ()]; 1260 + 1261 + if (size == sizeof(_Unwind_Ptr)) 1262 + tmp_sp->ptr = (_Unwind_Ptr) cfa; 1263 + else 1264 + { 1265 + gcc_assert (size == sizeof(_Unwind_Word)); 1266 + tmp_sp->word = (_Unwind_Ptr) cfa; 1267 + } 1268 + _Unwind_SetGRPtr (context, __builtin_dwarf_sp_column (), tmp_sp); 1269 + } 1270 + 1271 + static void 1272 + uw_update_context_1 (struct _Unwind_Context *context, _Unwind_FrameState *fs) 1273 + { 1274 + struct _Unwind_Context orig_context = *context; 1275 + void *cfa; 1276 + long i; 1277 + 1278 + #ifdef EH_RETURN_STACKADJ_RTX 1279 + /* Special handling here: Many machines do not use a frame pointer, 1280 + and track the CFA only through offsets from the stack pointer from 1281 + one frame to the next. In this case, the stack pointer is never 1282 + stored, so it has no saved address in the context. What we do 1283 + have is the CFA from the previous stack frame. 1284 + 1285 + In very special situations (such as unwind info for signal return), 1286 + there may be location expressions that use the stack pointer as well. 1287 + 1288 + Do this conditionally for one frame. This allows the unwind info 1289 + for one frame to save a copy of the stack pointer from the previous 1290 + frame, and be able to use much easier CFA mechanisms to do it. 1291 + Always zap the saved stack pointer value for the next frame; carrying 1292 + the value over from one frame to another doesn't make sense. */ 1293 + 1294 + _Unwind_SpTmp tmp_sp; 1295 + 1296 + if (!_Unwind_GetGRPtr (&orig_context, __builtin_dwarf_sp_column ())) 1297 + _Unwind_SetSpColumn (&orig_context, context->cfa, &tmp_sp); 1298 + _Unwind_SetGRPtr (context, __builtin_dwarf_sp_column (), NULL); 1299 + #endif 1300 + 1301 + /* Compute this frame's CFA. */ 1302 + switch (fs->regs.cfa_how) 1303 + { 1304 + case CFA_REG_OFFSET: 1305 + cfa = _Unwind_GetPtr (&orig_context, fs->regs.cfa_reg); 1306 + cfa += fs->regs.cfa_offset; 1307 + break; 1308 + 1309 + case CFA_EXP: 1310 + { 1311 + const unsigned char *exp = fs->regs.cfa_exp; 1312 + _uleb128_t len; 1313 + 1314 + exp = read_uleb128 (exp, &len); 1315 + cfa = (void *) (_Unwind_Ptr) 1316 + execute_stack_op (exp, exp + len, &orig_context, 0); 1317 + break; 1318 + } 1319 + 1320 + default: 1321 + gcc_unreachable (); 1322 + } 1323 + context->cfa = cfa; 1324 + 1325 + /* Compute the addresses of all registers saved in this frame. */ 1326 + for (i = 0; i < DWARF_FRAME_REGISTERS + 1; ++i) 1327 + switch (fs->regs.reg[i].how) 1328 + { 1329 + case REG_UNSAVED: 1330 + case REG_UNDEFINED: 1331 + break; 1332 + 1333 + case REG_SAVED_OFFSET: 1334 + _Unwind_SetGRPtr (context, i, 1335 + (void *) (cfa + fs->regs.reg[i].loc.offset)); 1336 + break; 1337 + 1338 + case REG_SAVED_REG: 1339 + if (_Unwind_GRByValue (&orig_context, fs->regs.reg[i].loc.reg)) 1340 + _Unwind_SetGRValue (context, i, 1341 + _Unwind_GetGR (&orig_context, 1342 + fs->regs.reg[i].loc.reg)); 1343 + else 1344 + _Unwind_SetGRPtr (context, i, 1345 + _Unwind_GetGRPtr (&orig_context, 1346 + fs->regs.reg[i].loc.reg)); 1347 + break; 1348 + 1349 + case REG_SAVED_EXP: 1350 + { 1351 + const unsigned char *exp = fs->regs.reg[i].loc.exp; 1352 + _uleb128_t len; 1353 + _Unwind_Ptr val; 1354 + 1355 + exp = read_uleb128 (exp, &len); 1356 + val = execute_stack_op (exp, exp + len, &orig_context, 1357 + (_Unwind_Ptr) cfa); 1358 + _Unwind_SetGRPtr (context, i, (void *) val); 1359 + } 1360 + break; 1361 + 1362 + case REG_SAVED_VAL_OFFSET: 1363 + _Unwind_SetGRValue (context, i, 1364 + (_Unwind_Internal_Ptr) 1365 + (cfa + fs->regs.reg[i].loc.offset)); 1366 + break; 1367 + 1368 + case REG_SAVED_VAL_EXP: 1369 + { 1370 + const unsigned char *exp = fs->regs.reg[i].loc.exp; 1371 + _uleb128_t len; 1372 + _Unwind_Ptr val; 1373 + 1374 + exp = read_uleb128 (exp, &len); 1375 + val = execute_stack_op (exp, exp + len, &orig_context, 1376 + (_Unwind_Ptr) cfa); 1377 + _Unwind_SetGRValue (context, i, val); 1378 + } 1379 + break; 1380 + } 1381 + 1382 + _Unwind_SetSignalFrame (context, fs->signal_frame); 1383 + 1384 + #ifdef MD_FROB_UPDATE_CONTEXT 1385 + MD_FROB_UPDATE_CONTEXT (context, fs); 1386 + #endif 1387 + } 1388 + 1389 + /* CONTEXT describes the unwind state for a frame, and FS describes the FDE 1390 + of its caller. Update CONTEXT to refer to the caller as well. Note 1391 + that the args_size and lsda members are not updated here, but later in 1392 + uw_frame_state_for. */ 1393 + 1394 + static void 1395 + uw_update_context (struct _Unwind_Context *context, _Unwind_FrameState *fs) 1396 + { 1397 + uw_update_context_1 (context, fs); 1398 + 1399 + /* In general this unwinder doesn't make any distinction between 1400 + undefined and same_value rule. Call-saved registers are assumed 1401 + to have same_value rule by default and explicit undefined 1402 + rule is handled like same_value. The only exception is 1403 + DW_CFA_undefined on retaddr_column which is supposed to 1404 + mark outermost frame in DWARF 3. */ 1405 + if (fs->regs.reg[DWARF_REG_TO_UNWIND_COLUMN (fs->retaddr_column)].how 1406 + == REG_UNDEFINED) 1407 + /* uw_frame_state_for uses context->ra == 0 check to find outermost 1408 + stack frame. */ 1409 + context->ra = 0; 1410 + else 1411 + /* Compute the return address now, since the return address column 1412 + can change from frame to frame. */ 1413 + context->ra = __builtin_extract_return_addr 1414 + (_Unwind_GetPtr (context, fs->retaddr_column)); 1415 + } 1416 + 1417 + static void 1418 + uw_advance_context (struct _Unwind_Context *context, _Unwind_FrameState *fs) 1419 + { 1420 + uw_update_context (context, fs); 1421 + } 1422 + 1423 + /* Fill in CONTEXT for top-of-stack. The only valid registers at this 1424 + level will be the return address and the CFA. */ 1425 + 1426 + #define uw_init_context(CONTEXT) \ 1427 + do \ 1428 + { \ 1429 + /* Do any necessary initialization to access arbitrary stack frames. \ 1430 + On the SPARC, this means flushing the register windows. */ \ 1431 + __builtin_unwind_init (); \ 1432 + uw_init_context_1 (CONTEXT, __builtin_dwarf_cfa (), \ 1433 + __builtin_return_address (0)); \ 1434 + } \ 1435 + while (0) 1436 + 1437 + static inline void 1438 + init_dwarf_reg_size_table (void) 1439 + { 1440 + __builtin_init_dwarf_reg_size_table (dwarf_reg_size_table); 1441 + } 1442 + 1443 + static void __attribute__((noinline)) 1444 + uw_init_context_1 (struct _Unwind_Context *context, 1445 + void *outer_cfa, void *outer_ra) 1446 + { 1447 + void *ra = __builtin_extract_return_addr (__builtin_return_address (0)); 1448 + _Unwind_FrameState fs; 1449 + _Unwind_SpTmp sp_slot; 1450 + _Unwind_Reason_Code code; 1451 + 1452 + memset (context, 0, sizeof (struct _Unwind_Context)); 1453 + context->ra = ra; 1454 + context->flags = EXTENDED_CONTEXT_BIT; 1455 + 1456 + code = uw_frame_state_for (context, &fs); 1457 + gcc_assert (code == _URC_NO_REASON); 1458 + 1459 + #if __GTHREADS 1460 + { 1461 + static __gthread_once_t once_regsizes = __GTHREAD_ONCE_INIT; 1462 + if (__gthread_once (&once_regsizes, init_dwarf_reg_size_table) != 0 1463 + && dwarf_reg_size_table[0] == 0) 1464 + init_dwarf_reg_size_table (); 1465 + } 1466 + #else 1467 + if (dwarf_reg_size_table[0] == 0) 1468 + init_dwarf_reg_size_table (); 1469 + #endif 1470 + 1471 + /* Force the frame state to use the known cfa value. */ 1472 + _Unwind_SetSpColumn (context, outer_cfa, &sp_slot); 1473 + fs.regs.cfa_how = CFA_REG_OFFSET; 1474 + fs.regs.cfa_reg = __builtin_dwarf_sp_column (); 1475 + fs.regs.cfa_offset = 0; 1476 + 1477 + uw_update_context_1 (context, &fs); 1478 + 1479 + /* If the return address column was saved in a register in the 1480 + initialization context, then we can't see it in the given 1481 + call frame data. So have the initialization context tell us. */ 1482 + context->ra = __builtin_extract_return_addr (outer_ra); 1483 + } 1484 + 1485 + static void _Unwind_DebugHook (void *, void *) 1486 + __attribute__ ((__noinline__, __used__, __noclone__)); 1487 + 1488 + /* This function is called during unwinding. It is intended as a hook 1489 + for a debugger to intercept exceptions. CFA is the CFA of the 1490 + target frame. HANDLER is the PC to which control will be 1491 + transferred. */ 1492 + static void 1493 + _Unwind_DebugHook (void *cfa __attribute__ ((__unused__)), 1494 + void *handler __attribute__ ((__unused__))) 1495 + { 1496 + asm (""); 1497 + } 1498 + 1499 + /* Install TARGET into CURRENT so that we can return to it. This is a 1500 + macro because __builtin_eh_return must be invoked in the context of 1501 + our caller. */ 1502 + 1503 + #define uw_install_context(CURRENT, TARGET) \ 1504 + do \ 1505 + { \ 1506 + long offset = uw_install_context_1 ((CURRENT), (TARGET)); \ 1507 + void *handler = __builtin_frob_return_addr ((TARGET)->ra); \ 1508 + _Unwind_DebugHook ((TARGET)->cfa, handler); \ 1509 + __builtin_eh_return (offset, handler); \ 1510 + } \ 1511 + while (0) 1512 + 1513 + static long 1514 + uw_install_context_1 (struct _Unwind_Context *current, 1515 + struct _Unwind_Context *target) 1516 + { 1517 + long i; 1518 + _Unwind_SpTmp sp_slot; 1519 + 1520 + /* If the target frame does not have a saved stack pointer, 1521 + then set up the target's CFA. */ 1522 + if (!_Unwind_GetGRPtr (target, __builtin_dwarf_sp_column ())) 1523 + _Unwind_SetSpColumn (target, target->cfa, &sp_slot); 1524 + 1525 + for (i = 0; i < DWARF_FRAME_REGISTERS; ++i) 1526 + { 1527 + void *c = current->reg[i]; 1528 + void *t = target->reg[i]; 1529 + 1530 + gcc_assert (current->by_value[i] == 0); 1531 + if (target->by_value[i] && c) 1532 + { 1533 + _Unwind_Word w; 1534 + _Unwind_Ptr p; 1535 + if (dwarf_reg_size_table[i] == sizeof (_Unwind_Word)) 1536 + { 1537 + w = (_Unwind_Internal_Ptr) t; 1538 + memcpy (c, &w, sizeof (_Unwind_Word)); 1539 + } 1540 + else 1541 + { 1542 + gcc_assert (dwarf_reg_size_table[i] == sizeof (_Unwind_Ptr)); 1543 + p = (_Unwind_Internal_Ptr) t; 1544 + memcpy (c, &p, sizeof (_Unwind_Ptr)); 1545 + } 1546 + } 1547 + else if (t && c && t != c) 1548 + memcpy (c, t, dwarf_reg_size_table[i]); 1549 + } 1550 + 1551 + /* If the current frame doesn't have a saved stack pointer, then we 1552 + need to rely on EH_RETURN_STACKADJ_RTX to get our target stack 1553 + pointer value reloaded. */ 1554 + if (!_Unwind_GetGRPtr (current, __builtin_dwarf_sp_column ())) 1555 + { 1556 + void *target_cfa; 1557 + 1558 + target_cfa = _Unwind_GetPtr (target, __builtin_dwarf_sp_column ()); 1559 + 1560 + /* We adjust SP by the difference between CURRENT and TARGET's CFA. */ 1561 + if (STACK_GROWS_DOWNWARD) 1562 + return target_cfa - current->cfa + target->args_size; 1563 + else 1564 + return current->cfa - target_cfa - target->args_size; 1565 + } 1566 + return 0; 1567 + } 1568 + 1569 + static inline _Unwind_Ptr 1570 + uw_identify_context (struct _Unwind_Context *context) 1571 + { 1572 + /* The CFA is not sufficient to disambiguate the context of a function 1573 + interrupted by a signal before establishing its frame and the context 1574 + of the signal itself. */ 1575 + if (STACK_GROWS_DOWNWARD) 1576 + return _Unwind_GetCFA (context) - _Unwind_IsSignalFrame (context); 1577 + else 1578 + return _Unwind_GetCFA (context) + _Unwind_IsSignalFrame (context); 1579 + } 1580 + 1581 + 1582 + #include "unwind.inc" 1583 + 1584 + #if defined (USE_GAS_SYMVER) && defined (SHARED) && defined (USE_LIBUNWIND_EXCEPTIONS) 1585 + alias (_Unwind_Backtrace); 1586 + alias (_Unwind_DeleteException); 1587 + alias (_Unwind_FindEnclosingFunction); 1588 + alias (_Unwind_ForcedUnwind); 1589 + alias (_Unwind_GetDataRelBase); 1590 + alias (_Unwind_GetTextRelBase); 1591 + alias (_Unwind_GetCFA); 1592 + alias (_Unwind_GetGR); 1593 + alias (_Unwind_GetIP); 1594 + alias (_Unwind_GetLanguageSpecificData); 1595 + alias (_Unwind_GetRegionStart); 1596 + alias (_Unwind_RaiseException); 1597 + alias (_Unwind_Resume); 1598 + alias (_Unwind_Resume_or_Rethrow); 1599 + alias (_Unwind_SetGR); 1600 + alias (_Unwind_SetIP); 1601 + #endif 1602 + 1603 + #endif /* !USING_SJLJ_EXCEPTIONS */
+87
src/libunwind-darwin/unwind-dw2.h
··· 1 + /* DWARF2 frame unwind data structure. 2 + Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2009 3 + Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + /* A target can override (perhaps for backward compatibility) how 27 + many dwarf2 columns are unwound. */ 28 + #ifndef DWARF_FRAME_REGISTERS 29 + #define DWARF_FRAME_REGISTERS FIRST_PSEUDO_REGISTER 30 + #endif 31 + 32 + /* The result of interpreting the frame unwind info for a frame. 33 + This is all symbolic at this point, as none of the values can 34 + be resolved until the target pc is located. */ 35 + typedef struct 36 + { 37 + /* Each register save state can be described in terms of a CFA slot, 38 + another register, or a location expression. */ 39 + struct frame_state_reg_info 40 + { 41 + struct { 42 + union { 43 + _Unwind_Word reg; 44 + _Unwind_Sword offset; 45 + const unsigned char *exp; 46 + } loc; 47 + enum { 48 + REG_UNSAVED, 49 + REG_SAVED_OFFSET, 50 + REG_SAVED_REG, 51 + REG_SAVED_EXP, 52 + REG_SAVED_VAL_OFFSET, 53 + REG_SAVED_VAL_EXP, 54 + REG_UNDEFINED 55 + } how; 56 + } reg[DWARF_FRAME_REGISTERS+1]; 57 + 58 + /* Used to implement DW_CFA_remember_state. */ 59 + struct frame_state_reg_info *prev; 60 + 61 + /* The CFA can be described in terms of a reg+offset or a 62 + location expression. */ 63 + _Unwind_Sword cfa_offset; 64 + _Unwind_Word cfa_reg; 65 + const unsigned char *cfa_exp; 66 + enum { 67 + CFA_UNSET, 68 + CFA_REG_OFFSET, 69 + CFA_EXP 70 + } cfa_how; 71 + } regs; 72 + 73 + /* The PC described by the current frame state. */ 74 + void *pc; 75 + 76 + /* The information we care about from the CIE/FDE. */ 77 + _Unwind_Personality_Fn personality; 78 + _Unwind_Sword data_align; 79 + _Unwind_Word code_align; 80 + _Unwind_Word retaddr_column; 81 + unsigned char fde_encoding; 82 + unsigned char lsda_encoding; 83 + unsigned char saw_z; 84 + unsigned char signal_frame; 85 + void *eh_ptr; 86 + } _Unwind_FrameState; 87 +
+276
src/libunwind-darwin/unwind-generic.h
··· 1 + /* Exception handling and frame unwind runtime interface routines. 2 + Copyright (C) 2001, 2003, 2004, 2006, 2008, 2009 Free Software Foundation, Inc. 3 + 4 + This file is part of GCC. 5 + 6 + GCC is free software; you can redistribute it and/or modify it 7 + under the terms of the GNU General Public License as published by 8 + the Free Software Foundation; either version 3, or (at your option) 9 + any later version. 10 + 11 + GCC is distributed in the hope that it will be useful, but WITHOUT 12 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 13 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 14 + License for more details. 15 + 16 + Under Section 7 of GPL version 3, you are granted additional 17 + permissions described in the GCC Runtime Library Exception, version 18 + 3.1, as published by the Free Software Foundation. 19 + 20 + You should have received a copy of the GNU General Public License and 21 + a copy of the GCC Runtime Library Exception along with this program; 22 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 + <http://www.gnu.org/licenses/>. */ 24 + 25 + /* This is derived from the C++ ABI for IA-64. Where we diverge 26 + for cross-architecture compatibility are noted with "@@@". */ 27 + 28 + #ifndef _UNWIND_H 29 + #define _UNWIND_H 30 + 31 + #ifndef HIDE_EXPORTS 32 + #pragma GCC visibility push(default) 33 + #endif 34 + 35 + #ifdef __cplusplus 36 + extern "C" { 37 + #endif 38 + 39 + /* Level 1: Base ABI */ 40 + 41 + /* @@@ The IA-64 ABI uses uint64 throughout. Most places this is 42 + inefficient for 32-bit and smaller machines. */ 43 + typedef unsigned _Unwind_Word __attribute__((__mode__(__unwind_word__))); 44 + typedef signed _Unwind_Sword __attribute__((__mode__(__unwind_word__))); 45 + #if defined(__ia64__) && defined(__hpux__) 46 + typedef unsigned _Unwind_Ptr __attribute__((__mode__(__word__))); 47 + #else 48 + typedef unsigned _Unwind_Ptr __attribute__((__mode__(__pointer__))); 49 + #endif 50 + typedef unsigned _Unwind_Internal_Ptr __attribute__((__mode__(__pointer__))); 51 + 52 + /* @@@ The IA-64 ABI uses a 64-bit word to identify the producer and 53 + consumer of an exception. We'll go along with this for now even on 54 + 32-bit machines. We'll need to provide some other option for 55 + 16-bit machines and for machines with > 8 bits per byte. */ 56 + typedef unsigned _Unwind_Exception_Class __attribute__((__mode__(__DI__))); 57 + 58 + /* The unwind interface uses reason codes in several contexts to 59 + identify the reasons for failures or other actions. */ 60 + typedef enum 61 + { 62 + _URC_NO_REASON = 0, 63 + _URC_FOREIGN_EXCEPTION_CAUGHT = 1, 64 + _URC_FATAL_PHASE2_ERROR = 2, 65 + _URC_FATAL_PHASE1_ERROR = 3, 66 + _URC_NORMAL_STOP = 4, 67 + _URC_END_OF_STACK = 5, 68 + _URC_HANDLER_FOUND = 6, 69 + _URC_INSTALL_CONTEXT = 7, 70 + _URC_CONTINUE_UNWIND = 8 71 + } _Unwind_Reason_Code; 72 + 73 + 74 + /* The unwind interface uses a pointer to an exception header object 75 + as its representation of an exception being thrown. In general, the 76 + full representation of an exception object is language- and 77 + implementation-specific, but it will be prefixed by a header 78 + understood by the unwind interface. */ 79 + 80 + struct _Unwind_Exception; 81 + 82 + typedef void (*_Unwind_Exception_Cleanup_Fn) (_Unwind_Reason_Code, 83 + struct _Unwind_Exception *); 84 + 85 + struct _Unwind_Exception 86 + { 87 + _Unwind_Exception_Class exception_class; 88 + _Unwind_Exception_Cleanup_Fn exception_cleanup; 89 + _Unwind_Word private_1; 90 + _Unwind_Word private_2; 91 + 92 + /* @@@ The IA-64 ABI says that this structure must be double-word aligned. 93 + Taking that literally does not make much sense generically. Instead we 94 + provide the maximum alignment required by any type for the machine. */ 95 + } __attribute__((__aligned__)); 96 + 97 + 98 + /* The ACTIONS argument to the personality routine is a bitwise OR of one 99 + or more of the following constants. */ 100 + typedef int _Unwind_Action; 101 + 102 + #define _UA_SEARCH_PHASE 1 103 + #define _UA_CLEANUP_PHASE 2 104 + #define _UA_HANDLER_FRAME 4 105 + #define _UA_FORCE_UNWIND 8 106 + #define _UA_END_OF_STACK 16 107 + 108 + /* The target can override this macro to define any back-end-specific 109 + attributes required for the lowest-level stack frame. */ 110 + #ifndef LIBGCC2_UNWIND_ATTRIBUTE 111 + #define LIBGCC2_UNWIND_ATTRIBUTE 112 + #endif 113 + 114 + /* This is an opaque type used to refer to a system-specific data 115 + structure used by the system unwinder. This context is created and 116 + destroyed by the system, and passed to the personality routine 117 + during unwinding. */ 118 + struct _Unwind_Context; 119 + 120 + /* Raise an exception, passing along the given exception object. */ 121 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 122 + _Unwind_RaiseException (struct _Unwind_Exception *); 123 + 124 + /* Raise an exception for forced unwinding. */ 125 + 126 + typedef _Unwind_Reason_Code (*_Unwind_Stop_Fn) 127 + (int, _Unwind_Action, _Unwind_Exception_Class, 128 + struct _Unwind_Exception *, struct _Unwind_Context *, void *); 129 + 130 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 131 + _Unwind_ForcedUnwind (struct _Unwind_Exception *, _Unwind_Stop_Fn, void *); 132 + 133 + /* Helper to invoke the exception_cleanup routine. */ 134 + extern void _Unwind_DeleteException (struct _Unwind_Exception *); 135 + 136 + /* Resume propagation of an existing exception. This is used after 137 + e.g. executing cleanup code, and not to implement rethrowing. */ 138 + extern void LIBGCC2_UNWIND_ATTRIBUTE 139 + _Unwind_Resume (struct _Unwind_Exception *); 140 + 141 + /* @@@ Resume propagation of a FORCE_UNWIND exception, or to rethrow 142 + a normal exception that was handled. */ 143 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 144 + _Unwind_Resume_or_Rethrow (struct _Unwind_Exception *); 145 + 146 + /* @@@ Use unwind data to perform a stack backtrace. The trace callback 147 + is called for every stack frame in the call chain, but no cleanup 148 + actions are performed. */ 149 + typedef _Unwind_Reason_Code (*_Unwind_Trace_Fn) 150 + (struct _Unwind_Context *, void *); 151 + 152 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 153 + _Unwind_Backtrace (_Unwind_Trace_Fn, void *); 154 + 155 + /* These functions are used for communicating information about the unwind 156 + context (i.e. the unwind descriptors and the user register state) between 157 + the unwind library and the personality routine and landing pad. Only 158 + selected registers may be manipulated. */ 159 + 160 + extern _Unwind_Word _Unwind_GetGR (struct _Unwind_Context *, int); 161 + extern void _Unwind_SetGR (struct _Unwind_Context *, int, _Unwind_Word); 162 + 163 + extern _Unwind_Ptr _Unwind_GetIP (struct _Unwind_Context *); 164 + extern _Unwind_Ptr _Unwind_GetIPInfo (struct _Unwind_Context *, int *); 165 + extern void _Unwind_SetIP (struct _Unwind_Context *, _Unwind_Ptr); 166 + 167 + /* @@@ Retrieve the CFA of the given context. */ 168 + extern _Unwind_Word _Unwind_GetCFA (struct _Unwind_Context *); 169 + 170 + extern void *_Unwind_GetLanguageSpecificData (struct _Unwind_Context *); 171 + 172 + extern _Unwind_Ptr _Unwind_GetRegionStart (struct _Unwind_Context *); 173 + 174 + 175 + /* The personality routine is the function in the C++ (or other language) 176 + runtime library which serves as an interface between the system unwind 177 + library and language-specific exception handling semantics. It is 178 + specific to the code fragment described by an unwind info block, and 179 + it is always referenced via the pointer in the unwind info block, and 180 + hence it has no ABI-specified name. 181 + 182 + Note that this implies that two different C++ implementations can 183 + use different names, and have different contents in the language 184 + specific data area. Moreover, that the language specific data 185 + area contains no version info because name of the function invoked 186 + provides more effective versioning by detecting at link time the 187 + lack of code to handle the different data format. */ 188 + 189 + typedef _Unwind_Reason_Code (*_Unwind_Personality_Fn) 190 + (int, _Unwind_Action, _Unwind_Exception_Class, 191 + struct _Unwind_Exception *, struct _Unwind_Context *); 192 + 193 + /* @@@ The following alternate entry points are for setjmp/longjmp 194 + based unwinding. */ 195 + 196 + struct SjLj_Function_Context; 197 + extern void _Unwind_SjLj_Register (struct SjLj_Function_Context *); 198 + extern void _Unwind_SjLj_Unregister (struct SjLj_Function_Context *); 199 + 200 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 201 + _Unwind_SjLj_RaiseException (struct _Unwind_Exception *); 202 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 203 + _Unwind_SjLj_ForcedUnwind (struct _Unwind_Exception *, _Unwind_Stop_Fn, void *); 204 + extern void LIBGCC2_UNWIND_ATTRIBUTE 205 + _Unwind_SjLj_Resume (struct _Unwind_Exception *); 206 + extern _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 207 + _Unwind_SjLj_Resume_or_Rethrow (struct _Unwind_Exception *); 208 + 209 + /* @@@ The following provide access to the base addresses for text 210 + and data-relative addressing in the LDSA. In order to stay link 211 + compatible with the standard ABI for IA-64, we inline these. */ 212 + 213 + #ifdef __ia64__ 214 + #include <stdlib.h> 215 + 216 + static inline _Unwind_Ptr 217 + _Unwind_GetDataRelBase (struct _Unwind_Context *_C) 218 + { 219 + /* The GP is stored in R1. */ 220 + return _Unwind_GetGR (_C, 1); 221 + } 222 + 223 + static inline _Unwind_Ptr 224 + _Unwind_GetTextRelBase (struct _Unwind_Context *_C __attribute__ ((__unused__))) 225 + { 226 + abort (); 227 + return 0; 228 + } 229 + 230 + /* @@@ Retrieve the Backing Store Pointer of the given context. */ 231 + extern _Unwind_Word _Unwind_GetBSP (struct _Unwind_Context *); 232 + #else 233 + extern _Unwind_Ptr _Unwind_GetDataRelBase (struct _Unwind_Context *); 234 + extern _Unwind_Ptr _Unwind_GetTextRelBase (struct _Unwind_Context *); 235 + #endif 236 + 237 + /* @@@ Given an address, return the entry point of the function that 238 + contains it. */ 239 + extern void * _Unwind_FindEnclosingFunction (void *pc); 240 + 241 + #ifndef __SIZEOF_LONG__ 242 + #error "__SIZEOF_LONG__ macro not defined" 243 + #endif 244 + 245 + #ifndef __SIZEOF_POINTER__ 246 + #error "__SIZEOF_POINTER__ macro not defined" 247 + #endif 248 + 249 + 250 + /* leb128 type numbers have a potentially unlimited size. 251 + The target of the following definitions of _sleb128_t and _uleb128_t 252 + is to have efficient data types large enough to hold the leb128 type 253 + numbers used in the unwind code. 254 + Mostly these types will simply be defined to long and unsigned long 255 + except when a unsigned long data type on the target machine is not 256 + capable of storing a pointer. */ 257 + 258 + #if __SIZEOF_LONG__ >= __SIZEOF_POINTER__ 259 + typedef long _sleb128_t; 260 + typedef unsigned long _uleb128_t; 261 + #elif __SIZEOF_LONG_LONG__ >= __SIZEOF_POINTER__ 262 + typedef long long _sleb128_t; 263 + typedef unsigned long long _uleb128_t; 264 + #else 265 + # error "What type shall we use for _sleb128_t?" 266 + #endif 267 + 268 + #ifdef __cplusplus 269 + } 270 + #endif 271 + 272 + #ifndef HIDE_EXPORTS 273 + #pragma GCC visibility pop 274 + #endif 275 + 276 + #endif /* unwind.h */
+289
src/libunwind-darwin/unwind-pe.h
··· 1 + /* Exception handling and frame unwind runtime interface routines. 2 + Copyright (C) 2001, 2002, 2003, 2004, 2008, 2009 Free Software Foundation, Inc. 3 + 4 + This file is part of GCC. 5 + 6 + GCC is free software; you can redistribute it and/or modify it 7 + under the terms of the GNU General Public License as published by 8 + the Free Software Foundation; either version 3, or (at your option) 9 + any later version. 10 + 11 + GCC is distributed in the hope that it will be useful, but WITHOUT 12 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 13 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 14 + License for more details. 15 + 16 + Under Section 7 of GPL version 3, you are granted additional 17 + permissions described in the GCC Runtime Library Exception, version 18 + 3.1, as published by the Free Software Foundation. 19 + 20 + You should have received a copy of the GNU General Public License and 21 + a copy of the GCC Runtime Library Exception along with this program; 22 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 + <http://www.gnu.org/licenses/>. */ 24 + 25 + /* @@@ Really this should be out of line, but this also causes link 26 + compatibility problems with the base ABI. This is slightly better 27 + than duplicating code, however. */ 28 + 29 + #ifndef GCC_UNWIND_PE_H 30 + #define GCC_UNWIND_PE_H 31 + 32 + /* If using C++, references to abort have to be qualified with std::. */ 33 + #if __cplusplus 34 + #define __gxx_abort std::abort 35 + #else 36 + #define __gxx_abort abort 37 + #endif 38 + 39 + /* Pointer encodings, from dwarf2.h. */ 40 + #define DW_EH_PE_absptr 0x00 41 + #define DW_EH_PE_omit 0xff 42 + 43 + #define DW_EH_PE_uleb128 0x01 44 + #define DW_EH_PE_udata2 0x02 45 + #define DW_EH_PE_udata4 0x03 46 + #define DW_EH_PE_udata8 0x04 47 + #define DW_EH_PE_sleb128 0x09 48 + #define DW_EH_PE_sdata2 0x0A 49 + #define DW_EH_PE_sdata4 0x0B 50 + #define DW_EH_PE_sdata8 0x0C 51 + #define DW_EH_PE_signed 0x08 52 + 53 + #define DW_EH_PE_pcrel 0x10 54 + #define DW_EH_PE_textrel 0x20 55 + #define DW_EH_PE_datarel 0x30 56 + #define DW_EH_PE_funcrel 0x40 57 + #define DW_EH_PE_aligned 0x50 58 + 59 + #define DW_EH_PE_indirect 0x80 60 + 61 + 62 + #ifndef NO_SIZE_OF_ENCODED_VALUE 63 + 64 + /* Given an encoding, return the number of bytes the format occupies. 65 + This is only defined for fixed-size encodings, and so does not 66 + include leb128. */ 67 + 68 + static unsigned int 69 + size_of_encoded_value (unsigned char encoding) __attribute__ ((unused)); 70 + 71 + static unsigned int 72 + size_of_encoded_value (unsigned char encoding) 73 + { 74 + if (encoding == DW_EH_PE_omit) 75 + return 0; 76 + 77 + switch (encoding & 0x07) 78 + { 79 + case DW_EH_PE_absptr: 80 + return sizeof (void *); 81 + case DW_EH_PE_udata2: 82 + return 2; 83 + case DW_EH_PE_udata4: 84 + return 4; 85 + case DW_EH_PE_udata8: 86 + return 8; 87 + } 88 + __gxx_abort (); 89 + } 90 + 91 + #endif 92 + 93 + #ifndef NO_BASE_OF_ENCODED_VALUE 94 + 95 + /* Given an encoding and an _Unwind_Context, return the base to which 96 + the encoding is relative. This base may then be passed to 97 + read_encoded_value_with_base for use when the _Unwind_Context is 98 + not available. */ 99 + 100 + static _Unwind_Ptr 101 + base_of_encoded_value (unsigned char encoding, struct _Unwind_Context *context) 102 + { 103 + if (encoding == DW_EH_PE_omit) 104 + return 0; 105 + 106 + switch (encoding & 0x70) 107 + { 108 + case DW_EH_PE_absptr: 109 + case DW_EH_PE_pcrel: 110 + case DW_EH_PE_aligned: 111 + return 0; 112 + 113 + case DW_EH_PE_textrel: 114 + return _Unwind_GetTextRelBase (context); 115 + case DW_EH_PE_datarel: 116 + return _Unwind_GetDataRelBase (context); 117 + case DW_EH_PE_funcrel: 118 + return _Unwind_GetRegionStart (context); 119 + } 120 + __gxx_abort (); 121 + } 122 + 123 + #endif 124 + 125 + /* Read an unsigned leb128 value from P, store the value in VAL, return 126 + P incremented past the value. We assume that a word is large enough to 127 + hold any value so encoded; if it is smaller than a pointer on some target, 128 + pointers should not be leb128 encoded on that target. */ 129 + 130 + static const unsigned char * 131 + read_uleb128 (const unsigned char *p, _uleb128_t *val) 132 + { 133 + unsigned int shift = 0; 134 + unsigned char byte; 135 + _uleb128_t result; 136 + 137 + result = 0; 138 + do 139 + { 140 + byte = *p++; 141 + result |= ((_uleb128_t)byte & 0x7f) << shift; 142 + shift += 7; 143 + } 144 + while (byte & 0x80); 145 + 146 + *val = result; 147 + return p; 148 + } 149 + 150 + /* Similar, but read a signed leb128 value. */ 151 + 152 + static const unsigned char * 153 + read_sleb128 (const unsigned char *p, _sleb128_t *val) 154 + { 155 + unsigned int shift = 0; 156 + unsigned char byte; 157 + _uleb128_t result; 158 + 159 + result = 0; 160 + do 161 + { 162 + byte = *p++; 163 + result |= ((_uleb128_t)byte & 0x7f) << shift; 164 + shift += 7; 165 + } 166 + while (byte & 0x80); 167 + 168 + /* Sign-extend a negative value. */ 169 + if (shift < 8 * sizeof(result) && (byte & 0x40) != 0) 170 + result |= -(((_uleb128_t)1L) << shift); 171 + 172 + *val = (_sleb128_t) result; 173 + return p; 174 + } 175 + 176 + /* Load an encoded value from memory at P. The value is returned in VAL; 177 + The function returns P incremented past the value. BASE is as given 178 + by base_of_encoded_value for this encoding in the appropriate context. */ 179 + 180 + static const unsigned char * 181 + read_encoded_value_with_base (unsigned char encoding, _Unwind_Ptr base, 182 + const unsigned char *p, _Unwind_Ptr *val) 183 + { 184 + union unaligned 185 + { 186 + void *ptr; 187 + unsigned u2 __attribute__ ((mode (HI))); 188 + unsigned u4 __attribute__ ((mode (SI))); 189 + unsigned u8 __attribute__ ((mode (DI))); 190 + signed s2 __attribute__ ((mode (HI))); 191 + signed s4 __attribute__ ((mode (SI))); 192 + signed s8 __attribute__ ((mode (DI))); 193 + } __attribute__((__packed__)); 194 + 195 + const union unaligned *u = (const union unaligned *) p; 196 + _Unwind_Internal_Ptr result; 197 + 198 + if (encoding == DW_EH_PE_aligned) 199 + { 200 + _Unwind_Internal_Ptr a = (_Unwind_Internal_Ptr) p; 201 + a = (a + sizeof (void *) - 1) & - sizeof(void *); 202 + result = *(_Unwind_Internal_Ptr *) a; 203 + p = (const unsigned char *) (_Unwind_Internal_Ptr) (a + sizeof (void *)); 204 + } 205 + else 206 + { 207 + switch (encoding & 0x0f) 208 + { 209 + case DW_EH_PE_absptr: 210 + result = (_Unwind_Internal_Ptr) u->ptr; 211 + p += sizeof (void *); 212 + break; 213 + 214 + case DW_EH_PE_uleb128: 215 + { 216 + _uleb128_t tmp; 217 + p = read_uleb128 (p, &tmp); 218 + result = (_Unwind_Internal_Ptr) tmp; 219 + } 220 + break; 221 + 222 + case DW_EH_PE_sleb128: 223 + { 224 + _sleb128_t tmp; 225 + p = read_sleb128 (p, &tmp); 226 + result = (_Unwind_Internal_Ptr) tmp; 227 + } 228 + break; 229 + 230 + case DW_EH_PE_udata2: 231 + result = u->u2; 232 + p += 2; 233 + break; 234 + case DW_EH_PE_udata4: 235 + result = u->u4; 236 + p += 4; 237 + break; 238 + case DW_EH_PE_udata8: 239 + result = u->u8; 240 + p += 8; 241 + break; 242 + 243 + case DW_EH_PE_sdata2: 244 + result = u->s2; 245 + p += 2; 246 + break; 247 + case DW_EH_PE_sdata4: 248 + result = u->s4; 249 + p += 4; 250 + break; 251 + case DW_EH_PE_sdata8: 252 + result = u->s8; 253 + p += 8; 254 + break; 255 + 256 + default: 257 + __gxx_abort (); 258 + } 259 + 260 + if (result != 0) 261 + { 262 + result += ((encoding & 0x70) == DW_EH_PE_pcrel 263 + ? (_Unwind_Internal_Ptr) u : base); 264 + if (encoding & DW_EH_PE_indirect) 265 + result = *(_Unwind_Internal_Ptr *) result; 266 + } 267 + } 268 + 269 + *val = result; 270 + return p; 271 + } 272 + 273 + #ifndef NO_BASE_OF_ENCODED_VALUE 274 + 275 + /* Like read_encoded_value_with_base, but get the base from the context 276 + rather than providing it directly. */ 277 + 278 + static inline const unsigned char * 279 + read_encoded_value (struct _Unwind_Context *context, unsigned char encoding, 280 + const unsigned char *p, _Unwind_Ptr *val) 281 + { 282 + return read_encoded_value_with_base (encoding, 283 + base_of_encoded_value (encoding, context), 284 + p, val); 285 + } 286 + 287 + #endif 288 + 289 + #endif /* unwind-pe.h */
+326
src/libunwind-darwin/unwind-sjlj.c
··· 1 + /* SJLJ exception handling and frame unwind runtime interface routines. 2 + Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2006, 3 + 2009 Free Software Foundation, Inc. 4 + 5 + This file is part of GCC. 6 + 7 + GCC is free software; you can redistribute it and/or modify it 8 + under the terms of the GNU General Public License as published by 9 + the Free Software Foundation; either version 3, or (at your option) 10 + any later version. 11 + 12 + GCC is distributed in the hope that it will be useful, but WITHOUT 13 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 14 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 15 + License for more details. 16 + 17 + Under Section 7 of GPL version 3, you are granted additional 18 + permissions described in the GCC Runtime Library Exception, version 19 + 3.1, as published by the Free Software Foundation. 20 + 21 + You should have received a copy of the GNU General Public License and 22 + a copy of the GCC Runtime Library Exception along with this program; 23 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24 + <http://www.gnu.org/licenses/>. */ 25 + 26 + #include "tconfig.h" 27 + #include "tsystem.h" 28 + #include "coretypes.h" 29 + #include "tm.h" 30 + #include "unwind.h" 31 + #include "gthr.h" 32 + 33 + #ifdef __USING_SJLJ_EXCEPTIONS__ 34 + 35 + #ifdef DONT_USE_BUILTIN_SETJMP 36 + #ifndef inhibit_libc 37 + #include <setjmp.h> 38 + #else 39 + typedef void *jmp_buf[JMP_BUF_SIZE]; 40 + extern void longjmp(jmp_buf, int) __attribute__((noreturn)); 41 + #endif 42 + #else 43 + #define longjmp __builtin_longjmp 44 + #endif 45 + 46 + /* The setjmp side is dealt with in the except.c file. */ 47 + #undef setjmp 48 + #define setjmp setjmp_should_not_be_used_in_this_file 49 + 50 + 51 + /* This structure is allocated on the stack of the target function. 52 + This must match the definition created in except.c:init_eh. */ 53 + struct SjLj_Function_Context 54 + { 55 + /* This is the chain through all registered contexts. It is 56 + filled in by _Unwind_SjLj_Register. */ 57 + struct SjLj_Function_Context *prev; 58 + 59 + /* This is assigned in by the target function before every call 60 + to the index of the call site in the lsda. It is assigned by 61 + the personality routine to the landing pad index. */ 62 + int call_site; 63 + 64 + /* This is how data is returned from the personality routine to 65 + the target function's handler. */ 66 + _Unwind_Word data[4]; 67 + 68 + /* These are filled in once by the target function before any 69 + exceptions are expected to be handled. */ 70 + _Unwind_Personality_Fn personality; 71 + void *lsda; 72 + 73 + #ifdef DONT_USE_BUILTIN_SETJMP 74 + /* We don't know what sort of alignment requirements the system 75 + jmp_buf has. We over estimated in except.c, and now we have 76 + to match that here just in case the system *didn't* have more 77 + restrictive requirements. */ 78 + jmp_buf jbuf __attribute__((aligned)); 79 + #else 80 + void *jbuf[]; 81 + #endif 82 + }; 83 + 84 + struct _Unwind_Context 85 + { 86 + struct SjLj_Function_Context *fc; 87 + }; 88 + 89 + typedef struct 90 + { 91 + _Unwind_Personality_Fn personality; 92 + } _Unwind_FrameState; 93 + 94 + 95 + /* Manage the chain of registered function contexts. */ 96 + 97 + /* Single threaded fallback chain. */ 98 + static struct SjLj_Function_Context *fc_static; 99 + 100 + #if __GTHREADS 101 + static __gthread_key_t fc_key; 102 + static int use_fc_key = -1; 103 + 104 + static void 105 + fc_key_init (void) 106 + { 107 + use_fc_key = __gthread_key_create (&fc_key, 0) == 0; 108 + } 109 + 110 + static void 111 + fc_key_init_once (void) 112 + { 113 + static __gthread_once_t once = __GTHREAD_ONCE_INIT; 114 + if (__gthread_once (&once, fc_key_init) != 0 || use_fc_key < 0) 115 + use_fc_key = 0; 116 + } 117 + #endif 118 + 119 + void 120 + _Unwind_SjLj_Register (struct SjLj_Function_Context *fc) 121 + { 122 + #if __GTHREADS 123 + if (use_fc_key < 0) 124 + fc_key_init_once (); 125 + 126 + if (use_fc_key) 127 + { 128 + fc->prev = __gthread_getspecific (fc_key); 129 + __gthread_setspecific (fc_key, fc); 130 + } 131 + else 132 + #endif 133 + { 134 + fc->prev = fc_static; 135 + fc_static = fc; 136 + } 137 + } 138 + 139 + static inline struct SjLj_Function_Context * 140 + _Unwind_SjLj_GetContext (void) 141 + { 142 + #if __GTHREADS 143 + if (use_fc_key < 0) 144 + fc_key_init_once (); 145 + 146 + if (use_fc_key) 147 + return __gthread_getspecific (fc_key); 148 + #endif 149 + return fc_static; 150 + } 151 + 152 + static inline void 153 + _Unwind_SjLj_SetContext (struct SjLj_Function_Context *fc) 154 + { 155 + #if __GTHREADS 156 + if (use_fc_key < 0) 157 + fc_key_init_once (); 158 + 159 + if (use_fc_key) 160 + __gthread_setspecific (fc_key, fc); 161 + else 162 + #endif 163 + fc_static = fc; 164 + } 165 + 166 + void 167 + _Unwind_SjLj_Unregister (struct SjLj_Function_Context *fc) 168 + { 169 + _Unwind_SjLj_SetContext (fc->prev); 170 + } 171 + 172 + 173 + /* Get/set the return data value at INDEX in CONTEXT. */ 174 + 175 + _Unwind_Word 176 + _Unwind_GetGR (struct _Unwind_Context *context, int index) 177 + { 178 + return context->fc->data[index]; 179 + } 180 + 181 + /* Get the value of the CFA as saved in CONTEXT. */ 182 + 183 + _Unwind_Word 184 + _Unwind_GetCFA (struct _Unwind_Context *context __attribute__((unused))) 185 + { 186 + /* ??? Ideally __builtin_setjmp places the CFA in the jmpbuf. */ 187 + 188 + #ifndef DONT_USE_BUILTIN_SETJMP 189 + /* This is a crude imitation of the CFA: the saved stack pointer. 190 + This is roughly the CFA of the frame before CONTEXT. When using the 191 + DWARF-2 unwinder _Unwind_GetCFA returns the CFA of the frame described 192 + by CONTEXT instead; but for DWARF-2 the cleanups associated with 193 + CONTEXT have already been run, and for SJLJ they have not yet been. */ 194 + if (context->fc != NULL) 195 + return (_Unwind_Word) context->fc->jbuf[2]; 196 + #endif 197 + 198 + /* Otherwise we're out of luck for now. */ 199 + return (_Unwind_Word) 0; 200 + } 201 + 202 + void 203 + _Unwind_SetGR (struct _Unwind_Context *context, int index, _Unwind_Word val) 204 + { 205 + context->fc->data[index] = val; 206 + } 207 + 208 + /* Get the call-site index as saved in CONTEXT. */ 209 + 210 + _Unwind_Ptr 211 + _Unwind_GetIP (struct _Unwind_Context *context) 212 + { 213 + return context->fc->call_site + 1; 214 + } 215 + 216 + _Unwind_Ptr 217 + _Unwind_GetIPInfo (struct _Unwind_Context *context, int *ip_before_insn) 218 + { 219 + *ip_before_insn = 0; 220 + if (context->fc != NULL) 221 + return context->fc->call_site + 1; 222 + else 223 + return 0; 224 + } 225 + 226 + /* Set the return landing pad index in CONTEXT. */ 227 + 228 + void 229 + _Unwind_SetIP (struct _Unwind_Context *context, _Unwind_Ptr val) 230 + { 231 + context->fc->call_site = val - 1; 232 + } 233 + 234 + void * 235 + _Unwind_GetLanguageSpecificData (struct _Unwind_Context *context) 236 + { 237 + return context->fc->lsda; 238 + } 239 + 240 + _Unwind_Ptr 241 + _Unwind_GetRegionStart (struct _Unwind_Context *context __attribute__((unused)) ) 242 + { 243 + return 0; 244 + } 245 + 246 + void * 247 + _Unwind_FindEnclosingFunction (void *pc __attribute__((unused))) 248 + { 249 + return NULL; 250 + } 251 + 252 + #ifndef __ia64__ 253 + _Unwind_Ptr 254 + _Unwind_GetDataRelBase (struct _Unwind_Context *context __attribute__((unused)) ) 255 + { 256 + return 0; 257 + } 258 + 259 + _Unwind_Ptr 260 + _Unwind_GetTextRelBase (struct _Unwind_Context *context __attribute__((unused)) ) 261 + { 262 + return 0; 263 + } 264 + #endif 265 + 266 + static inline _Unwind_Reason_Code 267 + uw_frame_state_for (struct _Unwind_Context *context, _Unwind_FrameState *fs) 268 + { 269 + if (context->fc == NULL) 270 + { 271 + fs->personality = NULL; 272 + return _URC_END_OF_STACK; 273 + } 274 + else 275 + { 276 + fs->personality = context->fc->personality; 277 + return _URC_NO_REASON; 278 + } 279 + } 280 + 281 + static inline void 282 + uw_update_context (struct _Unwind_Context *context, 283 + _Unwind_FrameState *fs __attribute__((unused)) ) 284 + { 285 + context->fc = context->fc->prev; 286 + } 287 + 288 + static void 289 + uw_advance_context (struct _Unwind_Context *context, _Unwind_FrameState *fs) 290 + { 291 + _Unwind_SjLj_Unregister (context->fc); 292 + uw_update_context (context, fs); 293 + } 294 + 295 + static inline void 296 + uw_init_context (struct _Unwind_Context *context) 297 + { 298 + context->fc = _Unwind_SjLj_GetContext (); 299 + } 300 + 301 + static void __attribute__((noreturn)) 302 + uw_install_context (struct _Unwind_Context *current __attribute__((unused)), 303 + struct _Unwind_Context *target) 304 + { 305 + _Unwind_SjLj_SetContext (target->fc); 306 + longjmp (target->fc->jbuf, 1); 307 + } 308 + 309 + static inline _Unwind_Ptr 310 + uw_identify_context (struct _Unwind_Context *context) 311 + { 312 + return (_Unwind_Ptr) context->fc; 313 + } 314 + 315 + 316 + /* Play games with unwind symbols so that we can have call frame 317 + and sjlj symbols in the same shared library. Not that you can 318 + use them simultaneously... */ 319 + #define _Unwind_RaiseException _Unwind_SjLj_RaiseException 320 + #define _Unwind_ForcedUnwind _Unwind_SjLj_ForcedUnwind 321 + #define _Unwind_Resume _Unwind_SjLj_Resume 322 + #define _Unwind_Resume_or_Rethrow _Unwind_SjLj_Resume_or_Rethrow 323 + 324 + #include "unwind.inc" 325 + 326 + #endif /* USING_SJLJ_EXCEPTIONS */
+307
src/libunwind-darwin/unwind.inc
··· 1 + /* Exception handling and frame unwind runtime interface routines. -*- C -*- 2 + Copyright (C) 2001, 2003, 2008, 2009 Free Software Foundation, Inc. 3 + 4 + This file is part of GCC. 5 + 6 + GCC is free software; you can redistribute it and/or modify it 7 + under the terms of the GNU General Public License as published by 8 + the Free Software Foundation; either version 3, or (at your option) 9 + any later version. 10 + 11 + GCC is distributed in the hope that it will be useful, but WITHOUT 12 + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 13 + or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 14 + License for more details. 15 + 16 + Under Section 7 of GPL version 3, you are granted additional 17 + permissions described in the GCC Runtime Library Exception, version 18 + 3.1, as published by the Free Software Foundation. 19 + 20 + You should have received a copy of the GNU General Public License and 21 + a copy of the GCC Runtime Library Exception along with this program; 22 + see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 + <http://www.gnu.org/licenses/>. */ 24 + 25 + /* This is derived from the C++ ABI for IA-64. Where we diverge 26 + for cross-architecture compatibility are noted with "@@@". 27 + This file is included from unwind-dw2.c, unwind-sjlj.c or 28 + unwind-ia64.c. */ 29 + 30 + /* Subroutine of _Unwind_RaiseException also invoked from _Unwind_Resume. 31 + 32 + Unwind the stack calling the personality routine to find both the 33 + exception handler and intermediary cleanup code. We'll only locate 34 + the first such frame here. Cleanup code will call back into 35 + _Unwind_Resume and we'll continue Phase 2 there. */ 36 + 37 + static _Unwind_Reason_Code 38 + _Unwind_RaiseException_Phase2(struct _Unwind_Exception *exc, 39 + struct _Unwind_Context *context) 40 + { 41 + _Unwind_Reason_Code code; 42 + 43 + while (1) 44 + { 45 + _Unwind_FrameState fs; 46 + int match_handler; 47 + 48 + code = uw_frame_state_for (context, &fs); 49 + 50 + /* Identify when we've reached the designated handler context. */ 51 + match_handler = (uw_identify_context (context) == exc->private_2 52 + ? _UA_HANDLER_FRAME : 0); 53 + 54 + if (code != _URC_NO_REASON) 55 + /* Some error encountered. Usually the unwinder doesn't 56 + diagnose these and merely crashes. */ 57 + return _URC_FATAL_PHASE2_ERROR; 58 + 59 + /* Unwind successful. Run the personality routine, if any. */ 60 + if (fs.personality) 61 + { 62 + code = (*fs.personality) (1, _UA_CLEANUP_PHASE | match_handler, 63 + exc->exception_class, exc, context); 64 + if (code == _URC_INSTALL_CONTEXT) 65 + break; 66 + if (code != _URC_CONTINUE_UNWIND) 67 + return _URC_FATAL_PHASE2_ERROR; 68 + } 69 + 70 + /* Don't let us unwind past the handler context. */ 71 + gcc_assert (!match_handler); 72 + 73 + uw_update_context (context, &fs); 74 + } 75 + 76 + return code; 77 + } 78 + 79 + /* Raise an exception, passing along the given exception object. */ 80 + 81 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 82 + _Unwind_RaiseException(struct _Unwind_Exception *exc) 83 + { 84 + struct _Unwind_Context this_context, cur_context; 85 + _Unwind_Reason_Code code; 86 + 87 + /* Set up this_context to describe the current stack frame. */ 88 + uw_init_context (&this_context); 89 + cur_context = this_context; 90 + 91 + /* Phase 1: Search. Unwind the stack, calling the personality routine 92 + with the _UA_SEARCH_PHASE flag set. Do not modify the stack yet. */ 93 + while (1) 94 + { 95 + _Unwind_FrameState fs; 96 + 97 + /* Set up fs to describe the FDE for the caller of cur_context. The 98 + first time through the loop, that means __cxa_throw. */ 99 + code = uw_frame_state_for (&cur_context, &fs); 100 + 101 + if (code == _URC_END_OF_STACK) 102 + /* Hit end of stack with no handler found. */ 103 + return _URC_END_OF_STACK; 104 + 105 + if (code != _URC_NO_REASON) 106 + /* Some error encountered. Usually the unwinder doesn't 107 + diagnose these and merely crashes. */ 108 + return _URC_FATAL_PHASE1_ERROR; 109 + 110 + /* Unwind successful. Run the personality routine, if any. */ 111 + if (fs.personality) 112 + { 113 + code = (*fs.personality) (1, _UA_SEARCH_PHASE, exc->exception_class, 114 + exc, &cur_context); 115 + if (code == _URC_HANDLER_FOUND) 116 + break; 117 + else if (code != _URC_CONTINUE_UNWIND) 118 + return _URC_FATAL_PHASE1_ERROR; 119 + } 120 + 121 + /* Update cur_context to describe the same frame as fs. */ 122 + uw_update_context (&cur_context, &fs); 123 + } 124 + 125 + /* Indicate to _Unwind_Resume and associated subroutines that this 126 + is not a forced unwind. Further, note where we found a handler. */ 127 + exc->private_1 = 0; 128 + exc->private_2 = uw_identify_context (&cur_context); 129 + 130 + cur_context = this_context; 131 + code = _Unwind_RaiseException_Phase2 (exc, &cur_context); 132 + if (code != _URC_INSTALL_CONTEXT) 133 + return code; 134 + 135 + uw_install_context (&this_context, &cur_context); 136 + } 137 + 138 + 139 + /* Subroutine of _Unwind_ForcedUnwind also invoked from _Unwind_Resume. */ 140 + 141 + static _Unwind_Reason_Code 142 + _Unwind_ForcedUnwind_Phase2 (struct _Unwind_Exception *exc, 143 + struct _Unwind_Context *context) 144 + { 145 + _Unwind_Stop_Fn stop = (_Unwind_Stop_Fn) (_Unwind_Ptr) exc->private_1; 146 + void *stop_argument = (void *) (_Unwind_Ptr) exc->private_2; 147 + _Unwind_Reason_Code code, stop_code; 148 + 149 + while (1) 150 + { 151 + _Unwind_FrameState fs; 152 + int action; 153 + 154 + /* Set up fs to describe the FDE for the caller of cur_context. */ 155 + code = uw_frame_state_for (context, &fs); 156 + if (code != _URC_NO_REASON && code != _URC_END_OF_STACK) 157 + return _URC_FATAL_PHASE2_ERROR; 158 + 159 + /* Unwind successful. */ 160 + action = _UA_FORCE_UNWIND | _UA_CLEANUP_PHASE; 161 + if (code == _URC_END_OF_STACK) 162 + action |= _UA_END_OF_STACK; 163 + stop_code = (*stop) (1, action, exc->exception_class, exc, 164 + context, stop_argument); 165 + if (stop_code != _URC_NO_REASON) 166 + return _URC_FATAL_PHASE2_ERROR; 167 + 168 + /* Stop didn't want to do anything. Invoke the personality 169 + handler, if applicable, to run cleanups. */ 170 + if (code == _URC_END_OF_STACK) 171 + break; 172 + 173 + if (fs.personality) 174 + { 175 + code = (*fs.personality) (1, _UA_FORCE_UNWIND | _UA_CLEANUP_PHASE, 176 + exc->exception_class, exc, context); 177 + if (code == _URC_INSTALL_CONTEXT) 178 + break; 179 + if (code != _URC_CONTINUE_UNWIND) 180 + return _URC_FATAL_PHASE2_ERROR; 181 + } 182 + 183 + /* Update cur_context to describe the same frame as fs, and discard 184 + the previous context if necessary. */ 185 + uw_advance_context (context, &fs); 186 + } 187 + 188 + return code; 189 + } 190 + 191 + 192 + /* Raise an exception for forced unwinding. */ 193 + 194 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 195 + _Unwind_ForcedUnwind (struct _Unwind_Exception *exc, 196 + _Unwind_Stop_Fn stop, void * stop_argument) 197 + { 198 + struct _Unwind_Context this_context, cur_context; 199 + _Unwind_Reason_Code code; 200 + 201 + uw_init_context (&this_context); 202 + cur_context = this_context; 203 + 204 + exc->private_1 = (_Unwind_Ptr) stop; 205 + exc->private_2 = (_Unwind_Ptr) stop_argument; 206 + 207 + code = _Unwind_ForcedUnwind_Phase2 (exc, &cur_context); 208 + if (code != _URC_INSTALL_CONTEXT) 209 + return code; 210 + 211 + uw_install_context (&this_context, &cur_context); 212 + } 213 + 214 + 215 + /* Resume propagation of an existing exception. This is used after 216 + e.g. executing cleanup code, and not to implement rethrowing. */ 217 + 218 + void LIBGCC2_UNWIND_ATTRIBUTE 219 + _Unwind_Resume (struct _Unwind_Exception *exc) 220 + { 221 + struct _Unwind_Context this_context, cur_context; 222 + _Unwind_Reason_Code code; 223 + 224 + uw_init_context (&this_context); 225 + cur_context = this_context; 226 + 227 + /* Choose between continuing to process _Unwind_RaiseException 228 + or _Unwind_ForcedUnwind. */ 229 + if (exc->private_1 == 0) 230 + code = _Unwind_RaiseException_Phase2 (exc, &cur_context); 231 + else 232 + code = _Unwind_ForcedUnwind_Phase2 (exc, &cur_context); 233 + 234 + gcc_assert (code == _URC_INSTALL_CONTEXT); 235 + 236 + uw_install_context (&this_context, &cur_context); 237 + } 238 + 239 + 240 + /* Resume propagation of an FORCE_UNWIND exception, or to rethrow 241 + a normal exception that was handled. */ 242 + 243 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 244 + _Unwind_Resume_or_Rethrow (struct _Unwind_Exception *exc) 245 + { 246 + struct _Unwind_Context this_context, cur_context; 247 + _Unwind_Reason_Code code; 248 + 249 + /* Choose between continuing to process _Unwind_RaiseException 250 + or _Unwind_ForcedUnwind. */ 251 + if (exc->private_1 == 0) 252 + return _Unwind_RaiseException (exc); 253 + 254 + uw_init_context (&this_context); 255 + cur_context = this_context; 256 + 257 + code = _Unwind_ForcedUnwind_Phase2 (exc, &cur_context); 258 + 259 + gcc_assert (code == _URC_INSTALL_CONTEXT); 260 + 261 + uw_install_context (&this_context, &cur_context); 262 + } 263 + 264 + 265 + /* A convenience function that calls the exception_cleanup field. */ 266 + 267 + void 268 + _Unwind_DeleteException (struct _Unwind_Exception *exc) 269 + { 270 + if (exc->exception_cleanup) 271 + (*exc->exception_cleanup) (_URC_FOREIGN_EXCEPTION_CAUGHT, exc); 272 + } 273 + 274 + 275 + /* Perform stack backtrace through unwind data. */ 276 + 277 + _Unwind_Reason_Code LIBGCC2_UNWIND_ATTRIBUTE 278 + _Unwind_Backtrace(_Unwind_Trace_Fn trace, void * trace_argument) 279 + { 280 + struct _Unwind_Context context; 281 + _Unwind_Reason_Code code; 282 + 283 + uw_init_context (&context); 284 + 285 + while (1) 286 + { 287 + _Unwind_FrameState fs; 288 + 289 + /* Set up fs to describe the FDE for the caller of context. */ 290 + code = uw_frame_state_for (&context, &fs); 291 + if (code != _URC_NO_REASON && code != _URC_END_OF_STACK) 292 + return _URC_FATAL_PHASE1_ERROR; 293 + 294 + /* Call trace function. */ 295 + if ((*trace) (&context, trace_argument) != _URC_NO_REASON) 296 + return _URC_FATAL_PHASE1_ERROR; 297 + 298 + /* We're done at end of stack. */ 299 + if (code == _URC_END_OF_STACK) 300 + break; 301 + 302 + /* Update context to describe the same frame as fs. */ 303 + uw_update_context (&context, &fs); 304 + } 305 + 306 + return code; 307 + }