void solaris_elf_asm_comdat_section (const char *name, unsigned int flags, tree decl) { const char *signature; char *section; comdat_entry entry, **slot; if (TREE_CODE (decl) == IDENTIFIER_NODE) signature = IDENTIFIER_POINTER (decl); else signature = IDENTIFIER_POINTER (DECL_COMDAT_GROUP (decl)); /* Sun as requires group sections to be fragmented, i.e. to have names of the form <section>%<fragment>. Strictly speaking this is only necessary to support cc -xF, but is enforced globally in violation of the ELF gABI. We keep the section names generated by GCC (generally of the form .text.<signature>) and append %<signature> to pacify as, despite the redundancy. */ section = concat (name, "%", signature, NULL); /* Clear SECTION_LINKONCE flag so targetm.asm_out.named_section only emits this as a regular section. Emit section before .group directive since Sun as treats undeclared sections as @progbits, which conflicts with .bss* sections which are @nobits. */ targetm.asm_out.named_section (section, flags & ~SECTION_LINKONCE, decl); /* Sun as separates declaration of a group section and of the group itself, using the .group directive and the #comdat flag. */ fprintf (asm_out_file, "\t.group\t%s," SECTION_NAME_FORMAT ",#comdat\n", signature, section); /* Unlike GNU as, group signature symbols need to be defined explicitly for Sun as. With a few exceptions, this is already the case. To identify the missing ones without changing the affected frontents, remember the signature symbols and emit those not marked TREE_SYMBOL_REFERENCED in solaris_file_end. */ if (!solaris_comdat_htab.is_created ()) solaris_comdat_htab.create (37); entry.sig = signature; slot = solaris_comdat_htab.find_slot (&entry, INSERT); if (*slot == NULL) { *slot = XCNEW (comdat_entry); /* Remember fragmented section name. */ (*slot)->name = section; /* Emit as regular section, .group declaration has already been done. */ (*slot)->flags = flags & ~SECTION_LINKONCE; (*slot)->decl = decl; (*slot)->sig = signature; } }
void lto_streamer_init (void) { /* Check that all the TS_* handled by the reader and writer routines match exactly the structures defined in treestruct.def. When a new TS_* astructure is added, the streamer should be updated to handle it. */ streamer_check_handled_ts_structures (); #ifdef LTO_STREAMER_DEBUG tree_htab.create (31); #endif }
/* For given name, return descriptor, create new if needed. */ static struct alloc_pool_descriptor * allocate_pool_descriptor (const char *name) { struct alloc_pool_descriptor **slot; if (!alloc_pool_hash.is_created ()) alloc_pool_hash.create (10); slot = alloc_pool_hash.find_slot_with_hash (name, htab_hash_pointer (name), INSERT); if (*slot) return *slot; *slot = XCNEW (struct alloc_pool_descriptor); (*slot)->name = name; return *slot; }
void browse_tree (tree begin) { tree head; TB_CODE tbc = TB_UNUSED_COMMAND; ssize_t rd; char *input = NULL; long input_size = 0; fprintf (TB_OUT_FILE, "\nTree Browser\n"); #define TB_SET_HEAD(N) do { \ vec_safe_push (TB_history_stack, N); \ head = N; \ if (TB_verbose) \ if (head) \ { \ print_generic_expr (TB_OUT_FILE, head, 0); \ fprintf (TB_OUT_FILE, "\n"); \ } \ } while (0) TB_SET_HEAD (begin); /* Store in a hashtable information about previous and upper statements. */ { TB_up_ht.create (1023); TB_update_up (head); } while (24) { fprintf (TB_OUT_FILE, "TB> "); rd = TB_getline (&input, &input_size, TB_IN_FILE); if (rd == -1) /* EOF. */ goto ret; if (rd != 1) /* Get a new command. Otherwise the user just pressed enter, and thus she expects the last command to be reexecuted. */ tbc = TB_get_command (input); switch (tbc) { case TB_UPDATE_UP: TB_update_up (head); break; case TB_MAX: if (head && (INTEGRAL_TYPE_P (head) || TREE_CODE (head) == REAL_TYPE || TREE_CODE (head) == FIXED_POINT_TYPE)) TB_SET_HEAD (TYPE_MAX_VALUE (head)); else TB_WF; break; case TB_MIN: if (head && (INTEGRAL_TYPE_P (head) || TREE_CODE (head) == REAL_TYPE || TREE_CODE (head) == FIXED_POINT_TYPE)) TB_SET_HEAD (TYPE_MIN_VALUE (head)); else TB_WF; break; case TB_ELT: if (head && TREE_CODE (head) == TREE_VEC) { /* This command takes another argument: the element number: for example "elt 1". */ TB_NIY; } else if (head && TREE_CODE (head) == VECTOR_CST) { /* This command takes another argument: the element number: for example "elt 1". */ TB_NIY; } else TB_WF; break; case TB_VALUE: if (head && TREE_CODE (head) == TREE_LIST) TB_SET_HEAD (TREE_VALUE (head)); else TB_WF; break; case TB_PURPOSE: if (head && TREE_CODE (head) == TREE_LIST) TB_SET_HEAD (TREE_PURPOSE (head)); else TB_WF; break; case TB_IMAG: if (head && TREE_CODE (head) == COMPLEX_CST) TB_SET_HEAD (TREE_IMAGPART (head)); else TB_WF; break; case TB_REAL: if (head && TREE_CODE (head) == COMPLEX_CST) TB_SET_HEAD (TREE_REALPART (head)); else TB_WF; break; case TB_BLOCK: if (head && TREE_CODE (head) == BIND_EXPR) TB_SET_HEAD (TREE_OPERAND (head, 2)); else TB_WF; break; case TB_SUBBLOCKS: if (head && TREE_CODE (head) == BLOCK) TB_SET_HEAD (BLOCK_SUBBLOCKS (head)); else TB_WF; break; case TB_SUPERCONTEXT: if (head && TREE_CODE (head) == BLOCK) TB_SET_HEAD (BLOCK_SUPERCONTEXT (head)); else TB_WF; break; case TB_VARS: if (head && TREE_CODE (head) == BLOCK) TB_SET_HEAD (BLOCK_VARS (head)); else if (head && TREE_CODE (head) == BIND_EXPR) TB_SET_HEAD (TREE_OPERAND (head, 0)); else TB_WF; break; case TB_REFERENCE_TO_THIS: if (head && TYPE_P (head)) TB_SET_HEAD (TYPE_REFERENCE_TO (head)); else TB_WF; break; case TB_POINTER_TO_THIS: if (head && TYPE_P (head)) TB_SET_HEAD (TYPE_POINTER_TO (head)); else TB_WF; break; case TB_BASETYPE: if (head && TREE_CODE (head) == OFFSET_TYPE) TB_SET_HEAD (TYPE_OFFSET_BASETYPE (head)); else TB_WF; break; case TB_ARG_TYPES: if (head && (TREE_CODE (head) == FUNCTION_TYPE || TREE_CODE (head) == METHOD_TYPE)) TB_SET_HEAD (TYPE_ARG_TYPES (head)); else TB_WF; break; case TB_METHOD_BASE_TYPE: if (head && (TREE_CODE (head) == FUNCTION_TYPE || TREE_CODE (head) == METHOD_TYPE) && TYPE_METHOD_BASETYPE (head)) TB_SET_HEAD (TYPE_METHOD_BASETYPE (head)); else TB_WF; break; case TB_FIELDS: if (head && (TREE_CODE (head) == RECORD_TYPE || TREE_CODE (head) == UNION_TYPE || TREE_CODE (head) == QUAL_UNION_TYPE)) TB_SET_HEAD (TYPE_FIELDS (head)); else TB_WF; break; case TB_DOMAIN: if (head && TREE_CODE (head) == ARRAY_TYPE) TB_SET_HEAD (TYPE_DOMAIN (head)); else TB_WF; break; case TB_VALUES: if (head && TREE_CODE (head) == ENUMERAL_TYPE) TB_SET_HEAD (TYPE_VALUES (head)); else TB_WF; break; case TB_ARG_TYPE: if (head && TREE_CODE (head) == PARM_DECL) TB_SET_HEAD (DECL_ARG_TYPE (head)); else TB_WF; break; case TB_INITIAL: if (head && DECL_P (head)) TB_SET_HEAD (DECL_INITIAL (head)); else TB_WF; break; case TB_RESULT: if (head && DECL_P (head)) TB_SET_HEAD (DECL_RESULT_FLD (head)); else TB_WF; break; case TB_ARGUMENTS: if (head && DECL_P (head)) TB_SET_HEAD (DECL_ARGUMENTS (head)); else TB_WF; break; case TB_ABSTRACT_ORIGIN: if (head && DECL_P (head)) TB_SET_HEAD (DECL_ABSTRACT_ORIGIN (head)); else if (head && TREE_CODE (head) == BLOCK) TB_SET_HEAD (BLOCK_ABSTRACT_ORIGIN (head)); else TB_WF; break; case TB_ATTRIBUTES: if (head && DECL_P (head)) TB_SET_HEAD (DECL_ATTRIBUTES (head)); else if (head && TYPE_P (head)) TB_SET_HEAD (TYPE_ATTRIBUTES (head)); else TB_WF; break; case TB_CONTEXT: if (head && DECL_P (head)) TB_SET_HEAD (DECL_CONTEXT (head)); else if (head && TYPE_P (head) && TYPE_CONTEXT (head)) TB_SET_HEAD (TYPE_CONTEXT (head)); else TB_WF; break; case TB_OFFSET: if (head && TREE_CODE (head) == FIELD_DECL) TB_SET_HEAD (DECL_FIELD_OFFSET (head)); else TB_WF; break; case TB_BIT_OFFSET: if (head && TREE_CODE (head) == FIELD_DECL) TB_SET_HEAD (DECL_FIELD_BIT_OFFSET (head)); else TB_WF; break; case TB_UNIT_SIZE: if (head && DECL_P (head)) TB_SET_HEAD (DECL_SIZE_UNIT (head)); else if (head && TYPE_P (head)) TB_SET_HEAD (TYPE_SIZE_UNIT (head)); else TB_WF; break; case TB_SIZE: if (head && DECL_P (head)) TB_SET_HEAD (DECL_SIZE (head)); else if (head && TYPE_P (head)) TB_SET_HEAD (TYPE_SIZE (head)); else TB_WF; break; case TB_TYPE: if (head && TREE_TYPE (head)) TB_SET_HEAD (TREE_TYPE (head)); else TB_WF; break; case TB_DECL_SAVED_TREE: if (head && TREE_CODE (head) == FUNCTION_DECL && DECL_SAVED_TREE (head)) TB_SET_HEAD (DECL_SAVED_TREE (head)); else TB_WF; break; case TB_BODY: if (head && TREE_CODE (head) == BIND_EXPR) TB_SET_HEAD (TREE_OPERAND (head, 1)); else TB_WF; break; case TB_CHILD_0: if (head && EXPR_P (head) && TREE_OPERAND (head, 0)) TB_SET_HEAD (TREE_OPERAND (head, 0)); else TB_WF; break; case TB_CHILD_1: if (head && EXPR_P (head) && TREE_OPERAND (head, 1)) TB_SET_HEAD (TREE_OPERAND (head, 1)); else TB_WF; break; case TB_CHILD_2: if (head && EXPR_P (head) && TREE_OPERAND (head, 2)) TB_SET_HEAD (TREE_OPERAND (head, 2)); else TB_WF; break; case TB_CHILD_3: if (head && EXPR_P (head) && TREE_OPERAND (head, 3)) TB_SET_HEAD (TREE_OPERAND (head, 3)); else TB_WF; break; case TB_PRINT: if (head) debug_tree (head); else TB_WF; break; case TB_PRETTY_PRINT: if (head) { print_generic_stmt (TB_OUT_FILE, head, 0); fprintf (TB_OUT_FILE, "\n"); } else TB_WF; break; case TB_SEARCH_NAME: break; case TB_SEARCH_CODE: { enum tree_code code; char *arg_text; arg_text = strchr (input, ' '); if (arg_text == NULL) { fprintf (TB_OUT_FILE, "First argument is missing. This isn't a valid search command. \n"); break; } code = TB_get_tree_code (arg_text + 1); /* Search in the subtree a node with the given code. */ { tree res; res = walk_tree (&head, find_node_with_code, &code, NULL); if (res == NULL_TREE) { fprintf (TB_OUT_FILE, "There's no node with this code (reachable via the walk_tree function from this node).\n"); } else { fprintf (TB_OUT_FILE, "Achoo! I got this node in the tree.\n"); TB_SET_HEAD (res); } } break; } #define TB_MOVE_HEAD(FCT) do { \ if (head) \ { \ tree t; \ t = FCT (head); \ if (t) \ TB_SET_HEAD (t); \ else \ TB_WF; \ } \ else \ TB_WF; \ } while (0) case TB_FIRST: TB_MOVE_HEAD (TB_first_in_bind); break; case TB_LAST: TB_MOVE_HEAD (TB_last_in_bind); break; case TB_UP: TB_MOVE_HEAD (TB_up_expr); break; case TB_PREV: TB_MOVE_HEAD (TB_prev_expr); break; case TB_NEXT: TB_MOVE_HEAD (TB_next_expr); break; case TB_HPREV: /* This command is a little bit special, since it deals with history stack. For this reason it should keep the "head = ..." statement and not use TB_MOVE_HEAD. */ if (head) { tree t; t = TB_history_prev (); if (t) { head = t; if (TB_verbose) { print_generic_expr (TB_OUT_FILE, head, 0); fprintf (TB_OUT_FILE, "\n"); } } else TB_WF; } else TB_WF; break; case TB_CHAIN: /* Don't go further if it's the last node in this chain. */ if (head && TREE_CODE (head) == BLOCK) TB_SET_HEAD (BLOCK_CHAIN (head)); else if (head && TREE_CHAIN (head)) TB_SET_HEAD (TREE_CHAIN (head)); else TB_WF; break; case TB_FUN: /* Go up to the current function declaration. */ TB_SET_HEAD (current_function_decl); fprintf (TB_OUT_FILE, "Current function declaration.\n"); break; case TB_HELP: /* Display a help message. */ { int i; fprintf (TB_OUT_FILE, "Possible commands are:\n\n"); for (i = 0; i < TB_UNUSED_COMMAND; i++) { fprintf (TB_OUT_FILE, "%20s - %s\n", TB_COMMAND_TEXT (i), TB_COMMAND_HELP (i)); } } break; case TB_VERBOSE: if (TB_verbose == 0) { TB_verbose = 1; fprintf (TB_OUT_FILE, "Verbose on.\n"); } else { TB_verbose = 0; fprintf (TB_OUT_FILE, "Verbose off.\n"); } break; case TB_EXIT: case TB_QUIT: /* Just exit from this function. */ goto ret; default: TB_NIY; } } ret:; TB_up_ht.dispose (); return; }