diff options
-rw-r--r-- | ld/ChangeLog | 8 | ||||
-rw-r--r-- | ld/emultempl/hppaelf.em | 228 |
2 files changed, 155 insertions, 81 deletions
diff --git a/ld/ChangeLog b/ld/ChangeLog index 21fc924..50ba5e2 100644 --- a/ld/ChangeLog +++ b/ld/ChangeLog @@ -1,5 +1,13 @@ Fri Feb 25 10:47:25 1994 Jeffrey A. Law (law@snake.cs.utah.edu) + * emultempl/hppaelf.em: First attempt to clean this file up. + Add comments in several functions as to their purpose and + how they function (or my current best guess). Clean up horrible + spacing and indention that never should have been accepted in the + first place. Add FIXMEs for issues which need to be resolved. + Disable linker-stub generation until it gets fixed. This allows + the linker to at least work on simple code for testing purposes. + * ldlang.c (lang_size_sections): No longer static (PA ELF calls it via hppaelf_finish). Prototype moved into ldlang.h. (lang_process): Move problematic extra call to lang_size_sections diff --git a/ld/emultempl/hppaelf.em b/ld/emultempl/hppaelf.em index 128cdda..fe2334d 100644 --- a/ld/emultempl/hppaelf.em +++ b/ld/emultempl/hppaelf.em @@ -35,7 +35,17 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ #include "ldmain.h" #include "ldctor.h" -static void hppaelf_before_parse() +static lang_input_statement_type *stub_file = 0; +static lang_input_section_type *stub_input_section = NULL; + +/* FIXME. This doesn't belong here. */ +extern asymbol *hppa_look_for_stubs_in_section (); + +/* Perform some emulation specific initialization. For PA ELF we set + up the local label prefix and the output architecture. */ + +static void +hppaelf_before_parse () { link_info.lprefix = "L$"; link_info.lprefix_len = 2; @@ -43,31 +53,51 @@ static void hppaelf_before_parse() ldfile_output_architecture = bfd_arch_hppa; } -static lang_input_statement_type *stub_file = 0; - -static lang_input_section_type *stub_input_section = NULL; +/* Walk all the lang statements splicing out any padding statements from + the list. */ static void -hppaelf_search_for_padding_statements(s,prev) - lang_statement_union_type *s; - lang_statement_union_type **prev; +hppaelf_search_for_padding_statements (s, prev) + lang_statement_union_type *s; + lang_statement_union_type **prev; { lang_statement_union_type *sprev = NULL; - for (; s != (lang_statement_union_type *) NULL; s = s->next) + for (; s != NULL; s = s->next) { switch (s->header.type) { + + /* We want recursively walk these sections. */ case lang_constructors_statement_enum: - hppaelf_search_for_padding_statements (constructor_list.head,&constructor_list.head); + hppaelf_search_for_padding_statements (constructor_list.head, + &constructor_list.head); break; + case lang_output_section_statement_enum: - hppaelf_search_for_padding_statements - (s->output_section_statement.children.head,&s->output_section_statement.children.head); + hppaelf_search_for_padding_statements (s->output_section_statement. + children.head, + &s->output_section_statement. + children.head); break; + + /* Huh? What is a lang_wild_statement? */ case lang_wild_statement_enum: - hppaelf_search_for_padding_statements - (s->wild_statement.children.head,&s->wild_statement.children.head); + hppaelf_search_for_padding_statements(s->wild_statement. + children.head, + &s->wild_statement. + children.head); + break; + + /* Here's what we are really looking for. Splice these out of + the list. */ + case lang_padding_statement_enum: + if (sprev) + sprev->header.next = s->header.next; + else + **prev = *s; break; + + /* We don't care about these cases. */ case lang_data_statement_enum: case lang_object_symbols_statement_enum: case lang_output_statement_enum: @@ -77,41 +107,47 @@ hppaelf_search_for_padding_statements(s,prev) case lang_assignment_statement_enum: case lang_address_statement_enum: break; - case lang_padding_statement_enum: - if ( sprev ) - { - sprev->header.next = s->header.next; - } - else - { - **prev = *s; - } - break; + default: - FAIL (); + abort (); break; } sprev = s; } } +/* Final emulation specific call. For the PA we use this opportunity + to determine what linker stubs are needed and generate them. + + FIXME: fast-linker work broke this in a big way. statement->asymbols + doesn't have anything useful in it anymore. And if we slurp in + the symbol table here and pass it down then we get lots of undefined + symbols. Egad. */ + static void -hppaelf_finish() +hppaelf_finish () { - extern asymbol *hppa_look_for_stubs_in_section(); + /* Disabled until it's fixed to work with the new linker. A noteworty + amount of code will still function without linker stubs allowing us + to continue testing. */ + +#if 0 + /* Only create stubs for final objects. */ if (link_info.relocateable == false) { - /* check for needed stubs */ - extern lang_statement_list_type file_chain; lang_input_statement_type *statement; - + + /* Look at all the statements. */ for (statement = (lang_input_statement_type *)file_chain.head; - statement != (lang_input_statement_type *)NULL; + statement != NULL; statement = (lang_input_statement_type *)statement->next) { asection *section; bfd *abfd = statement->the_bfd; + + /* Look at all the sections attached to the bfd associated with + the current statement. */ for (section = abfd->sections; section != (asection *)NULL; section = section ->next) @@ -119,7 +155,9 @@ hppaelf_finish() int new_sym_cnt = 0; int i,j; asymbol *syms; - + + /* Do the dirty work; an array of symbols for each new stub + will be returned. */ syms = hppa_look_for_stubs_in_section (stub_file->the_bfd, abfd, output_bfd, @@ -127,68 +165,94 @@ hppaelf_finish() statement->asymbols, &new_sym_cnt, &link_info); - - if ( (new_sym_cnt > 0) && syms ) + + if (new_sym_cnt > 0 && syms) { struct symbol_cache_entry **old_asymbols; - + old_asymbols = stub_file->asymbols; - - stub_file->asymbols = xmalloc((stub_file->symbol_count + new_sym_cnt) * sizeof(asymbol *)); - - for ( j = 0; j < stub_file->symbol_count; j++ ) + + /* Allocate space for the updated symbols */ + stub_file->asymbols + = xmalloc ((stub_file->symbol_count + new_sym_cnt) + * sizeof(asymbol *)); + if (stub_file->asymbols == NULL) + abort (); + + /* Copy the old symbols. + + FIXME. Shouldn't we free the space used by the old + symbols here? Might there be dangling references + made within hppa_look_for_stubs_in_section? */ + for (j = 0; j < stub_file->symbol_count; j++) stub_file->asymbols[j] = old_asymbols[j]; - - for ( j = 0, i = stub_file->symbol_count; j < new_sym_cnt; j++, i++ ) + + /* Copy in the new symbols. */ + for (j = 0, i = stub_file->symbol_count; + j < new_sym_cnt; + j++, i++) stub_file->asymbols[i] = &syms[j]; - + + /* Finally, adjust the symbol count. */ stub_file->symbol_count += new_sym_cnt; } } } - /* Add a statement to get the linker stubs included in the output */ - lang_add_wild(".hppa_linker_stubs",NULL); - - /* If we've added stubs,remove the padding_statements because */ - /* they are no longer valid */ - hppaelf_search_for_padding_statements(stat_ptr->head,&(stat_ptr->head)); + + /* Add a statement to get the linker stubs included in the output. */ + lang_add_wild (".hppa_linker_stubs",NULL); + + /* If stubs were added, then remove all the (now invalid) padding + statements. */ + hppaelf_search_for_padding_statements (stat_ptr->head, + &stat_ptr->head); } + /* Size up the sections again. */ - lang_size_sections (stat_ptr->head, - abs_output_section, - &(stat_ptr->head), 0, (bfd_vma) 0, false); - + lang_size_sections (stat_ptr->head, abs_output_section, + &stat_ptr->head, 0, (bfd_vma) 0, false); + + /* FIXME: Do we need to redo the "assignments" too? */ +#endif } +/* Create any emulation specific output statements. FIXME? Is this + redundant with above lang_add_wild or the code in the script? */ + static void -hppaelf_create_output_section_statements() +hppaelf_create_output_section_statements () { asection *stub_sec; - asection *output_text_sec = bfd_make_section_old_way(output_bfd,".text"); + asection *output_text_sec = bfd_make_section_old_way (output_bfd, ".text"); lang_input_section_type *new_input_sec; - + + /* Add a new "input file" (the linker stubs themselves). */ stub_file = lang_add_input_file ("linker stubs", lang_input_file_is_fake_enum, - (char *) NULL); + NULL); stub_file->the_bfd = bfd_create ("linker stubs", output_bfd); stub_file->symbol_count = 0; stub_file->the_bfd->sections = 0; - - stub_sec = bfd_make_section_old_way(stub_file->the_bfd,".hppa_linker_stubs"); + + /* Add a section to the fake input file. */ + stub_sec = bfd_make_section_old_way (stub_file->the_bfd, + ".hppa_linker_stubs"); stub_sec->output_section = output_text_sec; - bfd_set_section_flags(stub_file->the_bfd, stub_sec, SEC_HAS_CONTENTS | SEC_ALLOC | SEC_CODE | SEC_RELOC ); + bfd_set_section_flags (stub_file->the_bfd, stub_sec, + SEC_HAS_CONTENTS | SEC_ALLOC | SEC_CODE | SEC_RELOC); - /* The user data of a bfd points to the input statement attached */ + /* The user data of a bfd points to the input statement attached. */ stub_file->the_bfd->usrdata = (void *)stub_file; - stub_file->common_section = - bfd_make_section(stub_file->the_bfd,"COMMON"); + stub_file->common_section = bfd_make_section(stub_file->the_bfd,"COMMON"); - new_input_sec = (lang_input_section_type *)stat_alloc(sizeof(lang_input_section_type)); - if ( new_input_sec ) + new_input_sec = (lang_input_section_type *) + stat_alloc (sizeof (lang_input_section_type)); + + if (new_input_sec) { lang_output_section_statement_type *text_output_sec; lang_statement_union_type *stmt; - lang_wild_statement_type *stub_statement; + new_input_sec->section = stub_sec; new_input_sec->ifile = stub_file; new_input_sec->header.type = lang_input_section_enum; @@ -196,37 +260,39 @@ hppaelf_create_output_section_statements() stub_input_section = new_input_sec; - /* Find the output_section_statement for .text, */ - /* then find the wild_statement for .hppa_linker_stubs */ - - text_output_sec = lang_output_section_find(".text"); + /* Find the output_section_statement for .text, + then find the wild_statement for .hppa_linker_stubs. */ + text_output_sec = lang_output_section_find (".text"); stmt = text_output_sec->children.head; while (stmt && stmt->header.type != lang_wild_statement_enum) + stmt = stmt->header.next; + + /* Do something with the wild statement. FIXME. */ + if (stmt) { - stmt = stmt->header.next; - } - - if ( stmt ) - { - lang_wild_statement_type *wstmt = (lang_wild_statement_type *)stmt; - lang_list_init(&wstmt->children); - lang_statement_append(&wstmt->children, - (lang_statement_union_type *)new_input_sec, - &new_input_sec->header.next); + lang_wild_statement_type *wstmt = (lang_wild_statement_type *)stmt; + lang_list_init (&wstmt->children); + lang_statement_append (&wstmt->children, + (lang_statement_union_type *)new_input_sec, + &new_input_sec->header.next); } } } +/* Set the output architecture and machine. */ + static void hppaelf_set_output_arch() { - /* Set the output architecture and machine if possible */ - unsigned long machine = 0; - bfd_set_arch_mach(output_bfd, ldfile_output_architecture, machine); + unsigned long machine = 0; + + bfd_set_arch_mach (output_bfd, ldfile_output_architecture, machine); } +/* The script itself gets inserted here. */ + static char * hppaelf_get_script(isfile) int *isfile; |