118334Speter/* Handle #pragma, system V.4 style. Supports #pragma weak and #pragma pack. 2169689Skan Copyright (C) 1992, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 3169689Skan 2006 Free Software Foundation, Inc. 418334Speter 590075SobrienThis file is part of GCC. 618334Speter 790075SobrienGCC is free software; you can redistribute it and/or modify it under 890075Sobrienthe terms of the GNU General Public License as published by the Free 990075SobrienSoftware Foundation; either version 2, or (at your option) any later 1090075Sobrienversion. 1118334Speter 1290075SobrienGCC is distributed in the hope that it will be useful, but WITHOUT ANY 1390075SobrienWARRANTY; without even the implied warranty of MERCHANTABILITY or 1490075SobrienFITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 1590075Sobrienfor more details. 1618334Speter 1718334SpeterYou should have received a copy of the GNU General Public License 1890075Sobrienalong with GCC; see the file COPYING. If not, write to the Free 19169689SkanSoftware Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 20169689Skan02110-1301, USA. */ 2118334Speter 2218334Speter#include "config.h" 2350397Sobrien#include "system.h" 24132718Skan#include "coretypes.h" 25132718Skan#include "tm.h" 2650397Sobrien#include "rtl.h" 2718334Speter#include "tree.h" 2818334Speter#include "function.h" 2990075Sobrien#include "cpplib.h" 3018334Speter#include "c-pragma.h" 3150397Sobrien#include "flags.h" 3250397Sobrien#include "toplev.h" 3390075Sobrien#include "ggc.h" 3496263Sobrien#include "c-common.h" 3590075Sobrien#include "output.h" 3690075Sobrien#include "tm_p.h" 37169689Skan#include "vec.h" 38169689Skan#include "target.h" 39169689Skan#include "diagnostic.h" 40169689Skan#include "opts.h" 4118334Speter 42169689Skan#define GCC_BAD(gmsgid) \ 43169689Skan do { warning (OPT_Wpragmas, gmsgid); return; } while (0) 44169689Skan#define GCC_BAD2(gmsgid, arg) \ 45169689Skan do { warning (OPT_Wpragmas, gmsgid, arg); return; } while (0) 4618334Speter 47117395Skantypedef struct align_stack GTY(()) 4852284Sobrien{ 49169689Skan int alignment; 50169689Skan tree id; 5152284Sobrien struct align_stack * prev; 5252284Sobrien} align_stack; 5318334Speter 54117395Skanstatic GTY(()) struct align_stack * alignment_stack; 5552284Sobrien 56117395Skan#ifdef HANDLE_PRAGMA_PACK 57132718Skanstatic void handle_pragma_pack (cpp_reader *); 58117395Skan 59117395Skan#ifdef HANDLE_PRAGMA_PACK_PUSH_POP 6090075Sobrien/* If we have a "global" #pragma pack(<n>) in effect when the first 61169689Skan #pragma pack(push,<n>) is encountered, this stores the value of 62169689Skan maximum_field_alignment in effect. When the final pop_alignment() 6390075Sobrien happens, we restore the value to this, not to a value of 0 for 6490075Sobrien maximum_field_alignment. Value is in bits. */ 6596263Sobrienstatic int default_alignment; 66169689Skan#define SET_GLOBAL_ALIGNMENT(ALIGN) (maximum_field_alignment = *(alignment_stack == NULL \ 67169689Skan ? &default_alignment \ 68169689Skan : &alignment_stack->alignment) = (ALIGN)) 6952284Sobrien 70132718Skanstatic void push_alignment (int, tree); 71132718Skanstatic void pop_alignment (tree); 7290075Sobrien 7352284Sobrien/* Push an alignment value onto the stack. */ 7490075Sobrienstatic void 75132718Skanpush_alignment (int alignment, tree id) 7652284Sobrien{ 77169689Skan align_stack * entry; 7852284Sobrien 79169689Skan entry = GGC_NEW (align_stack); 8052284Sobrien 81169689Skan entry->alignment = alignment; 82169689Skan entry->id = id; 83169689Skan entry->prev = alignment_stack; 8452284Sobrien 85169689Skan /* The current value of maximum_field_alignment is not necessarily 86169689Skan 0 since there may be a #pragma pack(<n>) in effect; remember it 87169689Skan so that we can restore it after the final #pragma pop(). */ 88169689Skan if (alignment_stack == NULL) 89169689Skan default_alignment = maximum_field_alignment; 90169689Skan 91169689Skan alignment_stack = entry; 92169689Skan 93169689Skan maximum_field_alignment = alignment; 9452284Sobrien} 9552284Sobrien 9652284Sobrien/* Undo a push of an alignment onto the stack. */ 9790075Sobrienstatic void 98132718Skanpop_alignment (tree id) 9952284Sobrien{ 10052284Sobrien align_stack * entry; 101169689Skan 10252284Sobrien if (alignment_stack == NULL) 103169689Skan GCC_BAD ("#pragma pack (pop) encountered without matching #pragma pack (push)"); 10452284Sobrien 10552284Sobrien /* If we got an identifier, strip away everything above the target 10652284Sobrien entry so that the next step will restore the state just below it. */ 10752284Sobrien if (id) 10852284Sobrien { 10952284Sobrien for (entry = alignment_stack; entry; entry = entry->prev) 11052284Sobrien if (entry->id == id) 11152284Sobrien { 11252284Sobrien alignment_stack = entry; 11352284Sobrien break; 11452284Sobrien } 11552284Sobrien if (entry == NULL) 116169689Skan warning (OPT_Wpragmas, "\ 117169689Skan#pragma pack(pop, %s) encountered without matching #pragma pack(push, %s)" 11852284Sobrien , IDENTIFIER_POINTER (id), IDENTIFIER_POINTER (id)); 11952284Sobrien } 12052284Sobrien 121169689Skan entry = alignment_stack->prev; 12252284Sobrien 123169689Skan maximum_field_alignment = entry ? entry->alignment : default_alignment; 12452284Sobrien 125169689Skan alignment_stack = entry; 12652284Sobrien} 12790075Sobrien#else /* not HANDLE_PRAGMA_PACK_PUSH_POP */ 12890075Sobrien#define SET_GLOBAL_ALIGNMENT(ALIGN) (maximum_field_alignment = (ALIGN)) 12990075Sobrien#define push_alignment(ID, N) \ 130169689Skan GCC_BAD ("#pragma pack(push[, id], <n>) is not supported on this target") 13190075Sobrien#define pop_alignment(ID) \ 132169689Skan GCC_BAD ("#pragma pack(pop[, id], <n>) is not supported on this target") 13352284Sobrien#endif /* HANDLE_PRAGMA_PACK_PUSH_POP */ 13452284Sobrien 13590075Sobrien/* #pragma pack () 13690075Sobrien #pragma pack (N) 137169689Skan 138169689Skan #pragma pack (push) 13990075Sobrien #pragma pack (push, N) 140169689Skan #pragma pack (push, ID) 14190075Sobrien #pragma pack (push, ID, N) 14290075Sobrien #pragma pack (pop) 14390075Sobrien #pragma pack (pop, ID) */ 14490075Sobrienstatic void 145169689Skanhandle_pragma_pack (cpp_reader * ARG_UNUSED (dummy)) 14618334Speter{ 14790075Sobrien tree x, id = 0; 14890075Sobrien int align = -1; 14990075Sobrien enum cpp_ttype token; 15090075Sobrien enum { set, push, pop } action; 15118334Speter 152169689Skan if (pragma_lex (&x) != CPP_OPEN_PAREN) 153169689Skan GCC_BAD ("missing %<(%> after %<#pragma pack%> - ignored"); 15490075Sobrien 155169689Skan token = pragma_lex (&x); 15690075Sobrien if (token == CPP_CLOSE_PAREN) 15718334Speter { 15890075Sobrien action = set; 159169689Skan align = initial_max_fld_align; 16018334Speter } 16190075Sobrien else if (token == CPP_NUMBER) 16252284Sobrien { 163169689Skan if (TREE_CODE (x) != INTEGER_CST) 164169689Skan GCC_BAD ("invalid constant in %<#pragma pack%> - ignored"); 16590075Sobrien align = TREE_INT_CST_LOW (x); 16690075Sobrien action = set; 167169689Skan if (pragma_lex (&x) != CPP_CLOSE_PAREN) 168169689Skan GCC_BAD ("malformed %<#pragma pack%> - ignored"); 16952284Sobrien } 17090075Sobrien else if (token == CPP_NAME) 17118334Speter { 172169689Skan#define GCC_BAD_ACTION do { if (action != pop) \ 173169689Skan GCC_BAD ("malformed %<#pragma pack(push[, id][, <n>])%> - ignored"); \ 17490075Sobrien else \ 175169689Skan GCC_BAD ("malformed %<#pragma pack(pop[, id])%> - ignored"); \ 17690075Sobrien } while (0) 17718334Speter 17890075Sobrien const char *op = IDENTIFIER_POINTER (x); 17990075Sobrien if (!strcmp (op, "push")) 18090075Sobrien action = push; 18190075Sobrien else if (!strcmp (op, "pop")) 18290075Sobrien action = pop; 18352284Sobrien else 184169689Skan GCC_BAD2 ("unknown action %qs for %<#pragma pack%> - ignored", op); 18518334Speter 186169689Skan while ((token = pragma_lex (&x)) == CPP_COMMA) 18752284Sobrien { 188169689Skan token = pragma_lex (&x); 189169689Skan if (token == CPP_NAME && id == 0) 19052284Sobrien { 19190075Sobrien id = x; 19252284Sobrien } 193169689Skan else if (token == CPP_NUMBER && action == push && align == -1) 19490075Sobrien { 195169689Skan if (TREE_CODE (x) != INTEGER_CST) 196169689Skan GCC_BAD ("invalid constant in %<#pragma pack%> - ignored"); 197169689Skan align = TREE_INT_CST_LOW (x); 198169689Skan if (align == -1) 199169689Skan action = set; 20090075Sobrien } 201169689Skan else 202169689Skan GCC_BAD_ACTION; 20318334Speter } 20418334Speter 20590075Sobrien if (token != CPP_CLOSE_PAREN) 20690075Sobrien GCC_BAD_ACTION; 20790075Sobrien#undef GCC_BAD_ACTION 20890075Sobrien } 20990075Sobrien else 210169689Skan GCC_BAD ("malformed %<#pragma pack%> - ignored"); 21152284Sobrien 212169689Skan if (pragma_lex (&x) != CPP_EOF) 213169689Skan warning (OPT_Wpragmas, "junk at end of %<#pragma pack%>"); 21452284Sobrien 215169689Skan if (flag_pack_struct) 216169689Skan GCC_BAD ("#pragma pack has no effect with -fpack-struct - ignored"); 217169689Skan 21890075Sobrien if (action != pop) 21990075Sobrien switch (align) 22090075Sobrien { 22190075Sobrien case 0: 22290075Sobrien case 1: 22390075Sobrien case 2: 22490075Sobrien case 4: 22590075Sobrien case 8: 22690075Sobrien case 16: 22790075Sobrien align *= BITS_PER_UNIT; 22890075Sobrien break; 229169689Skan case -1: 230169689Skan if (action == push) 231169689Skan { 232169689Skan align = maximum_field_alignment; 233169689Skan break; 234169689Skan } 23590075Sobrien default: 23690075Sobrien GCC_BAD2 ("alignment must be a small power of two, not %d", align); 23790075Sobrien } 23818334Speter 23990075Sobrien switch (action) 24090075Sobrien { 24190075Sobrien case set: SET_GLOBAL_ALIGNMENT (align); break; 24290075Sobrien case push: push_alignment (align, id); break; 243169689Skan case pop: pop_alignment (id); break; 24490075Sobrien } 24590075Sobrien} 24690075Sobrien#endif /* HANDLE_PRAGMA_PACK */ 24718334Speter 248117395Skanstatic GTY(()) tree pending_weaks; 249117395Skan 25090075Sobrien#ifdef HANDLE_PRAGMA_WEAK 251132718Skanstatic void apply_pragma_weak (tree, tree); 252132718Skanstatic void handle_pragma_weak (cpp_reader *); 25352284Sobrien 25496263Sobrienstatic void 255132718Skanapply_pragma_weak (tree decl, tree value) 25696263Sobrien{ 25796263Sobrien if (value) 258102780Skan { 259102780Skan value = build_string (IDENTIFIER_LENGTH (value), 260102780Skan IDENTIFIER_POINTER (value)); 261102780Skan decl_attributes (&decl, build_tree_list (get_identifier ("alias"), 262102780Skan build_tree_list (NULL, value)), 263102780Skan 0); 264102780Skan } 265102780Skan 26696263Sobrien if (SUPPORTS_WEAK && DECL_EXTERNAL (decl) && TREE_USED (decl) 267132718Skan && !DECL_WEAK (decl) /* Don't complain about a redundant #pragma. */ 26896263Sobrien && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl))) 269169689Skan warning (OPT_Wpragmas, "applying #pragma weak %q+D after first use " 270169689Skan "results in unspecified behavior", decl); 27196263Sobrien 27296263Sobrien declare_weak (decl); 27396263Sobrien} 27496263Sobrien 27596263Sobrienvoid 276132718Skanmaybe_apply_pragma_weak (tree decl) 27796263Sobrien{ 27896263Sobrien tree *p, t, id; 27996263Sobrien 280119256Skan /* Avoid asking for DECL_ASSEMBLER_NAME when it's not needed. */ 281119256Skan 282119256Skan /* No weak symbols pending, take the short-cut. */ 283119256Skan if (!pending_weaks) 28496263Sobrien return; 285119256Skan /* If it's not visible outside this file, it doesn't matter whether 286119256Skan it's weak. */ 287119256Skan if (!DECL_EXTERNAL (decl) && !TREE_PUBLIC (decl)) 288119256Skan return; 289119256Skan /* If it's not a function or a variable, it can't be weak. 290119256Skan FIXME: what kinds of things are visible outside this file but 291169689Skan aren't functions or variables? Should this be an assert instead? */ 292119256Skan if (TREE_CODE (decl) != FUNCTION_DECL && TREE_CODE (decl) != VAR_DECL) 293119256Skan return; 29496263Sobrien 295119256Skan id = DECL_ASSEMBLER_NAME (decl); 296119256Skan 29796263Sobrien for (p = &pending_weaks; (t = *p) ; p = &TREE_CHAIN (t)) 29896263Sobrien if (id == TREE_PURPOSE (t)) 29996263Sobrien { 30096263Sobrien apply_pragma_weak (decl, TREE_VALUE (t)); 30196263Sobrien *p = TREE_CHAIN (t); 30296263Sobrien break; 30396263Sobrien } 30496263Sobrien} 30596263Sobrien 306169689Skan/* Process all "#pragma weak A = B" directives where we have not seen 307169689Skan a decl for A. */ 308169689Skanvoid 309169689Skanmaybe_apply_pending_pragma_weaks (void) 310169689Skan{ 311169689Skan tree *p, t, alias_id, id, decl, *next; 312169689Skan 313169689Skan for (p = &pending_weaks; (t = *p) ; p = next) 314169689Skan { 315169689Skan next = &TREE_CHAIN (t); 316169689Skan alias_id = TREE_PURPOSE (t); 317169689Skan id = TREE_VALUE (t); 318169689Skan 319169689Skan if (TREE_VALUE (t) == NULL) 320169689Skan continue; 321169689Skan 322169689Skan decl = build_decl (FUNCTION_DECL, alias_id, default_function_type); 323169689Skan 324169689Skan DECL_ARTIFICIAL (decl) = 1; 325169689Skan TREE_PUBLIC (decl) = 1; 326169689Skan DECL_EXTERNAL (decl) = 1; 327169689Skan DECL_WEAK (decl) = 1; 328169689Skan 329169689Skan assemble_alias (decl, id); 330169689Skan } 331169689Skan} 332169689Skan 33390075Sobrien/* #pragma weak name [= value] */ 33490075Sobrienstatic void 335169689Skanhandle_pragma_weak (cpp_reader * ARG_UNUSED (dummy)) 33690075Sobrien{ 33796263Sobrien tree name, value, x, decl; 33890075Sobrien enum cpp_ttype t; 33952284Sobrien 34090075Sobrien value = 0; 34152284Sobrien 342169689Skan if (pragma_lex (&name) != CPP_NAME) 34390075Sobrien GCC_BAD ("malformed #pragma weak, ignored"); 344169689Skan t = pragma_lex (&x); 34590075Sobrien if (t == CPP_EQ) 34690075Sobrien { 347169689Skan if (pragma_lex (&value) != CPP_NAME) 34890075Sobrien GCC_BAD ("malformed #pragma weak, ignored"); 349169689Skan t = pragma_lex (&x); 35090075Sobrien } 35190075Sobrien if (t != CPP_EOF) 352169689Skan warning (OPT_Wpragmas, "junk at end of %<#pragma weak%>"); 35352284Sobrien 35496263Sobrien decl = identifier_global_value (name); 355169689Skan if (decl && DECL_P (decl)) 356102780Skan { 357102780Skan apply_pragma_weak (decl, value); 358102780Skan if (value) 359102780Skan assemble_alias (decl, value); 360102780Skan } 36196263Sobrien else 36296263Sobrien pending_weaks = tree_cons (name, value, pending_weaks); 36390075Sobrien} 36496263Sobrien#else 36596263Sobrienvoid 366169689Skanmaybe_apply_pragma_weak (tree ARG_UNUSED (decl)) 36796263Sobrien{ 36896263Sobrien} 369169689Skan 370169689Skanvoid 371169689Skanmaybe_apply_pending_pragma_weaks (void) 372169689Skan{ 373169689Skan} 37496263Sobrien#endif /* HANDLE_PRAGMA_WEAK */ 37596263Sobrien 376169689Skan/* GCC supports two #pragma directives for renaming the external 377169689Skan symbol associated with a declaration (DECL_ASSEMBLER_NAME), for 378169689Skan compatibility with the Solaris and Tru64 system headers. GCC also 379169689Skan has its own notation for this, __asm__("name") annotations. 380169689Skan 381169689Skan Corner cases of these features and their interaction: 382169689Skan 383169689Skan 1) Both pragmas silently apply only to declarations with external 384169689Skan linkage (that is, TREE_PUBLIC || DECL_EXTERNAL). Asm labels 385169689Skan do not have this restriction. 386169689Skan 387169689Skan 2) In C++, both #pragmas silently apply only to extern "C" declarations. 388169689Skan Asm labels do not have this restriction. 389169689Skan 390169689Skan 3) If any of the three ways of changing DECL_ASSEMBLER_NAME is 391169689Skan applied to a decl whose DECL_ASSEMBLER_NAME is already set, and the 392169689Skan new name is different, a warning issues and the name does not change. 393169689Skan 394169689Skan 4) The "source name" for #pragma redefine_extname is the DECL_NAME, 395169689Skan *not* the DECL_ASSEMBLER_NAME. 396169689Skan 397169689Skan 5) If #pragma extern_prefix is in effect and a declaration occurs 398169689Skan with an __asm__ name, the #pragma extern_prefix is silently 399169689Skan ignored for that declaration. 400169689Skan 401169689Skan 6) If #pragma extern_prefix and #pragma redefine_extname apply to 402169689Skan the same declaration, whichever triggered first wins, and a warning 403169689Skan is issued. (We would like to have #pragma redefine_extname always 404169689Skan win, but it can appear either before or after the declaration, and 405169689Skan if it appears afterward, we have no way of knowing whether a modified 406169689Skan DECL_ASSEMBLER_NAME is due to #pragma extern_prefix.) */ 407169689Skan 408117395Skanstatic GTY(()) tree pending_redefine_extname; 409117395Skan 410132718Skanstatic void handle_pragma_redefine_extname (cpp_reader *); 41196263Sobrien 412169689Skan/* #pragma redefine_extname oldname newname */ 41396263Sobrienstatic void 414169689Skanhandle_pragma_redefine_extname (cpp_reader * ARG_UNUSED (dummy)) 41596263Sobrien{ 41696263Sobrien tree oldname, newname, decl, x; 41796263Sobrien enum cpp_ttype t; 41896263Sobrien 419169689Skan if (pragma_lex (&oldname) != CPP_NAME) 420169689Skan GCC_BAD ("malformed #pragma redefine_extname, ignored"); 421169689Skan if (pragma_lex (&newname) != CPP_NAME) 422169689Skan GCC_BAD ("malformed #pragma redefine_extname, ignored"); 423169689Skan t = pragma_lex (&x); 424169689Skan if (t != CPP_EOF) 425169689Skan warning (OPT_Wpragmas, "junk at end of %<#pragma redefine_extname%>"); 426169689Skan 427169689Skan if (!flag_mudflap && !targetm.handle_pragma_redefine_extname) 42896263Sobrien { 429169689Skan if (warn_unknown_pragmas > in_system_header) 430169689Skan warning (OPT_Wunknown_pragmas, 431169689Skan "#pragma redefine_extname not supported on this target"); 43296263Sobrien return; 43396263Sobrien } 43496263Sobrien 43596263Sobrien decl = identifier_global_value (oldname); 436169689Skan if (decl 437169689Skan && (TREE_PUBLIC (decl) || DECL_EXTERNAL (decl)) 438169689Skan && (TREE_CODE (decl) == FUNCTION_DECL 439169689Skan || TREE_CODE (decl) == VAR_DECL) 440169689Skan && has_c_linkage (decl)) 44196263Sobrien { 442169689Skan if (DECL_ASSEMBLER_NAME_SET_P (decl)) 443169689Skan { 444169689Skan const char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)); 445169689Skan name = targetm.strip_name_encoding (name); 446169689Skan 447169689Skan if (strcmp (name, IDENTIFIER_POINTER (newname))) 448169689Skan warning (OPT_Wpragmas, "#pragma redefine_extname ignored due to " 449169689Skan "conflict with previous rename"); 450169689Skan } 451169689Skan else 452169689Skan change_decl_assembler_name (decl, newname); 45396263Sobrien } 45496263Sobrien else 455169689Skan /* We have to add this to the rename list even if there's already 456169689Skan a global value that doesn't meet the above criteria, because in 457169689Skan C++ "struct foo {...};" puts "foo" in the current namespace but 458169689Skan does *not* conflict with a subsequent declaration of a function 459169689Skan or variable foo. See g++.dg/other/pragma-re-2.C. */ 460169689Skan add_to_renaming_pragma_list (oldname, newname); 46196263Sobrien} 46252284Sobrien 463169689Skan/* This is called from here and from ia64.c. */ 464117395Skanvoid 465132718Skanadd_to_renaming_pragma_list (tree oldname, tree newname) 466117395Skan{ 467169689Skan tree previous = purpose_member (oldname, pending_redefine_extname); 468169689Skan if (previous) 469169689Skan { 470169689Skan if (TREE_VALUE (previous) != newname) 471169689Skan warning (OPT_Wpragmas, "#pragma redefine_extname ignored due to " 472169689Skan "conflict with previous #pragma redefine_extname"); 473169689Skan return; 474169689Skan } 475169689Skan 476117395Skan pending_redefine_extname 477117395Skan = tree_cons (oldname, newname, pending_redefine_extname); 478117395Skan} 479117395Skan 480117395Skanstatic GTY(()) tree pragma_extern_prefix; 481117395Skan 48296263Sobrien/* #pragma extern_prefix "prefix" */ 48396263Sobrienstatic void 484169689Skanhandle_pragma_extern_prefix (cpp_reader * ARG_UNUSED (dummy)) 48596263Sobrien{ 48696263Sobrien tree prefix, x; 48796263Sobrien enum cpp_ttype t; 48896263Sobrien 489169689Skan if (pragma_lex (&prefix) != CPP_STRING) 490169689Skan GCC_BAD ("malformed #pragma extern_prefix, ignored"); 491169689Skan t = pragma_lex (&x); 49296263Sobrien if (t != CPP_EOF) 493169689Skan warning (OPT_Wpragmas, "junk at end of %<#pragma extern_prefix%>"); 49496263Sobrien 495169689Skan if (targetm.handle_pragma_extern_prefix) 496169689Skan /* Note that the length includes the null terminator. */ 497169689Skan pragma_extern_prefix = (TREE_STRING_LENGTH (prefix) > 1 ? prefix : NULL); 498169689Skan else if (warn_unknown_pragmas > in_system_header) 499169689Skan warning (OPT_Wunknown_pragmas, 500169689Skan "#pragma extern_prefix not supported on this target"); 50196263Sobrien} 50296263Sobrien 503132718Skan/* Hook from the front ends to apply the results of one of the preceding 50496263Sobrien pragmas that rename variables. */ 50596263Sobrien 50696263Sobrientree 507132718Skanmaybe_apply_renaming_pragma (tree decl, tree asmname) 50896263Sobrien{ 509169689Skan tree *p, t; 51096263Sobrien 511169689Skan /* The renaming pragmas are only applied to declarations with 512169689Skan external linkage. */ 513169689Skan if ((TREE_CODE (decl) != FUNCTION_DECL && TREE_CODE (decl) != VAR_DECL) 514169689Skan || (!TREE_PUBLIC (decl) && !DECL_EXTERNAL (decl)) 515169689Skan || !has_c_linkage (decl)) 51696263Sobrien return asmname; 51796263Sobrien 518169689Skan /* If the DECL_ASSEMBLER_NAME is already set, it does not change, 519169689Skan but we may warn about a rename that conflicts. */ 520169689Skan if (DECL_ASSEMBLER_NAME_SET_P (decl)) 52196263Sobrien { 522169689Skan const char *oldname = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)); 523169689Skan oldname = targetm.strip_name_encoding (oldname); 524169689Skan 525169689Skan if (asmname && strcmp (TREE_STRING_POINTER (asmname), oldname)) 526169689Skan warning (OPT_Wpragmas, "asm declaration ignored due to " 527169689Skan "conflict with previous rename"); 528169689Skan 529169689Skan /* Take any pending redefine_extname off the list. */ 530169689Skan for (p = &pending_redefine_extname; (t = *p); p = &TREE_CHAIN (t)) 531169689Skan if (DECL_NAME (decl) == TREE_PURPOSE (t)) 532169689Skan { 533169689Skan /* Only warn if there is a conflict. */ 534169689Skan if (strcmp (IDENTIFIER_POINTER (TREE_VALUE (t)), oldname)) 535169689Skan warning (OPT_Wpragmas, "#pragma redefine_extname ignored due to " 536169689Skan "conflict with previous rename"); 537169689Skan 538169689Skan *p = TREE_CHAIN (t); 539169689Skan break; 540169689Skan } 541169689Skan return 0; 54296263Sobrien } 54396263Sobrien 544169689Skan /* Find out if we have a pending #pragma redefine_extname. */ 545169689Skan for (p = &pending_redefine_extname; (t = *p); p = &TREE_CHAIN (t)) 546169689Skan if (DECL_NAME (decl) == TREE_PURPOSE (t)) 547169689Skan { 548169689Skan tree newname = TREE_VALUE (t); 549169689Skan *p = TREE_CHAIN (t); 55096263Sobrien 551169689Skan /* If we already have an asmname, #pragma redefine_extname is 552169689Skan ignored (with a warning if it conflicts). */ 553169689Skan if (asmname) 554169689Skan { 555169689Skan if (strcmp (TREE_STRING_POINTER (asmname), 556169689Skan IDENTIFIER_POINTER (newname)) != 0) 557169689Skan warning (OPT_Wpragmas, "#pragma redefine_extname ignored due to " 558169689Skan "conflict with __asm__ declaration"); 559169689Skan return asmname; 560169689Skan } 56196263Sobrien 562169689Skan /* Otherwise we use what we've got; #pragma extern_prefix is 563169689Skan silently ignored. */ 564169689Skan return build_string (IDENTIFIER_LENGTH (newname), 565169689Skan IDENTIFIER_POINTER (newname)); 566169689Skan } 56796263Sobrien 568169689Skan /* If we've got an asmname, #pragma extern_prefix is silently ignored. */ 569169689Skan if (asmname) 570169689Skan return asmname; 57196263Sobrien 572169689Skan /* If #pragma extern_prefix is in effect, apply it. */ 573169689Skan if (pragma_extern_prefix) 57496263Sobrien { 575169689Skan const char *prefix = TREE_STRING_POINTER (pragma_extern_prefix); 576169689Skan size_t plen = TREE_STRING_LENGTH (pragma_extern_prefix) - 1; 577169689Skan 578169689Skan const char *id = IDENTIFIER_POINTER (DECL_NAME (decl)); 579169689Skan size_t ilen = IDENTIFIER_LENGTH (DECL_NAME (decl)); 580169689Skan 581169689Skan char *newname = (char *) alloca (plen + ilen + 1); 582169689Skan 583169689Skan memcpy (newname, prefix, plen); 584169689Skan memcpy (newname + plen, id, ilen + 1); 585169689Skan 586169689Skan return build_string (plen + ilen, newname); 58796263Sobrien } 588169689Skan 589169689Skan /* Nada. */ 590169689Skan return 0; 591169689Skan} 592169689Skan 593169689Skan 594169689Skan#ifdef HANDLE_PRAGMA_VISIBILITY 595169689Skanstatic void handle_pragma_visibility (cpp_reader *); 596169689Skan 597169689Skantypedef enum symbol_visibility visibility; 598169689SkanDEF_VEC_I (visibility); 599169689SkanDEF_VEC_ALLOC_I (visibility, heap); 600169689Skanstatic VEC (visibility, heap) *visstack; 601169689Skan 602169689Skan/* Push the visibility indicated by STR onto the top of the #pragma 603169689Skan visibility stack. */ 604169689Skan 605169689Skanvoid 606169689Skanpush_visibility (const char *str) 607169689Skan{ 608169689Skan VEC_safe_push (visibility, heap, visstack, 609169689Skan default_visibility); 610169689Skan if (!strcmp (str, "default")) 611169689Skan default_visibility = VISIBILITY_DEFAULT; 612169689Skan else if (!strcmp (str, "internal")) 613169689Skan default_visibility = VISIBILITY_INTERNAL; 614169689Skan else if (!strcmp (str, "hidden")) 615169689Skan default_visibility = VISIBILITY_HIDDEN; 616169689Skan else if (!strcmp (str, "protected")) 617169689Skan default_visibility = VISIBILITY_PROTECTED; 618169689Skan else 619169689Skan GCC_BAD ("#pragma GCC visibility push() must specify default, internal, hidden or protected"); 620169689Skan visibility_options.inpragma = 1; 621169689Skan} 622169689Skan 623169689Skan/* Pop a level of the #pragma visibility stack. */ 624169689Skan 625169689Skanvoid 626169689Skanpop_visibility (void) 627169689Skan{ 628169689Skan default_visibility = VEC_pop (visibility, visstack); 629169689Skan visibility_options.inpragma 630169689Skan = VEC_length (visibility, visstack) != 0; 631169689Skan} 632169689Skan 633169689Skan/* Sets the default visibility for symbols to something other than that 634169689Skan specified on the command line. */ 635169689Skan 636169689Skanstatic void 637169689Skanhandle_pragma_visibility (cpp_reader *dummy ATTRIBUTE_UNUSED) 638169689Skan{ 639169689Skan /* Form is #pragma GCC visibility push(hidden)|pop */ 640169689Skan tree x; 641169689Skan enum cpp_ttype token; 642169689Skan enum { bad, push, pop } action = bad; 643169689Skan 644169689Skan token = pragma_lex (&x); 645169689Skan if (token == CPP_NAME) 646169689Skan { 647169689Skan const char *op = IDENTIFIER_POINTER (x); 648169689Skan if (!strcmp (op, "push")) 649169689Skan action = push; 650169689Skan else if (!strcmp (op, "pop")) 651169689Skan action = pop; 652169689Skan } 653169689Skan if (bad == action) 654169689Skan GCC_BAD ("#pragma GCC visibility must be followed by push or pop"); 655169689Skan else 656169689Skan { 657169689Skan if (pop == action) 658169689Skan { 659169689Skan if (!VEC_length (visibility, visstack)) 660169689Skan GCC_BAD ("no matching push for %<#pragma GCC visibility pop%>"); 661169689Skan else 662169689Skan pop_visibility (); 663169689Skan } 664169689Skan else 665169689Skan { 666169689Skan if (pragma_lex (&x) != CPP_OPEN_PAREN) 667169689Skan GCC_BAD ("missing %<(%> after %<#pragma GCC visibility push%> - ignored"); 668169689Skan token = pragma_lex (&x); 669169689Skan if (token != CPP_NAME) 670169689Skan GCC_BAD ("malformed #pragma GCC visibility push"); 671169689Skan else 672169689Skan push_visibility (IDENTIFIER_POINTER (x)); 673169689Skan if (pragma_lex (&x) != CPP_CLOSE_PAREN) 674169689Skan GCC_BAD ("missing %<(%> after %<#pragma GCC visibility push%> - ignored"); 675169689Skan } 676169689Skan } 677169689Skan if (pragma_lex (&x) != CPP_EOF) 678169689Skan warning (OPT_Wpragmas, "junk at end of %<#pragma GCC visibility%>"); 679169689Skan} 680169689Skan 68196263Sobrien#endif 68296263Sobrien 683169689Skanstatic void 684169689Skanhandle_pragma_diagnostic(cpp_reader *ARG_UNUSED(dummy)) 685169689Skan{ 686169689Skan const char *kind_string, *option_string; 687169689Skan unsigned int option_index; 688169689Skan enum cpp_ttype token; 689169689Skan diagnostic_t kind; 690169689Skan tree x; 691169689Skan 692169689Skan if (cfun) 693169689Skan { 694169689Skan error ("#pragma GCC diagnostic not allowed inside functions"); 695169689Skan return; 696169689Skan } 697169689Skan 698169689Skan token = pragma_lex (&x); 699169689Skan if (token != CPP_NAME) 700169689Skan GCC_BAD ("missing [error|warning|ignored] after %<#pragma GCC diagnostic%>"); 701169689Skan kind_string = IDENTIFIER_POINTER (x); 702169689Skan if (strcmp (kind_string, "error") == 0) 703169689Skan kind = DK_ERROR; 704169689Skan else if (strcmp (kind_string, "warning") == 0) 705169689Skan kind = DK_WARNING; 706169689Skan else if (strcmp (kind_string, "ignored") == 0) 707169689Skan kind = DK_IGNORED; 708169689Skan else 709169689Skan GCC_BAD ("expected [error|warning|ignored] after %<#pragma GCC diagnostic%>"); 710169689Skan 711169689Skan token = pragma_lex (&x); 712169689Skan if (token != CPP_STRING) 713169689Skan GCC_BAD ("missing option after %<#pragma GCC diagnostic%> kind"); 714169689Skan option_string = TREE_STRING_POINTER (x); 715169689Skan for (option_index = 0; option_index < cl_options_count; option_index++) 716169689Skan if (strcmp (cl_options[option_index].opt_text, option_string) == 0) 717169689Skan { 718169689Skan /* This overrides -Werror, for example. */ 719169689Skan diagnostic_classify_diagnostic (global_dc, option_index, kind); 720169689Skan /* This makes sure the option is enabled, like -Wfoo would do. */ 721169689Skan if (cl_options[option_index].var_type == CLVC_BOOLEAN 722169689Skan && cl_options[option_index].flag_var 723169689Skan && kind != DK_IGNORED) 724169689Skan *(int *) cl_options[option_index].flag_var = 1; 725169689Skan return; 726169689Skan } 727169689Skan GCC_BAD ("unknown option after %<#pragma GCC diagnostic%> kind"); 72896263Sobrien} 72996263Sobrien 730169689Skan/* A vector of registered pragma callbacks. */ 731169689Skan 732169689SkanDEF_VEC_O (pragma_handler); 733169689SkanDEF_VEC_ALLOC_O (pragma_handler, heap); 734169689Skan 735169689Skanstatic VEC(pragma_handler, heap) *registered_pragmas; 736169689Skan 737169689Skan/* Front-end wrappers for pragma registration to avoid dragging 738132718Skan cpplib.h in almost everywhere. */ 739169689Skan 740169689Skanstatic void 741169689Skanc_register_pragma_1 (const char *space, const char *name, 742169689Skan pragma_handler handler, bool allow_expansion) 743169689Skan{ 744169689Skan unsigned id; 745169689Skan 746169689Skan VEC_safe_push (pragma_handler, heap, registered_pragmas, &handler); 747169689Skan id = VEC_length (pragma_handler, registered_pragmas); 748169689Skan id += PRAGMA_FIRST_EXTERNAL - 1; 749169689Skan 750169689Skan /* The C++ front end allocates 6 bits in cp_token; the C front end 751169689Skan allocates 7 bits in c_token. At present this is sufficient. */ 752169689Skan gcc_assert (id < 64); 753169689Skan 754169689Skan cpp_register_deferred_pragma (parse_in, space, name, id, 755169689Skan allow_expansion, false); 756169689Skan} 757169689Skan 75890075Sobrienvoid 759169689Skanc_register_pragma (const char *space, const char *name, pragma_handler handler) 76090075Sobrien{ 761169689Skan c_register_pragma_1 (space, name, handler, false); 762132718Skan} 763132718Skan 764169689Skanvoid 765169689Skanc_register_pragma_with_expansion (const char *space, const char *name, 766169689Skan pragma_handler handler) 767169689Skan{ 768169689Skan c_register_pragma_1 (space, name, handler, true); 769169689Skan} 770169689Skan 771169689Skanvoid 772169689Skanc_invoke_pragma_handler (unsigned int id) 773169689Skan{ 774169689Skan pragma_handler handler; 775169689Skan 776169689Skan id -= PRAGMA_FIRST_EXTERNAL; 777169689Skan handler = *VEC_index (pragma_handler, registered_pragmas, id); 778169689Skan 779169689Skan handler (parse_in); 780169689Skan} 781169689Skan 782132718Skan/* Set up front-end pragmas. */ 783132718Skanvoid 784132718Skaninit_pragma (void) 785132718Skan{ 786169689Skan if (flag_openmp && !flag_preprocess_only) 787169689Skan { 788169689Skan struct omp_pragma_def { const char *name; unsigned int id; }; 789169689Skan static const struct omp_pragma_def omp_pragmas[] = { 790169689Skan { "atomic", PRAGMA_OMP_ATOMIC }, 791169689Skan { "barrier", PRAGMA_OMP_BARRIER }, 792169689Skan { "critical", PRAGMA_OMP_CRITICAL }, 793169689Skan { "flush", PRAGMA_OMP_FLUSH }, 794169689Skan { "for", PRAGMA_OMP_FOR }, 795169689Skan { "master", PRAGMA_OMP_MASTER }, 796169689Skan { "ordered", PRAGMA_OMP_ORDERED }, 797169689Skan { "parallel", PRAGMA_OMP_PARALLEL }, 798169689Skan { "section", PRAGMA_OMP_SECTION }, 799169689Skan { "sections", PRAGMA_OMP_SECTIONS }, 800169689Skan { "single", PRAGMA_OMP_SINGLE }, 801169689Skan { "threadprivate", PRAGMA_OMP_THREADPRIVATE } 802169689Skan }; 803169689Skan 804169689Skan const int n_omp_pragmas = sizeof (omp_pragmas) / sizeof (*omp_pragmas); 805169689Skan int i; 806169689Skan 807169689Skan for (i = 0; i < n_omp_pragmas; ++i) 808169689Skan cpp_register_deferred_pragma (parse_in, "omp", omp_pragmas[i].name, 809169689Skan omp_pragmas[i].id, true, true); 810169689Skan } 811169689Skan 812169689Skan cpp_register_deferred_pragma (parse_in, "GCC", "pch_preprocess", 813169689Skan PRAGMA_GCC_PCH_PREPROCESS, false, false); 814169689Skan 81590075Sobrien#ifdef HANDLE_PRAGMA_PACK 816169689Skan#ifdef HANDLE_PRAGMA_PACK_WITH_EXPANSION 817169689Skan c_register_pragma_with_expansion (0, "pack", handle_pragma_pack); 818169689Skan#else 819132718Skan c_register_pragma (0, "pack", handle_pragma_pack); 82090075Sobrien#endif 821169689Skan#endif 82290075Sobrien#ifdef HANDLE_PRAGMA_WEAK 823132718Skan c_register_pragma (0, "weak", handle_pragma_weak); 82490075Sobrien#endif 825169689Skan#ifdef HANDLE_PRAGMA_VISIBILITY 826169689Skan c_register_pragma ("GCC", "visibility", handle_pragma_visibility); 82796263Sobrien#endif 828169689Skan 829169689Skan c_register_pragma ("GCC", "diagnostic", handle_pragma_diagnostic); 830169689Skan 831169689Skan c_register_pragma_with_expansion (0, "redefine_extname", handle_pragma_redefine_extname); 832132718Skan c_register_pragma (0, "extern_prefix", handle_pragma_extern_prefix); 83396263Sobrien 83490075Sobrien#ifdef REGISTER_TARGET_PRAGMAS 835132718Skan REGISTER_TARGET_PRAGMAS (); 83690075Sobrien#endif 837117395Skan} 83818334Speter 839117395Skan#include "gt-c-pragma.h" 840