1 /* Functions for generic Darwin as target machine for GNU C compiler. 2 Copyright (C) 1989, 1990, 1991, 1992, 1993, 2000, 2001, 2002, 2003, 2004, 3 2005, 2006, 2007, 2008, 2009, 2010 4 Free Software Foundation, Inc. 5 Contributed by Apple Computer Inc. 6 7 This file is part of GCC. 8 9 GCC is free software; you can redistribute it and/or modify 10 it under the terms of the GNU General Public License as published by 11 the Free Software Foundation; either version 3, or (at your option) 12 any later version. 13 14 GCC is distributed in the hope that it will be useful, 15 but WITHOUT ANY WARRANTY; without even the implied warranty of 16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 GNU General Public License for more details. 18 19 You should have received a copy of the GNU General Public License 20 along with GCC; see the file COPYING3. If not see 21 <http://www.gnu.org/licenses/>. */ 22 23 #include "config.h" 24 #include "system.h" 25 #include "coretypes.h" 26 #include "tm.h" 27 #include "rtl.h" 28 #include "regs.h" 29 #include "hard-reg-set.h" 30 #include "real.h" 31 #include "insn-config.h" 32 #include "conditions.h" 33 #include "insn-flags.h" 34 #include "output.h" 35 #include "insn-attr.h" 36 #include "flags.h" 37 #include "tree.h" 38 #include "expr.h" 39 #include "reload.h" 40 #include "function.h" 41 #include "ggc.h" 42 #include "langhooks.h" 43 #include "target.h" 44 #include "tm_p.h" 45 #include "toplev.h" 46 #include "hashtab.h" 47 #include "df.h" 48 #include "debug.h" 49 #include "obstack.h" 50 #include "lto-streamer.h" 51 52 /* Darwin supports a feature called fix-and-continue, which is used 53 for rapid turn around debugging. When code is compiled with the 54 -mfix-and-continue flag, two changes are made to the generated code 55 that allow the system to do things that it would normally not be 56 able to do easily. These changes allow gdb to load in 57 recompilation of a translation unit that has been changed into a 58 running program and replace existing functions and methods of that 59 translation unit with versions of those functions and methods 60 from the newly compiled translation unit. The new functions access 61 the existing static symbols from the old translation unit, if the 62 symbol existed in the unit to be replaced, and from the new 63 translation unit, otherwise. 64 65 The changes are to insert 5 nops at the beginning of all functions 66 and to use indirection to get at static symbols. The 5 nops 67 are required by consumers of the generated code. Currently, gdb 68 uses this to patch in a jump to the overriding function, this 69 allows all uses of the old name to forward to the replacement, 70 including existing function pointers and virtual methods. See 71 rs6000_emit_prologue for the code that handles the nop insertions. 72 73 The added indirection allows gdb to redirect accesses to static 74 symbols from the newly loaded translation unit to the existing 75 symbol, if any. @code{static} symbols are special and are handled by 76 setting the second word in the .non_lazy_symbol_pointer data 77 structure to symbol. See indirect_data for the code that handles 78 the extra indirection, and machopic_output_indirection and its use 79 of MACHO_SYMBOL_STATIC for the code that handles @code{static} 80 symbol indirection. */ 81 82 /* Section names. */ 83 section * darwin_sections[NUM_DARWIN_SECTIONS]; 84 85 /* True if we're setting __attribute__ ((ms_struct)). */ 86 int darwin_ms_struct = false; 87 88 /* A get_unnamed_section callback used to switch to an ObjC section. 89 DIRECTIVE is as for output_section_asm_op. */ 90 91 static void 92 output_objc_section_asm_op (const void *directive) 93 { 94 static bool been_here = false; 95 96 if (! been_here) 97 { 98 static const enum darwin_section_enum tomark[] = 99 { 100 /* written, cold -> hot */ 101 objc_cat_cls_meth_section, 102 objc_cat_inst_meth_section, 103 objc_string_object_section, 104 objc_constant_string_object_section, 105 objc_selector_refs_section, 106 objc_selector_fixup_section, 107 objc_cls_refs_section, 108 objc_class_section, 109 objc_meta_class_section, 110 /* shared, hot -> cold */ 111 objc_cls_meth_section, 112 objc_inst_meth_section, 113 objc_protocol_section, 114 objc_class_names_section, 115 objc_meth_var_types_section, 116 objc_meth_var_names_section, 117 objc_category_section, 118 objc_class_vars_section, 119 objc_instance_vars_section, 120 objc_module_info_section, 121 objc_symbols_section 122 }; 123 size_t i; 124 125 been_here = true; 126 for (i = 0; i < ARRAY_SIZE (tomark); i++) 127 switch_to_section (darwin_sections[tomark[i]]); 128 } 129 output_section_asm_op (directive); 130 } 131 132 /* Implement TARGET_ASM_INIT_SECTIONS. */ 133 134 void 135 darwin_init_sections (void) 136 { 137 #define DEF_SECTION(NAME, FLAGS, DIRECTIVE, OBJC) \ 138 darwin_sections[NAME] = \ 139 get_unnamed_section (FLAGS, (OBJC \ 140 ? output_objc_section_asm_op \ 141 : output_section_asm_op), \ 142 "\t" DIRECTIVE); 143 #include "config/darwin-sections.def" 144 #undef DEF_SECTION 145 146 readonly_data_section = darwin_sections[const_section]; 147 exception_section = darwin_sections[darwin_exception_section]; 148 eh_frame_section = darwin_sections[darwin_eh_frame_section]; 149 } 150 151 int 152 name_needs_quotes (const char *name) 153 { 154 int c; 155 while ((c = *name++) != '\0') 156 if (! ISIDNUM (c) && c != '.' && c != '$') 157 return 1; 158 return 0; 159 } 160 161 /* Return true if SYM_REF can be used without an indirection. */ 162 static int 163 machopic_symbol_defined_p (rtx sym_ref) 164 { 165 if (SYMBOL_REF_FLAGS (sym_ref) & MACHO_SYMBOL_FLAG_DEFINED) 166 return true; 167 168 /* If a symbol references local and is not an extern to this 169 file, then the symbol might be able to declared as defined. */ 170 if (SYMBOL_REF_LOCAL_P (sym_ref) && ! SYMBOL_REF_EXTERNAL_P (sym_ref)) 171 { 172 /* If the symbol references a variable and the variable is a 173 common symbol, then this symbol is not defined. */ 174 if (SYMBOL_REF_FLAGS (sym_ref) & MACHO_SYMBOL_FLAG_VARIABLE) 175 { 176 tree decl = SYMBOL_REF_DECL (sym_ref); 177 if (!decl) 178 return true; 179 if (DECL_COMMON (decl)) 180 return false; 181 } 182 return true; 183 } 184 return false; 185 } 186 187 /* This module assumes that (const (symbol_ref "foo")) is a legal pic 188 reference, which will not be changed. */ 189 190 enum machopic_addr_class 191 machopic_classify_symbol (rtx sym_ref) 192 { 193 int flags; 194 bool function_p; 195 196 flags = SYMBOL_REF_FLAGS (sym_ref); 197 function_p = SYMBOL_REF_FUNCTION_P (sym_ref); 198 if (machopic_symbol_defined_p (sym_ref)) 199 return (function_p 200 ? MACHOPIC_DEFINED_FUNCTION : MACHOPIC_DEFINED_DATA); 201 else 202 return (function_p 203 ? MACHOPIC_UNDEFINED_FUNCTION : MACHOPIC_UNDEFINED_DATA); 204 } 205 206 #ifndef TARGET_FIX_AND_CONTINUE 207 #define TARGET_FIX_AND_CONTINUE 0 208 #endif 209 210 /* Indicate when fix-and-continue style code generation is being used 211 and when a reference to data should be indirected so that it can be 212 rebound in a new translation unit to reference the original instance 213 of that data. Symbol names that are for code generation local to 214 the translation unit are bound to the new translation unit; 215 currently this means symbols that begin with L or _OBJC_; 216 otherwise, we indicate that an indirect reference should be made to 217 permit the runtime to rebind new instances of the translation unit 218 to the original instance of the data. */ 219 220 static int 221 indirect_data (rtx sym_ref) 222 { 223 int lprefix; 224 const char *name; 225 226 /* If we aren't generating fix-and-continue code, don't do anything 227 special. */ 228 if (TARGET_FIX_AND_CONTINUE == 0) 229 return 0; 230 231 /* Otherwise, all symbol except symbols that begin with L or _OBJC_ 232 are indirected. Symbols that begin with L and _OBJC_ are always 233 bound to the current translation unit as they are used for 234 generated local data of the translation unit. */ 235 236 name = XSTR (sym_ref, 0); 237 238 lprefix = (((name[0] == '*' || name[0] == '&') 239 && (name[1] == 'L' || (name[1] == '"' && name[2] == 'L'))) 240 || (strncmp (name, "_OBJC_", 6) == 0)); 241 242 return ! lprefix; 243 } 244 245 246 static int 247 machopic_data_defined_p (rtx sym_ref) 248 { 249 if (indirect_data (sym_ref)) 250 return 0; 251 252 switch (machopic_classify_symbol (sym_ref)) 253 { 254 case MACHOPIC_DEFINED_DATA: 255 case MACHOPIC_DEFINED_FUNCTION: 256 return 1; 257 default: 258 return 0; 259 } 260 } 261 262 void 263 machopic_define_symbol (rtx mem) 264 { 265 rtx sym_ref; 266 267 gcc_assert (GET_CODE (mem) == MEM); 268 sym_ref = XEXP (mem, 0); 269 SYMBOL_REF_FLAGS (sym_ref) |= MACHO_SYMBOL_FLAG_DEFINED; 270 } 271 272 /* Return either ORIG or: 273 274 (const:P (unspec:P [ORIG] UNSPEC_MACHOPIC_OFFSET)) 275 276 depending on MACHO_DYNAMIC_NO_PIC_P. */ 277 rtx 278 machopic_gen_offset (rtx orig) 279 { 280 if (MACHO_DYNAMIC_NO_PIC_P) 281 return orig; 282 else 283 { 284 /* Play games to avoid marking the function as needing pic if we 285 are being called as part of the cost-estimation process. */ 286 if (current_ir_type () != IR_GIMPLE || currently_expanding_to_rtl) 287 crtl->uses_pic_offset_table = 1; 288 orig = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, orig), 289 UNSPEC_MACHOPIC_OFFSET); 290 return gen_rtx_CONST (Pmode, orig); 291 } 292 } 293 294 static GTY(()) const char * function_base_func_name; 295 static GTY(()) int current_pic_label_num; 296 297 void 298 machopic_output_function_base_name (FILE *file) 299 { 300 const char *current_name; 301 302 /* If dynamic-no-pic is on, we should not get here. */ 303 gcc_assert (!MACHO_DYNAMIC_NO_PIC_P); 304 current_name = 305 IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (current_function_decl)); 306 if (function_base_func_name != current_name) 307 { 308 ++current_pic_label_num; 309 function_base_func_name = current_name; 310 } 311 fprintf (file, "\"L%011d$pb\"", current_pic_label_num); 312 } 313 314 /* The suffix attached to non-lazy pointer symbols. */ 315 #define NON_LAZY_POINTER_SUFFIX "$non_lazy_ptr" 316 /* The suffix attached to stub symbols. */ 317 #define STUB_SUFFIX "$stub" 318 319 typedef struct GTY (()) machopic_indirection 320 { 321 /* The SYMBOL_REF for the entity referenced. */ 322 rtx symbol; 323 /* The name of the stub or non-lazy pointer. */ 324 const char * ptr_name; 325 /* True iff this entry is for a stub (as opposed to a non-lazy 326 pointer). */ 327 bool stub_p; 328 /* True iff this stub or pointer pointer has been referenced. */ 329 bool used; 330 } machopic_indirection; 331 332 /* A table mapping stub names and non-lazy pointer names to 333 SYMBOL_REFs for the stubbed-to and pointed-to entities. */ 334 335 static GTY ((param_is (struct machopic_indirection))) htab_t 336 machopic_indirections; 337 338 /* Return a hash value for a SLOT in the indirections hash table. */ 339 340 void 341 darwin_rename_builtins (void) 342 { 343 /* The system ___divdc3 routine in libSystem on darwin10 is not 344 accurate to 1ulp, ours is, so we avoid ever using the system name 345 for this routine and instead install a non-conflicting name that 346 is accurate. 347 348 When -ffast-math or -funsafe-math-optimizations is given, we can 349 use the faster version. */ 350 if (!flag_unsafe_math_optimizations) 351 { 352 int dcode = (BUILT_IN_COMPLEX_DIV_MIN 353 + DCmode - MIN_MODE_COMPLEX_FLOAT); 354 tree fn = built_in_decls[dcode]; 355 /* Fortran and c call TARGET_INIT_BUILTINS and 356 TARGET_INIT_LIBFUNCS at different times, so we have to put a 357 call into each to ensure that at least one of them is called 358 after build_common_builtin_nodes. A better fix is to add a 359 new hook to run after build_common_builtin_nodes runs. */ 360 if (fn) 361 set_user_assembler_name (fn, "___ieee_divdc3"); 362 fn = implicit_built_in_decls[dcode]; 363 if (fn) 364 set_user_assembler_name (fn, "___ieee_divdc3"); 365 } 366 } 367 368 static hashval_t 369 machopic_indirection_hash (const void *slot) 370 { 371 const machopic_indirection *p = (const machopic_indirection *) slot; 372 return htab_hash_string (p->ptr_name); 373 } 374 375 /* Returns true if the KEY is the same as that associated with 376 SLOT. */ 377 378 static int 379 machopic_indirection_eq (const void *slot, const void *key) 380 { 381 return strcmp (((const machopic_indirection *) slot)->ptr_name, 382 (const char *) key) == 0; 383 } 384 385 /* Return the name of the non-lazy pointer (if STUB_P is false) or 386 stub (if STUB_B is true) corresponding to the given name. */ 387 388 const char * 389 machopic_indirection_name (rtx sym_ref, bool stub_p) 390 { 391 char *buffer; 392 const char *name = XSTR (sym_ref, 0); 393 size_t namelen = strlen (name); 394 machopic_indirection *p; 395 void ** slot; 396 bool saw_star = false; 397 bool needs_quotes; 398 const char *suffix; 399 const char *prefix = user_label_prefix; 400 const char *quote = ""; 401 tree id; 402 403 id = maybe_get_identifier (name); 404 if (id) 405 { 406 tree id_orig = id; 407 408 while (IDENTIFIER_TRANSPARENT_ALIAS (id)) 409 id = TREE_CHAIN (id); 410 if (id != id_orig) 411 { 412 name = IDENTIFIER_POINTER (id); 413 namelen = strlen (name); 414 } 415 } 416 417 if (name[0] == '*') 418 { 419 saw_star = true; 420 prefix = ""; 421 ++name; 422 --namelen; 423 } 424 425 needs_quotes = name_needs_quotes (name); 426 if (needs_quotes) 427 { 428 quote = "\""; 429 } 430 431 if (stub_p) 432 suffix = STUB_SUFFIX; 433 else 434 suffix = NON_LAZY_POINTER_SUFFIX; 435 436 buffer = XALLOCAVEC (char, strlen ("&L") 437 + strlen (prefix) 438 + namelen 439 + strlen (suffix) 440 + 2 * strlen (quote) 441 + 1 /* '\0' */); 442 443 /* Construct the name of the non-lazy pointer or stub. */ 444 sprintf (buffer, "&%sL%s%s%s%s", quote, prefix, name, suffix, quote); 445 446 if (!machopic_indirections) 447 machopic_indirections = htab_create_ggc (37, 448 machopic_indirection_hash, 449 machopic_indirection_eq, 450 /*htab_del=*/NULL); 451 452 slot = htab_find_slot_with_hash (machopic_indirections, buffer, 453 htab_hash_string (buffer), INSERT); 454 if (*slot) 455 { 456 p = (machopic_indirection *) *slot; 457 } 458 else 459 { 460 p = (machopic_indirection *) ggc_alloc (sizeof (machopic_indirection)); 461 p->symbol = sym_ref; 462 p->ptr_name = xstrdup (buffer); 463 p->stub_p = stub_p; 464 p->used = false; 465 *slot = p; 466 } 467 468 return p->ptr_name; 469 } 470 471 /* Return the name of the stub for the mcount function. */ 472 473 const char* 474 machopic_mcount_stub_name (void) 475 { 476 rtx symbol = gen_rtx_SYMBOL_REF (Pmode, "*mcount"); 477 return machopic_indirection_name (symbol, /*stub_p=*/true); 478 } 479 480 /* If NAME is the name of a stub or a non-lazy pointer , mark the stub 481 or non-lazy pointer as used -- and mark the object to which the 482 pointer/stub refers as used as well, since the pointer/stub will 483 emit a reference to it. */ 484 485 void 486 machopic_validate_stub_or_non_lazy_ptr (const char *name) 487 { 488 machopic_indirection *p; 489 490 p = ((machopic_indirection *) 491 (htab_find_with_hash (machopic_indirections, name, 492 htab_hash_string (name)))); 493 if (p && ! p->used) 494 { 495 const char *real_name; 496 tree id; 497 498 p->used = true; 499 500 /* Do what output_addr_const will do when we actually call it. */ 501 if (SYMBOL_REF_DECL (p->symbol)) 502 mark_decl_referenced (SYMBOL_REF_DECL (p->symbol)); 503 504 real_name = targetm.strip_name_encoding (XSTR (p->symbol, 0)); 505 506 id = maybe_get_identifier (real_name); 507 if (id) 508 mark_referenced (id); 509 } 510 } 511 512 /* Transform ORIG, which may be any data source, to the corresponding 513 source using indirections. */ 514 515 rtx 516 machopic_indirect_data_reference (rtx orig, rtx reg) 517 { 518 rtx ptr_ref = orig; 519 520 if (! MACHOPIC_INDIRECT) 521 return orig; 522 523 if (GET_CODE (orig) == SYMBOL_REF) 524 { 525 int defined = machopic_data_defined_p (orig); 526 527 if (defined && MACHO_DYNAMIC_NO_PIC_P) 528 { 529 #if defined (TARGET_TOC) 530 /* Create a new register for CSE opportunities. */ 531 rtx hi_reg = (!can_create_pseudo_p () ? reg : gen_reg_rtx (Pmode)); 532 emit_insn (gen_macho_high (hi_reg, orig)); 533 emit_insn (gen_macho_low (reg, hi_reg, orig)); 534 #else 535 /* some other cpu -- writeme! */ 536 gcc_unreachable (); 537 #endif 538 return reg; 539 } 540 else if (defined) 541 { 542 #if defined (TARGET_TOC) || defined (HAVE_lo_sum) 543 rtx offset = machopic_gen_offset (orig); 544 #endif 545 546 #if defined (TARGET_TOC) /* i.e., PowerPC */ 547 rtx hi_sum_reg = (!can_create_pseudo_p () 548 ? reg 549 : gen_reg_rtx (Pmode)); 550 551 gcc_assert (reg); 552 553 emit_insn (gen_rtx_SET (Pmode, hi_sum_reg, 554 gen_rtx_PLUS (Pmode, pic_offset_table_rtx, 555 gen_rtx_HIGH (Pmode, offset)))); 556 emit_insn (gen_rtx_SET (Pmode, reg, 557 gen_rtx_LO_SUM (Pmode, hi_sum_reg, 558 copy_rtx (offset)))); 559 560 orig = reg; 561 #else 562 #if defined (HAVE_lo_sum) 563 gcc_assert (reg); 564 565 emit_insn (gen_rtx_SET (VOIDmode, reg, 566 gen_rtx_HIGH (Pmode, offset))); 567 emit_insn (gen_rtx_SET (VOIDmode, reg, 568 gen_rtx_LO_SUM (Pmode, reg, 569 copy_rtx (offset)))); 570 emit_use (pic_offset_table_rtx); 571 572 orig = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, reg); 573 #endif 574 #endif 575 return orig; 576 } 577 578 ptr_ref = (gen_rtx_SYMBOL_REF 579 (Pmode, 580 machopic_indirection_name (orig, /*stub_p=*/false))); 581 582 SYMBOL_REF_DATA (ptr_ref) = SYMBOL_REF_DATA (orig); 583 584 ptr_ref = gen_const_mem (Pmode, ptr_ref); 585 machopic_define_symbol (ptr_ref); 586 587 return ptr_ref; 588 } 589 else if (GET_CODE (orig) == CONST) 590 { 591 rtx base, result; 592 593 /* legitimize both operands of the PLUS */ 594 if (GET_CODE (XEXP (orig, 0)) == PLUS) 595 { 596 base = machopic_indirect_data_reference (XEXP (XEXP (orig, 0), 0), 597 reg); 598 orig = machopic_indirect_data_reference (XEXP (XEXP (orig, 0), 1), 599 (base == reg ? 0 : reg)); 600 } 601 else 602 return orig; 603 604 if (MACHOPIC_PURE && GET_CODE (orig) == CONST_INT) 605 result = plus_constant (base, INTVAL (orig)); 606 else 607 result = gen_rtx_PLUS (Pmode, base, orig); 608 609 if (MACHOPIC_JUST_INDIRECT && GET_CODE (base) == MEM) 610 { 611 if (reg) 612 { 613 emit_move_insn (reg, result); 614 result = reg; 615 } 616 else 617 { 618 result = force_reg (GET_MODE (result), result); 619 } 620 } 621 622 return result; 623 624 } 625 else if (GET_CODE (orig) == MEM) 626 XEXP (ptr_ref, 0) = machopic_indirect_data_reference (XEXP (orig, 0), reg); 627 /* When the target is i386, this code prevents crashes due to the 628 compiler's ignorance on how to move the PIC base register to 629 other registers. (The reload phase sometimes introduces such 630 insns.) */ 631 else if (GET_CODE (orig) == PLUS 632 && GET_CODE (XEXP (orig, 0)) == REG 633 && REGNO (XEXP (orig, 0)) == PIC_OFFSET_TABLE_REGNUM 634 #ifdef I386 635 /* Prevent the same register from being erroneously used 636 as both the base and index registers. */ 637 && GET_CODE (XEXP (orig, 1)) == CONST 638 #endif 639 && reg) 640 { 641 emit_move_insn (reg, XEXP (orig, 0)); 642 XEXP (ptr_ref, 0) = reg; 643 } 644 return ptr_ref; 645 } 646 647 /* Transform TARGET (a MEM), which is a function call target, to the 648 corresponding symbol_stub if necessary. Return a new MEM. */ 649 650 rtx 651 machopic_indirect_call_target (rtx target) 652 { 653 if (GET_CODE (target) != MEM) 654 return target; 655 656 if (MACHOPIC_INDIRECT 657 && GET_CODE (XEXP (target, 0)) == SYMBOL_REF 658 && !(SYMBOL_REF_FLAGS (XEXP (target, 0)) 659 & MACHO_SYMBOL_FLAG_DEFINED)) 660 { 661 rtx sym_ref = XEXP (target, 0); 662 const char *stub_name = machopic_indirection_name (sym_ref, 663 /*stub_p=*/true); 664 enum machine_mode mode = GET_MODE (sym_ref); 665 666 XEXP (target, 0) = gen_rtx_SYMBOL_REF (mode, stub_name); 667 SYMBOL_REF_DATA (XEXP (target, 0)) = SYMBOL_REF_DATA (sym_ref); 668 MEM_READONLY_P (target) = 1; 669 MEM_NOTRAP_P (target) = 1; 670 } 671 672 return target; 673 } 674 675 rtx 676 machopic_legitimize_pic_address (rtx orig, enum machine_mode mode, rtx reg) 677 { 678 rtx pic_ref = orig; 679 680 if (! MACHOPIC_INDIRECT) 681 return orig; 682 683 /* First handle a simple SYMBOL_REF or LABEL_REF */ 684 if (GET_CODE (orig) == LABEL_REF 685 || (GET_CODE (orig) == SYMBOL_REF 686 )) 687 { 688 /* addr(foo) = &func+(foo-func) */ 689 orig = machopic_indirect_data_reference (orig, reg); 690 691 if (GET_CODE (orig) == PLUS 692 && GET_CODE (XEXP (orig, 0)) == REG) 693 { 694 if (reg == 0) 695 return force_reg (mode, orig); 696 697 emit_move_insn (reg, orig); 698 return reg; 699 } 700 701 if (GET_CODE (orig) == MEM) 702 { 703 if (reg == 0) 704 { 705 gcc_assert (!reload_in_progress); 706 reg = gen_reg_rtx (Pmode); 707 } 708 709 #ifdef HAVE_lo_sum 710 if (MACHO_DYNAMIC_NO_PIC_P 711 && (GET_CODE (XEXP (orig, 0)) == SYMBOL_REF 712 || GET_CODE (XEXP (orig, 0)) == LABEL_REF)) 713 { 714 #if defined (TARGET_TOC) /* ppc */ 715 rtx temp_reg = (!can_create_pseudo_p () 716 ? reg : 717 gen_reg_rtx (Pmode)); 718 rtx asym = XEXP (orig, 0); 719 rtx mem; 720 721 emit_insn (gen_macho_high (temp_reg, asym)); 722 mem = gen_const_mem (GET_MODE (orig), 723 gen_rtx_LO_SUM (Pmode, temp_reg, 724 copy_rtx (asym))); 725 emit_insn (gen_rtx_SET (VOIDmode, reg, mem)); 726 #else 727 /* Some other CPU -- WriteMe! but right now there are no other 728 platforms that can use dynamic-no-pic */ 729 gcc_unreachable (); 730 #endif 731 pic_ref = reg; 732 } 733 else 734 if (GET_CODE (XEXP (orig, 0)) == SYMBOL_REF 735 || GET_CODE (XEXP (orig, 0)) == LABEL_REF) 736 { 737 rtx offset = machopic_gen_offset (XEXP (orig, 0)); 738 #if defined (TARGET_TOC) /* i.e., PowerPC */ 739 /* Generating a new reg may expose opportunities for 740 common subexpression elimination. */ 741 rtx hi_sum_reg = (!can_create_pseudo_p () 742 ? reg 743 : gen_reg_rtx (Pmode)); 744 rtx mem; 745 rtx insn; 746 rtx sum; 747 748 sum = gen_rtx_HIGH (Pmode, offset); 749 if (! MACHO_DYNAMIC_NO_PIC_P) 750 sum = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, sum); 751 752 emit_insn (gen_rtx_SET (Pmode, hi_sum_reg, sum)); 753 754 mem = gen_const_mem (GET_MODE (orig), 755 gen_rtx_LO_SUM (Pmode, 756 hi_sum_reg, 757 copy_rtx (offset))); 758 insn = emit_insn (gen_rtx_SET (VOIDmode, reg, mem)); 759 set_unique_reg_note (insn, REG_EQUAL, pic_ref); 760 761 pic_ref = reg; 762 #else 763 emit_use (gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM)); 764 765 emit_insn (gen_rtx_SET (VOIDmode, reg, 766 gen_rtx_HIGH (Pmode, 767 gen_rtx_CONST (Pmode, 768 offset)))); 769 emit_insn (gen_rtx_SET (VOIDmode, reg, 770 gen_rtx_LO_SUM (Pmode, reg, 771 gen_rtx_CONST (Pmode, 772 copy_rtx (offset))))); 773 pic_ref = gen_rtx_PLUS (Pmode, 774 pic_offset_table_rtx, reg); 775 #endif 776 } 777 else 778 #endif /* HAVE_lo_sum */ 779 { 780 rtx pic = pic_offset_table_rtx; 781 if (GET_CODE (pic) != REG) 782 { 783 emit_move_insn (reg, pic); 784 pic = reg; 785 } 786 #if 0 787 emit_use (gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM)); 788 #endif 789 790 if (reload_in_progress) 791 df_set_regs_ever_live (REGNO (pic), true); 792 pic_ref = gen_rtx_PLUS (Pmode, pic, 793 machopic_gen_offset (XEXP (orig, 0))); 794 } 795 796 #if !defined (TARGET_TOC) 797 emit_move_insn (reg, pic_ref); 798 pic_ref = gen_const_mem (GET_MODE (orig), reg); 799 #endif 800 } 801 else 802 { 803 804 #ifdef HAVE_lo_sum 805 if (GET_CODE (orig) == SYMBOL_REF 806 || GET_CODE (orig) == LABEL_REF) 807 { 808 rtx offset = machopic_gen_offset (orig); 809 #if defined (TARGET_TOC) /* i.e., PowerPC */ 810 rtx hi_sum_reg; 811 812 if (reg == 0) 813 { 814 gcc_assert (!reload_in_progress); 815 reg = gen_reg_rtx (Pmode); 816 } 817 818 hi_sum_reg = reg; 819 820 emit_insn (gen_rtx_SET (Pmode, hi_sum_reg, 821 (MACHO_DYNAMIC_NO_PIC_P) 822 ? gen_rtx_HIGH (Pmode, offset) 823 : gen_rtx_PLUS (Pmode, 824 pic_offset_table_rtx, 825 gen_rtx_HIGH (Pmode, 826 offset)))); 827 emit_insn (gen_rtx_SET (VOIDmode, reg, 828 gen_rtx_LO_SUM (Pmode, 829 hi_sum_reg, 830 copy_rtx (offset)))); 831 pic_ref = reg; 832 #else 833 emit_insn (gen_rtx_SET (VOIDmode, reg, 834 gen_rtx_HIGH (Pmode, offset))); 835 emit_insn (gen_rtx_SET (VOIDmode, reg, 836 gen_rtx_LO_SUM (Pmode, reg, 837 copy_rtx (offset)))); 838 pic_ref = gen_rtx_PLUS (Pmode, 839 pic_offset_table_rtx, reg); 840 #endif 841 } 842 else 843 #endif /* HAVE_lo_sum */ 844 { 845 if (REG_P (orig) 846 || GET_CODE (orig) == SUBREG) 847 { 848 return orig; 849 } 850 else 851 { 852 rtx pic = pic_offset_table_rtx; 853 if (GET_CODE (pic) != REG) 854 { 855 emit_move_insn (reg, pic); 856 pic = reg; 857 } 858 #if 0 859 emit_use (pic_offset_table_rtx); 860 #endif 861 if (reload_in_progress) 862 df_set_regs_ever_live (REGNO (pic), true); 863 pic_ref = gen_rtx_PLUS (Pmode, 864 pic, 865 machopic_gen_offset (orig)); 866 } 867 } 868 } 869 870 if (GET_CODE (pic_ref) != REG) 871 { 872 if (reg != 0) 873 { 874 emit_move_insn (reg, pic_ref); 875 return reg; 876 } 877 else 878 { 879 return force_reg (mode, pic_ref); 880 } 881 } 882 else 883 { 884 return pic_ref; 885 } 886 } 887 888 else if (GET_CODE (orig) == SYMBOL_REF) 889 return orig; 890 891 else if (GET_CODE (orig) == PLUS 892 && (GET_CODE (XEXP (orig, 0)) == MEM 893 || GET_CODE (XEXP (orig, 0)) == SYMBOL_REF 894 || GET_CODE (XEXP (orig, 0)) == LABEL_REF) 895 && XEXP (orig, 0) != pic_offset_table_rtx 896 && GET_CODE (XEXP (orig, 1)) != REG) 897 898 { 899 rtx base; 900 int is_complex = (GET_CODE (XEXP (orig, 0)) == MEM); 901 902 base = machopic_legitimize_pic_address (XEXP (orig, 0), Pmode, reg); 903 orig = machopic_legitimize_pic_address (XEXP (orig, 1), 904 Pmode, (base == reg ? 0 : reg)); 905 if (GET_CODE (orig) == CONST_INT) 906 { 907 pic_ref = plus_constant (base, INTVAL (orig)); 908 is_complex = 1; 909 } 910 else 911 pic_ref = gen_rtx_PLUS (Pmode, base, orig); 912 913 if (reg && is_complex) 914 { 915 emit_move_insn (reg, pic_ref); 916 pic_ref = reg; 917 } 918 /* Likewise, should we set special REG_NOTEs here? */ 919 } 920 921 else if (GET_CODE (orig) == CONST) 922 { 923 return machopic_legitimize_pic_address (XEXP (orig, 0), Pmode, reg); 924 } 925 926 else if (GET_CODE (orig) == MEM 927 && GET_CODE (XEXP (orig, 0)) == SYMBOL_REF) 928 { 929 rtx addr = machopic_legitimize_pic_address (XEXP (orig, 0), Pmode, reg); 930 addr = replace_equiv_address (orig, addr); 931 emit_move_insn (reg, addr); 932 pic_ref = reg; 933 } 934 935 return pic_ref; 936 } 937 938 /* Output the stub or non-lazy pointer in *SLOT, if it has been used. 939 DATA is the FILE* for assembly output. Called from 940 htab_traverse. */ 941 942 static int 943 machopic_output_indirection (void **slot, void *data) 944 { 945 machopic_indirection *p = *((machopic_indirection **) slot); 946 FILE *asm_out_file = (FILE *) data; 947 rtx symbol; 948 const char *sym_name; 949 const char *ptr_name; 950 951 if (!p->used) 952 return 1; 953 954 symbol = p->symbol; 955 sym_name = XSTR (symbol, 0); 956 ptr_name = p->ptr_name; 957 958 if (p->stub_p) 959 { 960 char *sym; 961 char *stub; 962 tree id; 963 964 id = maybe_get_identifier (sym_name); 965 if (id) 966 { 967 tree id_orig = id; 968 969 while (IDENTIFIER_TRANSPARENT_ALIAS (id)) 970 id = TREE_CHAIN (id); 971 if (id != id_orig) 972 sym_name = IDENTIFIER_POINTER (id); 973 } 974 975 sym = XALLOCAVEC (char, strlen (sym_name) + 2); 976 if (sym_name[0] == '*' || sym_name[0] == '&') 977 strcpy (sym, sym_name + 1); 978 else if (sym_name[0] == '-' || sym_name[0] == '+') 979 strcpy (sym, sym_name); 980 else 981 sprintf (sym, "%s%s", user_label_prefix, sym_name); 982 983 stub = XALLOCAVEC (char, strlen (ptr_name) + 2); 984 if (ptr_name[0] == '*' || ptr_name[0] == '&') 985 strcpy (stub, ptr_name + 1); 986 else 987 sprintf (stub, "%s%s", user_label_prefix, ptr_name); 988 989 machopic_output_stub (asm_out_file, sym, stub); 990 } 991 else if (! indirect_data (symbol) 992 && (machopic_symbol_defined_p (symbol) 993 || SYMBOL_REF_LOCAL_P (symbol))) 994 { 995 switch_to_section (data_section); 996 assemble_align (GET_MODE_ALIGNMENT (Pmode)); 997 assemble_label (ptr_name); 998 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, sym_name), 999 GET_MODE_SIZE (Pmode), 1000 GET_MODE_ALIGNMENT (Pmode), 1); 1001 } 1002 else 1003 { 1004 rtx init = const0_rtx; 1005 1006 switch_to_section (darwin_sections[machopic_nl_symbol_ptr_section]); 1007 1008 /* Mach-O symbols are passed around in code through indirect 1009 references and the original symbol_ref hasn't passed through 1010 the generic handling and reference-catching in 1011 output_operand, so we need to manually mark weak references 1012 as such. */ 1013 if (SYMBOL_REF_WEAK (symbol)) 1014 { 1015 tree decl = SYMBOL_REF_DECL (symbol); 1016 gcc_assert (DECL_P (decl)); 1017 1018 if (decl != NULL_TREE 1019 && DECL_EXTERNAL (decl) && TREE_PUBLIC (decl) 1020 /* Handle only actual external-only definitions, not 1021 e.g. extern inline code or variables for which 1022 storage has been allocated. */ 1023 && !TREE_STATIC (decl)) 1024 { 1025 fputs ("\t.weak_reference ", asm_out_file); 1026 assemble_name (asm_out_file, sym_name); 1027 fputc ('\n', asm_out_file); 1028 } 1029 } 1030 1031 assemble_name (asm_out_file, ptr_name); 1032 fprintf (asm_out_file, ":\n"); 1033 1034 fprintf (asm_out_file, "\t.indirect_symbol "); 1035 assemble_name (asm_out_file, sym_name); 1036 fprintf (asm_out_file, "\n"); 1037 1038 /* Variables that are marked with MACHO_SYMBOL_STATIC need to 1039 have their symbol name instead of 0 in the second entry of 1040 the non-lazy symbol pointer data structure when they are 1041 defined. This allows the runtime to rebind newer instances 1042 of the translation unit with the original instance of the 1043 symbol. */ 1044 1045 if ((SYMBOL_REF_FLAGS (symbol) & MACHO_SYMBOL_STATIC) 1046 && machopic_symbol_defined_p (symbol)) 1047 init = gen_rtx_SYMBOL_REF (Pmode, sym_name); 1048 1049 assemble_integer (init, GET_MODE_SIZE (Pmode), 1050 GET_MODE_ALIGNMENT (Pmode), 1); 1051 } 1052 1053 return 1; 1054 } 1055 1056 void 1057 machopic_finish (FILE *asm_out_file) 1058 { 1059 if (machopic_indirections) 1060 htab_traverse_noresize (machopic_indirections, 1061 machopic_output_indirection, 1062 asm_out_file); 1063 } 1064 1065 int 1066 machopic_operand_p (rtx op) 1067 { 1068 if (MACHOPIC_JUST_INDIRECT) 1069 return (GET_CODE (op) == SYMBOL_REF 1070 && machopic_symbol_defined_p (op)); 1071 else 1072 return (GET_CODE (op) == CONST 1073 && GET_CODE (XEXP (op, 0)) == UNSPEC 1074 && XINT (XEXP (op, 0), 1) == UNSPEC_MACHOPIC_OFFSET); 1075 } 1076 1077 /* This function records whether a given name corresponds to a defined 1078 or undefined function or variable, for machopic_classify_ident to 1079 use later. */ 1080 1081 void 1082 darwin_encode_section_info (tree decl, rtx rtl, int first ATTRIBUTE_UNUSED) 1083 { 1084 rtx sym_ref; 1085 1086 /* Do the standard encoding things first. */ 1087 default_encode_section_info (decl, rtl, first); 1088 1089 if (TREE_CODE (decl) != FUNCTION_DECL && TREE_CODE (decl) != VAR_DECL) 1090 return; 1091 1092 sym_ref = XEXP (rtl, 0); 1093 if (TREE_CODE (decl) == VAR_DECL) 1094 SYMBOL_REF_FLAGS (sym_ref) |= MACHO_SYMBOL_FLAG_VARIABLE; 1095 1096 if (!DECL_EXTERNAL (decl) 1097 && (!TREE_PUBLIC (decl) || !DECL_WEAK (decl)) 1098 && ! lookup_attribute ("weakref", DECL_ATTRIBUTES (decl)) 1099 && ((TREE_STATIC (decl) 1100 && (!DECL_COMMON (decl) || !TREE_PUBLIC (decl))) 1101 || (!DECL_COMMON (decl) && DECL_INITIAL (decl) 1102 && DECL_INITIAL (decl) != error_mark_node))) 1103 SYMBOL_REF_FLAGS (sym_ref) |= MACHO_SYMBOL_FLAG_DEFINED; 1104 1105 if (! TREE_PUBLIC (decl)) 1106 SYMBOL_REF_FLAGS (sym_ref) |= MACHO_SYMBOL_STATIC; 1107 } 1108 1109 void 1110 darwin_mark_decl_preserved (const char *name) 1111 { 1112 fprintf (asm_out_file, ".no_dead_strip "); 1113 assemble_name (asm_out_file, name); 1114 fputc ('\n', asm_out_file); 1115 } 1116 1117 static section * 1118 darwin_text_section (int reloc, int weak) 1119 { 1120 if (reloc) 1121 return (weak 1122 ? darwin_sections[text_unlikely_coal_section] 1123 : unlikely_text_section ()); 1124 else 1125 return (weak 1126 ? darwin_sections[text_coal_section] 1127 : text_section); 1128 } 1129 1130 static section * 1131 darwin_rodata_section (int weak) 1132 { 1133 return (weak 1134 ? darwin_sections[const_coal_section] 1135 : darwin_sections[const_section]); 1136 } 1137 1138 static section * 1139 darwin_mergeable_string_section (tree exp, 1140 unsigned HOST_WIDE_INT align) 1141 { 1142 if (flag_merge_constants 1143 && TREE_CODE (exp) == STRING_CST 1144 && TREE_CODE (TREE_TYPE (exp)) == ARRAY_TYPE 1145 && align <= 256 1146 && (int_size_in_bytes (TREE_TYPE (exp)) 1147 == TREE_STRING_LENGTH (exp)) 1148 && ((size_t) TREE_STRING_LENGTH (exp) 1149 == strlen (TREE_STRING_POINTER (exp)) + 1)) 1150 return darwin_sections[cstring_section]; 1151 1152 return readonly_data_section; 1153 } 1154 1155 #ifndef HAVE_GAS_LITERAL16 1156 #define HAVE_GAS_LITERAL16 0 1157 #endif 1158 1159 static section * 1160 darwin_mergeable_constant_section (tree exp, 1161 unsigned HOST_WIDE_INT align) 1162 { 1163 enum machine_mode mode = DECL_MODE (exp); 1164 unsigned int modesize = GET_MODE_BITSIZE (mode); 1165 1166 if (flag_merge_constants 1167 && mode != VOIDmode 1168 && mode != BLKmode 1169 && modesize <= align 1170 && align >= 8 1171 && align <= 256 1172 && (align & (align -1)) == 0) 1173 { 1174 tree size = TYPE_SIZE_UNIT (TREE_TYPE (exp)); 1175 1176 if (TREE_CODE (size) == INTEGER_CST 1177 && TREE_INT_CST_LOW (size) == 4 1178 && TREE_INT_CST_HIGH (size) == 0) 1179 return darwin_sections[literal4_section]; 1180 else if (TREE_CODE (size) == INTEGER_CST 1181 && TREE_INT_CST_LOW (size) == 8 1182 && TREE_INT_CST_HIGH (size) == 0) 1183 return darwin_sections[literal8_section]; 1184 else if (HAVE_GAS_LITERAL16 1185 && TARGET_64BIT 1186 && TREE_CODE (size) == INTEGER_CST 1187 && TREE_INT_CST_LOW (size) == 16 1188 && TREE_INT_CST_HIGH (size) == 0) 1189 return darwin_sections[literal16_section]; 1190 else 1191 return readonly_data_section; 1192 } 1193 1194 return readonly_data_section; 1195 } 1196 1197 int 1198 machopic_reloc_rw_mask (void) 1199 { 1200 return MACHOPIC_INDIRECT ? 3 : 0; 1201 } 1202 1203 section * 1204 machopic_select_section (tree decl, 1205 int reloc, 1206 unsigned HOST_WIDE_INT align) 1207 { 1208 bool weak = (DECL_P (decl) 1209 && DECL_WEAK (decl) 1210 && !lookup_attribute ("weak_import", 1211 DECL_ATTRIBUTES (decl))); 1212 section *base_section; 1213 1214 switch (categorize_decl_for_section (decl, reloc)) 1215 { 1216 case SECCAT_TEXT: 1217 base_section = darwin_text_section (reloc, weak); 1218 break; 1219 1220 case SECCAT_RODATA: 1221 case SECCAT_SRODATA: 1222 base_section = darwin_rodata_section (weak); 1223 break; 1224 1225 case SECCAT_RODATA_MERGE_STR: 1226 base_section = darwin_mergeable_string_section (decl, align); 1227 break; 1228 1229 case SECCAT_RODATA_MERGE_STR_INIT: 1230 base_section = darwin_mergeable_string_section (DECL_INITIAL (decl), align); 1231 break; 1232 1233 case SECCAT_RODATA_MERGE_CONST: 1234 base_section = darwin_mergeable_constant_section (decl, align); 1235 break; 1236 1237 case SECCAT_DATA: 1238 case SECCAT_DATA_REL: 1239 case SECCAT_DATA_REL_LOCAL: 1240 case SECCAT_DATA_REL_RO: 1241 case SECCAT_DATA_REL_RO_LOCAL: 1242 case SECCAT_SDATA: 1243 case SECCAT_TDATA: 1244 case SECCAT_BSS: 1245 case SECCAT_SBSS: 1246 case SECCAT_TBSS: 1247 if (TREE_READONLY (decl) || TREE_CONSTANT (decl)) 1248 base_section = weak ? darwin_sections[const_data_coal_section] 1249 : darwin_sections[const_data_section]; 1250 else 1251 base_section = weak ? darwin_sections[data_coal_section] : data_section; 1252 break; 1253 1254 default: 1255 gcc_unreachable (); 1256 } 1257 1258 /* Darwin weird special cases. */ 1259 if (TREE_CODE (decl) == CONSTRUCTOR 1260 && TREE_TYPE (decl) 1261 && TREE_CODE (TREE_TYPE (decl)) == RECORD_TYPE 1262 && TYPE_NAME (TREE_TYPE (decl))) 1263 { 1264 tree name = TYPE_NAME (TREE_TYPE (decl)); 1265 if (TREE_CODE (name) == TYPE_DECL) 1266 name = DECL_NAME (name); 1267 1268 if (!strcmp (IDENTIFIER_POINTER (name), "__builtin_ObjCString")) 1269 { 1270 if (flag_next_runtime) 1271 return darwin_sections[objc_constant_string_object_section]; 1272 else 1273 return darwin_sections[objc_string_object_section]; 1274 } 1275 else 1276 return base_section; 1277 } 1278 else if (TREE_CODE (decl) == VAR_DECL 1279 && DECL_NAME (decl) 1280 && TREE_CODE (DECL_NAME (decl)) == IDENTIFIER_NODE 1281 && IDENTIFIER_POINTER (DECL_NAME (decl)) 1282 && !strncmp (IDENTIFIER_POINTER (DECL_NAME (decl)), "_OBJC_", 6)) 1283 { 1284 const char *name = IDENTIFIER_POINTER (DECL_NAME (decl)); 1285 1286 if (!strncmp (name, "_OBJC_CLASS_METHODS_", 20)) 1287 return darwin_sections[objc_cls_meth_section]; 1288 else if (!strncmp (name, "_OBJC_INSTANCE_METHODS_", 23)) 1289 return darwin_sections[objc_inst_meth_section]; 1290 else if (!strncmp (name, "_OBJC_CATEGORY_CLASS_METHODS_", 20)) 1291 return darwin_sections[objc_cat_cls_meth_section]; 1292 else if (!strncmp (name, "_OBJC_CATEGORY_INSTANCE_METHODS_", 23)) 1293 return darwin_sections[objc_cat_inst_meth_section]; 1294 else if (!strncmp (name, "_OBJC_CLASS_VARIABLES_", 22)) 1295 return darwin_sections[objc_class_vars_section]; 1296 else if (!strncmp (name, "_OBJC_INSTANCE_VARIABLES_", 25)) 1297 return darwin_sections[objc_instance_vars_section]; 1298 else if (!strncmp (name, "_OBJC_CLASS_PROTOCOLS_", 22)) 1299 return darwin_sections[objc_cat_cls_meth_section]; 1300 else if (!strncmp (name, "_OBJC_CLASS_NAME_", 17)) 1301 return darwin_sections[objc_class_names_section]; 1302 else if (!strncmp (name, "_OBJC_METH_VAR_NAME_", 20)) 1303 return darwin_sections[objc_meth_var_names_section]; 1304 else if (!strncmp (name, "_OBJC_METH_VAR_TYPE_", 20)) 1305 return darwin_sections[objc_meth_var_types_section]; 1306 else if (!strncmp (name, "_OBJC_CLASS_REFERENCES", 22)) 1307 return darwin_sections[objc_cls_refs_section]; 1308 else if (!strncmp (name, "_OBJC_CLASS_", 12)) 1309 return darwin_sections[objc_class_section]; 1310 else if (!strncmp (name, "_OBJC_METACLASS_", 16)) 1311 return darwin_sections[objc_meta_class_section]; 1312 else if (!strncmp (name, "_OBJC_CATEGORY_", 15)) 1313 return darwin_sections[objc_category_section]; 1314 else if (!strncmp (name, "_OBJC_SELECTOR_REFERENCES", 25)) 1315 return darwin_sections[objc_selector_refs_section]; 1316 else if (!strncmp (name, "_OBJC_SELECTOR_FIXUP", 20)) 1317 return darwin_sections[objc_selector_fixup_section]; 1318 else if (!strncmp (name, "_OBJC_SYMBOLS", 13)) 1319 return darwin_sections[objc_symbols_section]; 1320 else if (!strncmp (name, "_OBJC_MODULES", 13)) 1321 return darwin_sections[objc_module_info_section]; 1322 else if (!strncmp (name, "_OBJC_IMAGE_INFO", 16)) 1323 return darwin_sections[objc_image_info_section]; 1324 else if (!strncmp (name, "_OBJC_PROTOCOL_INSTANCE_METHODS_", 32)) 1325 return darwin_sections[objc_cat_inst_meth_section]; 1326 else if (!strncmp (name, "_OBJC_PROTOCOL_CLASS_METHODS_", 29)) 1327 return darwin_sections[objc_cat_cls_meth_section]; 1328 else if (!strncmp (name, "_OBJC_PROTOCOL_REFS_", 20)) 1329 return darwin_sections[objc_cat_cls_meth_section]; 1330 else if (!strncmp (name, "_OBJC_PROTOCOL_", 15)) 1331 return darwin_sections[objc_protocol_section]; 1332 else 1333 return base_section; 1334 } 1335 1336 return base_section; 1337 } 1338 1339 /* This can be called with address expressions as "rtx". 1340 They must go in "const". */ 1341 1342 section * 1343 machopic_select_rtx_section (enum machine_mode mode, rtx x, 1344 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED) 1345 { 1346 if (GET_MODE_SIZE (mode) == 8 1347 && (GET_CODE (x) == CONST_INT 1348 || GET_CODE (x) == CONST_DOUBLE)) 1349 return darwin_sections[literal8_section]; 1350 else if (GET_MODE_SIZE (mode) == 4 1351 && (GET_CODE (x) == CONST_INT 1352 || GET_CODE (x) == CONST_DOUBLE)) 1353 return darwin_sections[literal4_section]; 1354 else if (HAVE_GAS_LITERAL16 1355 && TARGET_64BIT 1356 && GET_MODE_SIZE (mode) == 16 1357 && (GET_CODE (x) == CONST_INT 1358 || GET_CODE (x) == CONST_DOUBLE 1359 || GET_CODE (x) == CONST_VECTOR)) 1360 return darwin_sections[literal16_section]; 1361 else if (MACHOPIC_INDIRECT 1362 && (GET_CODE (x) == SYMBOL_REF 1363 || GET_CODE (x) == CONST 1364 || GET_CODE (x) == LABEL_REF)) 1365 return darwin_sections[const_data_section]; 1366 else 1367 return darwin_sections[const_section]; 1368 } 1369 1370 void 1371 machopic_asm_out_constructor (rtx symbol, int priority ATTRIBUTE_UNUSED) 1372 { 1373 if (MACHOPIC_INDIRECT) 1374 switch_to_section (darwin_sections[mod_init_section]); 1375 else 1376 switch_to_section (darwin_sections[constructor_section]); 1377 assemble_align (POINTER_SIZE); 1378 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1); 1379 1380 if (! MACHOPIC_INDIRECT) 1381 fprintf (asm_out_file, ".reference .constructors_used\n"); 1382 } 1383 1384 void 1385 machopic_asm_out_destructor (rtx symbol, int priority ATTRIBUTE_UNUSED) 1386 { 1387 if (MACHOPIC_INDIRECT) 1388 switch_to_section (darwin_sections[mod_term_section]); 1389 else 1390 switch_to_section (darwin_sections[destructor_section]); 1391 assemble_align (POINTER_SIZE); 1392 assemble_integer (symbol, POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1); 1393 1394 if (! MACHOPIC_INDIRECT) 1395 fprintf (asm_out_file, ".reference .destructors_used\n"); 1396 } 1397 1398 void 1399 darwin_globalize_label (FILE *stream, const char *name) 1400 { 1401 if (!!strncmp (name, "_OBJC_", 6)) 1402 default_globalize_label (stream, name); 1403 } 1404 1405 /* This routine returns non-zero if 'name' starts with the special objective-c 1406 anonymous file-scope static name. It accommodates c++'s mangling of such 1407 symbols (in this case the symbols will have form _ZL{d}*_OBJC_* d=digit). */ 1408 1409 int 1410 darwin_label_is_anonymous_local_objc_name (const char *name) 1411 { 1412 const unsigned char *p = (const unsigned char *) name; 1413 if (*p != '_') 1414 return 0; 1415 if (p[1] == 'Z' && p[2] == 'L') 1416 { 1417 p += 3; 1418 while (*p >= '0' && *p <= '9') 1419 p++; 1420 } 1421 return (!strncmp ((const char *)p, "_OBJC_", 6)); 1422 } 1423 1424 /* LTO support for Mach-O. */ 1425 1426 /* Section names for LTO sections. */ 1427 static unsigned int lto_section_names_offset = 0; 1428 1429 /* This is the obstack which we use to allocate the many strings. */ 1430 static struct obstack lto_section_names_obstack; 1431 1432 /* Segment name for LTO sections. */ 1433 #define LTO_SEGMENT_NAME "__GNU_LTO" 1434 1435 /* Section name for LTO section names section. */ 1436 #define LTO_NAMES_SECTION "__section_names" 1437 1438 /* File to temporarily store LTO data. This is appended to asm_out_file 1439 in darwin_end_file. */ 1440 static FILE *lto_asm_out_file, *saved_asm_out_file; 1441 static char *lto_asm_out_name; 1442 1443 /* Prepare asm_out_file for LTO output. For darwin, this means hiding 1444 asm_out_file and switching to an alternative output file. */ 1445 void 1446 darwin_asm_lto_start (void) 1447 { 1448 gcc_assert (! saved_asm_out_file); 1449 saved_asm_out_file = asm_out_file; 1450 if (! lto_asm_out_name) 1451 lto_asm_out_name = make_temp_file (".lto.s"); 1452 lto_asm_out_file = fopen (lto_asm_out_name, "a"); 1453 if (lto_asm_out_file == NULL) 1454 fatal_error ("failed to open temporary file %s for LTO output", 1455 lto_asm_out_name); 1456 asm_out_file = lto_asm_out_file; 1457 } 1458 1459 /* Restore asm_out_file. */ 1460 void 1461 darwin_asm_lto_end (void) 1462 { 1463 gcc_assert (saved_asm_out_file); 1464 fclose (lto_asm_out_file); 1465 asm_out_file = saved_asm_out_file; 1466 saved_asm_out_file = NULL; 1467 } 1468 1469 void 1470 darwin_asm_named_section (const char *name, 1471 unsigned int flags, 1472 tree decl ATTRIBUTE_UNUSED) 1473 { 1474 /* LTO sections go in a special segment __GNU_LTO. We want to replace the 1475 section name with something we can use to represent arbitrary-length 1476 names (section names in Mach-O are at most 16 characters long). */ 1477 if (strncmp (name, LTO_SECTION_NAME_PREFIX, 1478 strlen (LTO_SECTION_NAME_PREFIX)) == 0) 1479 { 1480 /* We expect certain flags to be set... */ 1481 gcc_assert ((flags & (SECTION_DEBUG | SECTION_NAMED)) 1482 == (SECTION_DEBUG | SECTION_NAMED)); 1483 1484 /* Add the section name to the things to output when we end the 1485 current assembler output file. 1486 This is all not very efficient, but that doesn't matter -- this 1487 shouldn't be a hot path in the compiler... */ 1488 obstack_1grow (<o_section_names_obstack, '\t'); 1489 obstack_grow (<o_section_names_obstack, ".ascii ", 7); 1490 obstack_1grow (<o_section_names_obstack, '"'); 1491 obstack_grow (<o_section_names_obstack, name, strlen (name)); 1492 obstack_grow (<o_section_names_obstack, "\\0\"\n", 4); 1493 1494 /* Output the dummy section name. */ 1495 fprintf (asm_out_file, "\t# %s\n", name); 1496 fprintf (asm_out_file, "\t.section %s,__%08X,regular,debug\n", 1497 LTO_SEGMENT_NAME, lto_section_names_offset); 1498 1499 /* Update the offset for the next section name. Make sure we stay 1500 within reasonable length. */ 1501 lto_section_names_offset += strlen (name) + 1; 1502 gcc_assert (lto_section_names_offset > 0 1503 && lto_section_names_offset < ((unsigned) 1 << 31)); 1504 } 1505 else 1506 fprintf (asm_out_file, "\t.section %s\n", name); 1507 } 1508 1509 void 1510 darwin_unique_section (tree decl ATTRIBUTE_UNUSED, int reloc ATTRIBUTE_UNUSED) 1511 { 1512 /* Darwin does not use unique sections. */ 1513 } 1514 1515 /* Handle __attribute__ ((apple_kext_compatibility)). 1516 This only applies to darwin kexts for 2.95 compatibility -- it shrinks the 1517 vtable for classes with this attribute (and their descendants) by not 1518 outputting the new 3.0 nondeleting destructor. This means that such 1519 objects CANNOT be allocated on the stack or as globals UNLESS they have 1520 a completely empty `operator delete'. 1521 Luckily, this fits in with the Darwin kext model. 1522 1523 This attribute also disables gcc3's potential overlaying of derived 1524 class data members on the padding at the end of the base class. */ 1525 1526 tree 1527 darwin_handle_kext_attribute (tree *node, tree name, 1528 tree args ATTRIBUTE_UNUSED, 1529 int flags ATTRIBUTE_UNUSED, 1530 bool *no_add_attrs) 1531 { 1532 /* APPLE KEXT stuff -- only applies with pure static C++ code. */ 1533 if (! TARGET_KEXTABI) 1534 { 1535 warning (0, "%qE 2.95 vtable-compatibility attribute applies " 1536 "only when compiling a kext", name); 1537 1538 *no_add_attrs = true; 1539 } 1540 else if (TREE_CODE (*node) != RECORD_TYPE) 1541 { 1542 warning (0, "%qE 2.95 vtable-compatibility attribute applies " 1543 "only to C++ classes", name); 1544 1545 *no_add_attrs = true; 1546 } 1547 1548 return NULL_TREE; 1549 } 1550 1551 /* Handle a "weak_import" attribute; arguments as in 1552 struct attribute_spec.handler. */ 1553 1554 tree 1555 darwin_handle_weak_import_attribute (tree *node, tree name, 1556 tree ARG_UNUSED (args), 1557 int ARG_UNUSED (flags), 1558 bool * no_add_attrs) 1559 { 1560 if (TREE_CODE (*node) != FUNCTION_DECL && TREE_CODE (*node) != VAR_DECL) 1561 { 1562 warning (OPT_Wattributes, "%qE attribute ignored", 1563 name); 1564 *no_add_attrs = true; 1565 } 1566 else 1567 declare_weak (*node); 1568 1569 return NULL_TREE; 1570 } 1571 1572 /* Emit a label for an FDE, making it global and/or weak if appropriate. 1573 The third parameter is nonzero if this is for exception handling. 1574 The fourth parameter is nonzero if this is just a placeholder for an 1575 FDE that we are omitting. */ 1576 1577 void 1578 darwin_emit_unwind_label (FILE *file, tree decl, int for_eh, int empty) 1579 { 1580 char *lab; 1581 1582 if (! for_eh) 1583 return; 1584 1585 lab = concat (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)), ".eh", NULL); 1586 1587 if (TREE_PUBLIC (decl)) 1588 { 1589 targetm.asm_out.globalize_label (file, lab); 1590 if (DECL_VISIBILITY (decl) == VISIBILITY_HIDDEN) 1591 { 1592 fputs ("\t.private_extern ", file); 1593 assemble_name (file, lab); 1594 fputc ('\n', file); 1595 } 1596 } 1597 1598 if (DECL_WEAK (decl)) 1599 { 1600 fputs ("\t.weak_definition ", file); 1601 assemble_name (file, lab); 1602 fputc ('\n', file); 1603 } 1604 1605 assemble_name (file, lab); 1606 if (empty) 1607 { 1608 fputs (" = 0\n", file); 1609 1610 /* Mark the absolute .eh and .eh1 style labels as needed to 1611 ensure that we don't dead code strip them and keep such 1612 labels from another instantiation point until we can fix this 1613 properly with group comdat support. */ 1614 darwin_mark_decl_preserved (lab); 1615 } 1616 else 1617 fputs (":\n", file); 1618 1619 free (lab); 1620 } 1621 1622 static GTY(()) unsigned long except_table_label_num; 1623 1624 void 1625 darwin_emit_except_table_label (FILE *file) 1626 { 1627 char section_start_label[30]; 1628 1629 ASM_GENERATE_INTERNAL_LABEL (section_start_label, "GCC_except_table", 1630 except_table_label_num++); 1631 ASM_OUTPUT_LABEL (file, section_start_label); 1632 } 1633 /* Generate a PC-relative reference to a Mach-O non-lazy-symbol. */ 1634 1635 void 1636 darwin_non_lazy_pcrel (FILE *file, rtx addr) 1637 { 1638 const char *nlp_name; 1639 1640 gcc_assert (GET_CODE (addr) == SYMBOL_REF); 1641 1642 nlp_name = machopic_indirection_name (addr, /*stub_p=*/false); 1643 fputs ("\t.long\t", file); 1644 ASM_OUTPUT_LABELREF (file, nlp_name); 1645 fputs ("-.", file); 1646 } 1647 1648 /* Emit an assembler directive to set visibility for a symbol. The 1649 only supported visibilities are VISIBILITY_DEFAULT and 1650 VISIBILITY_HIDDEN; the latter corresponds to Darwin's "private 1651 extern". There is no MACH-O equivalent of ELF's 1652 VISIBILITY_INTERNAL or VISIBILITY_PROTECTED. */ 1653 1654 void 1655 darwin_assemble_visibility (tree decl, int vis) 1656 { 1657 if (vis == VISIBILITY_DEFAULT) 1658 ; 1659 else if (vis == VISIBILITY_HIDDEN) 1660 { 1661 fputs ("\t.private_extern ", asm_out_file); 1662 assemble_name (asm_out_file, 1663 (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)))); 1664 fputs ("\n", asm_out_file); 1665 } 1666 else 1667 warning (OPT_Wattributes, "internal and protected visibility attributes " 1668 "not supported in this configuration; ignored"); 1669 } 1670 1671 /* Output a difference of two labels that will be an assembly time 1672 constant if the two labels are local. (.long lab1-lab2 will be 1673 very different if lab1 is at the boundary between two sections; it 1674 will be relocated according to the second section, not the first, 1675 so one ends up with a difference between labels in different 1676 sections, which is bad in the dwarf2 eh context for instance.) */ 1677 1678 static int darwin_dwarf_label_counter; 1679 1680 void 1681 darwin_asm_output_dwarf_delta (FILE *file, int size, 1682 const char *lab1, const char *lab2) 1683 { 1684 int islocaldiff = (lab1[0] == '*' && lab1[1] == 'L' 1685 && lab2[0] == '*' && lab2[1] == 'L'); 1686 const char *directive = (size == 8 ? ".quad" : ".long"); 1687 1688 if (islocaldiff) 1689 fprintf (file, "\t.set L$set$%d,", darwin_dwarf_label_counter); 1690 else 1691 fprintf (file, "\t%s\t", directive); 1692 assemble_name_raw (file, lab1); 1693 fprintf (file, "-"); 1694 assemble_name_raw (file, lab2); 1695 if (islocaldiff) 1696 fprintf (file, "\n\t%s L$set$%d", directive, darwin_dwarf_label_counter++); 1697 } 1698 1699 /* Output labels for the start of the DWARF sections if necessary. 1700 Initialize the stuff we need for LTO long section names support. */ 1701 void 1702 darwin_file_start (void) 1703 { 1704 if (write_symbols == DWARF2_DEBUG) 1705 { 1706 static const char * const debugnames[] = 1707 { 1708 DEBUG_FRAME_SECTION, 1709 DEBUG_INFO_SECTION, 1710 DEBUG_ABBREV_SECTION, 1711 DEBUG_ARANGES_SECTION, 1712 DEBUG_MACINFO_SECTION, 1713 DEBUG_LINE_SECTION, 1714 DEBUG_LOC_SECTION, 1715 DEBUG_PUBNAMES_SECTION, 1716 DEBUG_PUBTYPES_SECTION, 1717 DEBUG_STR_SECTION, 1718 DEBUG_RANGES_SECTION 1719 }; 1720 size_t i; 1721 1722 for (i = 0; i < ARRAY_SIZE (debugnames); i++) 1723 { 1724 int namelen; 1725 1726 switch_to_section (get_section (debugnames[i], SECTION_DEBUG, NULL)); 1727 1728 gcc_assert (strncmp (debugnames[i], "__DWARF,", 8) == 0); 1729 gcc_assert (strchr (debugnames[i] + 8, ',')); 1730 1731 namelen = strchr (debugnames[i] + 8, ',') - (debugnames[i] + 8); 1732 fprintf (asm_out_file, "Lsection%.*s:\n", namelen, debugnames[i] + 8); 1733 } 1734 } 1735 1736 /* We fill this obstack with the complete section text for the lto section 1737 names to write in darwin_file_end. */ 1738 obstack_init (<o_section_names_obstack); 1739 lto_section_names_offset = 0; 1740 } 1741 1742 /* Output an offset in a DWARF section on Darwin. On Darwin, DWARF section 1743 offsets are not represented using relocs in .o files; either the 1744 section never leaves the .o file, or the linker or other tool is 1745 responsible for parsing the DWARF and updating the offsets. */ 1746 1747 void 1748 darwin_asm_output_dwarf_offset (FILE *file, int size, const char * lab, 1749 section *base) 1750 { 1751 char sname[64]; 1752 int namelen; 1753 1754 gcc_assert (base->common.flags & SECTION_NAMED); 1755 gcc_assert (strncmp (base->named.name, "__DWARF,", 8) == 0); 1756 gcc_assert (strchr (base->named.name + 8, ',')); 1757 1758 namelen = strchr (base->named.name + 8, ',') - (base->named.name + 8); 1759 sprintf (sname, "*Lsection%.*s", namelen, base->named.name + 8); 1760 darwin_asm_output_dwarf_delta (file, size, lab, sname); 1761 } 1762 1763 void 1764 darwin_file_end (void) 1765 { 1766 const char *lto_section_names; 1767 1768 machopic_finish (asm_out_file); 1769 if (strcmp (lang_hooks.name, "GNU C++") == 0) 1770 { 1771 switch_to_section (darwin_sections[constructor_section]); 1772 switch_to_section (darwin_sections[destructor_section]); 1773 ASM_OUTPUT_ALIGN (asm_out_file, 1); 1774 } 1775 1776 /* If there was LTO assembler output, append it to asm_out_file. */ 1777 if (lto_asm_out_name) 1778 { 1779 int n; 1780 char *buf, *lto_asm_txt; 1781 1782 /* Shouldn't be here if we failed to switch back. */ 1783 gcc_assert (! saved_asm_out_file); 1784 1785 lto_asm_out_file = fopen (lto_asm_out_name, "r"); 1786 if (lto_asm_out_file == NULL) 1787 fatal_error ("failed to open temporary file %s with LTO output", 1788 lto_asm_out_name); 1789 fseek (lto_asm_out_file, 0, SEEK_END); 1790 n = ftell (lto_asm_out_file); 1791 if (n > 0) 1792 { 1793 fseek (lto_asm_out_file, 0, SEEK_SET); 1794 lto_asm_txt = buf = (char *) xmalloc (n + 1); 1795 while (fgets (lto_asm_txt, n, lto_asm_out_file)) 1796 fputs (lto_asm_txt, asm_out_file); 1797 } 1798 1799 /* Remove the temporary file. */ 1800 fclose (lto_asm_out_file); 1801 unlink_if_ordinary (lto_asm_out_name); 1802 free (lto_asm_out_name); 1803 } 1804 1805 /* Finish the LTO section names obstack. Don't output anything if 1806 there are no recorded section names. */ 1807 obstack_1grow (<o_section_names_obstack, '\0'); 1808 lto_section_names = XOBFINISH (<o_section_names_obstack, const char *); 1809 if (strlen (lto_section_names) > 0) 1810 { 1811 fprintf (asm_out_file, 1812 "\t.section %s,%s,regular,debug\n", 1813 LTO_SEGMENT_NAME, LTO_NAMES_SECTION); 1814 fprintf (asm_out_file, 1815 "\t# Section names in %s are offsets into this table\n", 1816 LTO_SEGMENT_NAME); 1817 fprintf (asm_out_file, "%s\n", lto_section_names); 1818 } 1819 obstack_free (<o_section_names_obstack, NULL); 1820 1821 fprintf (asm_out_file, "\t.subsections_via_symbols\n"); 1822 } 1823 1824 /* TODO: Add a language hook for identifying if a decl is a vtable. */ 1825 #define DARWIN_VTABLE_P(DECL) 0 1826 1827 /* Cross-module name binding. Darwin does not support overriding 1828 functions at dynamic-link time, except for vtables in kexts. */ 1829 1830 bool 1831 darwin_binds_local_p (const_tree decl) 1832 { 1833 return default_binds_local_p_1 (decl, 1834 TARGET_KEXTABI && DARWIN_VTABLE_P (decl)); 1835 } 1836 1837 #if 0 1838 /* See TARGET_ASM_OUTPUT_ANCHOR for why we can't do this yet. */ 1839 /* The Darwin's implementation of TARGET_ASM_OUTPUT_ANCHOR. Define the 1840 anchor relative to ".", the current section position. We cannot use 1841 the default one because ASM_OUTPUT_DEF is wrong for Darwin. */ 1842 1843 void 1844 darwin_asm_output_anchor (rtx symbol) 1845 { 1846 fprintf (asm_out_file, "\t.set\t"); 1847 assemble_name (asm_out_file, XSTR (symbol, 0)); 1848 fprintf (asm_out_file, ", . + " HOST_WIDE_INT_PRINT_DEC "\n", 1849 SYMBOL_REF_BLOCK_OFFSET (symbol)); 1850 } 1851 #endif 1852 1853 /* Set the darwin specific attributes on TYPE. */ 1854 void 1855 darwin_set_default_type_attributes (tree type) 1856 { 1857 if (darwin_ms_struct 1858 && TREE_CODE (type) == RECORD_TYPE) 1859 TYPE_ATTRIBUTES (type) = tree_cons (get_identifier ("ms_struct"), 1860 NULL_TREE, 1861 TYPE_ATTRIBUTES (type)); 1862 } 1863 1864 /* True, iff we're generating code for loadable kernel extensions. */ 1865 1866 bool 1867 darwin_kextabi_p (void) { 1868 return flag_apple_kext; 1869 } 1870 1871 void 1872 darwin_override_options (void) 1873 { 1874 /* Don't emit DWARF3/4 unless specifically selected. This is a 1875 workaround for tool bugs. */ 1876 if (dwarf_strict < 0) 1877 dwarf_strict = 1; 1878 1879 /* Disable -freorder-blocks-and-partition for darwin_emit_unwind_label. */ 1880 if (flag_reorder_blocks_and_partition 1881 && (targetm.asm_out.unwind_label == darwin_emit_unwind_label)) 1882 { 1883 inform (input_location, 1884 "-freorder-blocks-and-partition does not work with exceptions " 1885 "on this architecture"); 1886 flag_reorder_blocks_and_partition = 0; 1887 flag_reorder_blocks = 1; 1888 } 1889 1890 if (flag_mkernel || flag_apple_kext) 1891 { 1892 /* -mkernel implies -fapple-kext for C++ */ 1893 if (strcmp (lang_hooks.name, "GNU C++") == 0) 1894 flag_apple_kext = 1; 1895 1896 flag_no_common = 1; 1897 1898 /* No EH in kexts. */ 1899 flag_exceptions = 0; 1900 /* No -fnon-call-exceptions data in kexts. */ 1901 flag_non_call_exceptions = 0; 1902 } 1903 if (flag_var_tracking 1904 && strverscmp (darwin_macosx_version_min, "10.5") >= 0 1905 && debug_info_level >= DINFO_LEVEL_NORMAL 1906 && debug_hooks->var_location != do_nothing_debug_hooks.var_location) 1907 flag_var_tracking_uninit = 1; 1908 } 1909 1910 /* Add $LDBL128 suffix to long double builtins. */ 1911 1912 static void 1913 darwin_patch_builtin (int fncode) 1914 { 1915 tree fn = built_in_decls[fncode]; 1916 tree sym; 1917 char *newname; 1918 1919 if (!fn) 1920 return; 1921 1922 sym = DECL_ASSEMBLER_NAME (fn); 1923 newname = ACONCAT (("_", IDENTIFIER_POINTER (sym), "$LDBL128", NULL)); 1924 1925 set_user_assembler_name (fn, newname); 1926 1927 fn = implicit_built_in_decls[fncode]; 1928 if (fn) 1929 set_user_assembler_name (fn, newname); 1930 } 1931 1932 void 1933 darwin_patch_builtins (void) 1934 { 1935 if (LONG_DOUBLE_TYPE_SIZE != 128) 1936 return; 1937 1938 #define PATCH_BUILTIN(fncode) darwin_patch_builtin (fncode); 1939 #define PATCH_BUILTIN_NO64(fncode) \ 1940 if (!TARGET_64BIT) \ 1941 darwin_patch_builtin (fncode); 1942 #define PATCH_BUILTIN_VARIADIC(fncode) \ 1943 if (!TARGET_64BIT \ 1944 && (strverscmp (darwin_macosx_version_min, "10.3.9") >= 0)) \ 1945 darwin_patch_builtin (fncode); 1946 #include "darwin-ppc-ldouble-patch.def" 1947 #undef PATCH_BUILTIN 1948 #undef PATCH_BUILTIN_NO64 1949 #undef PATCH_BUILTIN_VARIADIC 1950 } 1951 1952 1953 #include "gt-darwin.h" 1954