/* This file is is generated by a shell script. DO NOT EDIT! */
/* Emulate the original gld for the given ${EMULATION_NAME}
- Copyright (C) 2014-2017 Free Software Foundation, Inc.
+ Copyright (C) 2014-2020 Free Software Foundation, Inc.
Written by Steve Chamberlain steve@cygnus.com
Extended for the MSP430 by Nick Clifton nickc@redhat.com
-
+
This file is part of the GNU Binutils.
This program is free software; you can redistribute it and/or modify
#include "sysdep.h"
#include "bfd.h"
#include "bfdlink.h"
+#include "ctf-api.h"
#include "ld.h"
#include "getopt.h"
size = BYTE_SIZE;
break;
default:
- einfo ("%P: error: unhandled data_statement size\n");
+ einfo (_("%P: error: unhandled data_statement size\n"));
FAIL ();
}
return size;
break;
case lang_wild_statement_enum:
- amount += scan_children (l->wild_statement.children.head);
+ amount += scan_children (l->wild_statement.children.head);
break;
case lang_data_statement_enum:
return amount;
}
-
+
+#define WARN_UPPER 0
+#define WARN_LOWER 1
+#define WARN_TEXT 0
+#define WARN_DATA 1
+#define WARN_BSS 2
+#define WARN_RODATA 3
+
+/* Warn only once per output section.
+ * NAME starts with ".upper." or ".lower.". */
+static void
+warn_no_output_section (const char *name)
+{
+ static bfd_boolean warned[2][4] = {{FALSE, FALSE, FALSE, FALSE},
+ {FALSE, FALSE, FALSE, FALSE}};
+ int i = WARN_LOWER;
+
+ if (strncmp (name, ".upper.", 7) == 0)
+ i = WARN_UPPER;
+
+ if (!warned[i][WARN_TEXT] && strcmp (name + 6, ".text") == 0)
+ warned[i][WARN_TEXT] = TRUE;
+ else if (!warned[i][WARN_DATA] && strcmp (name + 6, ".data") == 0)
+ warned[i][WARN_DATA] = TRUE;
+ else if (!warned[i][WARN_BSS] && strcmp (name + 6, ".bss") == 0)
+ warned[i][WARN_BSS] = TRUE;
+ else if (!warned[i][WARN_RODATA] && strcmp (name + 6, ".rodata") == 0)
+ warned[i][WARN_RODATA] = TRUE;
+ else
+ return;
+ einfo ("%P: warning: no input section rule matches %s in linker script\n",
+ name);
+}
+
+
/* Place an orphan section. We use this to put .either sections
into either their lower or their upper equivalents. */
if (constraint != 0)
return NULL;
+ if (strncmp (secname, ".upper.", 7) == 0
+ || strncmp (secname, ".lower.", 7) == 0)
+ {
+ warn_no_output_section (secname);
+ return NULL;
+ }
+
/* We only need special handling for .either sections. */
if (strncmp (secname, ".either.", 8) != 0)
return NULL;
}
else
name = (char *) secname;
-
+
lower_name = concat (".lower", name, NULL);
upper_name = concat (".upper", name, NULL);
if (lower == NULL && upper == NULL)
{
- einfo ("%P: error: no section named %s or %s in linker script\n",
+ einfo (_("%P: error: no section named %s or %s in linker script\n"),
lower_name, upper_name);
goto end;
}
lower = lang_output_section_find (name);
if (lower == NULL)
{
- einfo ("%P: error: no section named %s in linker script\n", name);
+ einfo (_("%P: error: no section named %s in linker script\n"), name);
goto end;
}
}
end:
free (upper_name);
free (lower_name);
- if (buf)
- free (buf);
+ free (buf);
return lower;
}
EOF
}
static void
-move_prefixed_section (asection *s, char *new_name,
- lang_output_section_statement_type * new_output_sec)
+add_region_prefix (bfd *abfd ATTRIBUTE_UNUSED, asection *s,
+ void *unused ATTRIBUTE_UNUSED)
{
- s->name = new_name;
- if (s->output_section == NULL)
- lang_add_section (& (new_output_sec->children), s, NULL, new_output_sec);
- else
- {
- lang_output_section_statement_type * curr_output_sec
- = lang_output_section_find (s->output_section->name);
- change_output_section (&(curr_output_sec->children.head), s,
- new_output_sec);
- }
-}
-
-static void
-add_region_prefix (bfd *abfd, asection *s,
- ATTRIBUTE_UNUSED void *unused)
-{
- const char *curr_name = bfd_get_section_name (abfd, s);
- char * base_name;
- char * new_input_sec_name = NULL;
- char * new_output_sec_name = NULL;
+ const char *curr_name = bfd_section_name (s);
int region = REGION_NONE;
if (strncmp (curr_name, ".text", 5) == 0)
- {
- region = code_region;
- base_name = concat (".text", NULL);
- }
+ region = code_region;
else if (strncmp (curr_name, ".data", 5) == 0)
- {
- region = data_region;
- base_name = concat (".data", NULL);
- }
+ region = data_region;
else if (strncmp (curr_name, ".bss", 4) == 0)
- {
- region = data_region;
- base_name = concat (".bss", NULL);
- }
+ region = data_region;
else if (strncmp (curr_name, ".rodata", 7) == 0)
- {
- region = data_region;
- base_name = concat (".rodata", NULL);
- }
+ region = data_region;
else
return;
case REGION_NONE:
break;
case REGION_UPPER:
- new_input_sec_name = concat (".upper", curr_name, NULL);
- new_output_sec_name = concat (".upper", base_name, NULL);
- lang_output_section_statement_type * upper
- = lang_output_section_find (new_output_sec_name);
- if (upper != NULL)
- {
- move_prefixed_section (s, new_input_sec_name, upper);
- }
- else
- einfo ("%P: error: no section named %s in linker script\n",
- new_output_sec_name);
+ bfd_rename_section (s, concat (".upper", curr_name, NULL));
break;
case REGION_LOWER:
- new_input_sec_name = concat (".lower", curr_name, NULL);
- new_output_sec_name = concat (".lower", base_name, NULL);
- lang_output_section_statement_type * lower
- = lang_output_section_find (new_output_sec_name);
- if (lower != NULL)
- {
- move_prefixed_section (s, new_input_sec_name, lower);
- }
- else
- einfo ("%P: error: no section named %s in linker script\n",
- new_output_sec_name);
+ bfd_rename_section (s, concat (".lower", curr_name, NULL));
break;
case REGION_EITHER:
s->name = concat (".either", curr_name, NULL);
FAIL ();
break;
}
- free (base_name);
- if (new_input_sec_name)
- {
- free (new_input_sec_name);
- free (new_output_sec_name);
- }
}
static void
static void
gld${EMULATION_NAME}_list_options (FILE * file)
{
- fprintf (file, _("\
- --code-region={either,lower,upper,none}\n\
- \tTransform .text* sections to {either,lower,upper,none}.text* sections.\n\
- --data-region={either,lower,upper,none}\n\
- \tTransform .data*, .rodata* and .bss* sections to\n\
- {either,lower,upper,none}.{bss,data,rodata}* sections\n\
- --disable-sec-transformation\n\
- \tDisable transformation of .{text,data,bss,rodata}* sections to\n\
- \tadd the {either,lower,upper,none} prefixes\n"));
+ fprintf (file, _(" --code-region={either,lower,upper,none}\n\
+ Transform .text* sections to {either,lower,upper,none}.text* sections\n"));
+ fprintf (file, _(" --data-region={either,lower,upper,none}\n\
+ Transform .data*, .rodata* and .bss* sections to\n\
+ {either,lower,upper,none}.{bss,data,rodata}* sections\n"));
+ fprintf (file, _(" --disable-sec-transformation\n\
+ Disable transformation of .{text,data,bss,rodata}* sections to\n\
+ add the {either,lower,upper,none} prefixes\n"));
}
static bfd_boolean
code_region = REGION_NONE;
else if (strlen (optarg) == 0)
{
- einfo (_("%P: --code-region requires an argument: \
- {upper,lower,either,none}\n"));
+ einfo (_("%P: --code-region requires an argument: "
+ "{upper,lower,either,none}\n"));
return FALSE;
}
else
{
- einfo (_("%P: error: unrecognized argument to --code-region= option: \
- \"%s\"\n"), optarg);
+ einfo (_("%P: error: unrecognized argument to --code-region= option: "
+ "\"%s\"\n"), optarg);
return FALSE;
}
break;
data_region = REGION_NONE;
else if (strlen (optarg) == 0)
{
- einfo (_("%P: --data-region requires an argument: \
- {upper,lower,either,none}\n"));
+ einfo (_("%P: --data-region requires an argument: "
+ "{upper,lower,either,none}\n"));
return FALSE;
}
else
{
- einfo (_("%P: error: unrecognized argument to --data-region= option: \
- \"%s\"\n"), optarg);
+ einfo (_("%P: error: unrecognized argument to --data-region= option: "
+ "\"%s\"\n"), optarg);
return FALSE;
}
break;
}
static void
-eval_upper_either_sections (bfd *abfd, asection *s, void *data)
+eval_upper_either_sections (bfd *abfd ATTRIBUTE_UNUSED,
+ asection *s, void *data)
{
- char * base_sec_name;
+ const char * base_sec_name;
const char * curr_name;
char * either_name;
int curr_region;
if (bfd_link_relocatable (&link_info))
return;
- base_sec_name = (char *) data;
- curr_name = bfd_get_section_name (abfd, s);
+ base_sec_name = (const char *) data;
+ curr_name = bfd_section_name (s);
/* Only concerned with .either input sections in the upper output section. */
either_name = concat (".either", base_sec_name, NULL);
}
static void
-eval_lower_either_sections (bfd *abfd, asection *s, void *data)
+eval_lower_either_sections (bfd *abfd ATTRIBUTE_UNUSED,
+ asection *s, void *data)
{
- char * base_sec_name;
+ const char * base_sec_name;
const char * curr_name;
char * either_name;
int curr_region;
if (bfd_link_relocatable (&link_info))
return;
- base_sec_name = (char *) data;
- curr_name = bfd_get_section_name (abfd, s);
+ base_sec_name = (const char *) data;
+ curr_name = bfd_section_name (s);
/* Only concerned with .either input sections in the lower or "default"
output section i.e. not in the upper output section. */
msp430_elf_after_allocation (void)
{
int relax_count = 0;
- int i;
+ unsigned int i;
/* Go over each section twice, once to place either sections that don't fit
in lower into upper, and then again to move any sections in upper that
fit in lower into lower. */
for (i = 0; i < 8; i++)
{
int placement_stage = (i < 4) ? LOWER_TO_UPPER : UPPER_TO_LOWER;
- char * base_sec_name;
+ const char * base_sec_name;
lang_output_section_statement_type * upper;
switch (i % 4)
{
+ default:
case 0:
- base_sec_name = concat (".text", NULL);
+ base_sec_name = ".text";
break;
case 1:
- base_sec_name = concat (".data", NULL);
+ base_sec_name = ".data";
break;
case 2:
- base_sec_name = concat (".bss", NULL);
+ base_sec_name = ".bss";
break;
case 3:
- base_sec_name = concat (".rodata", NULL);
+ base_sec_name = ".rodata";
break;
}
upper = lang_output_section_find (concat (".upper", base_sec_name, NULL));
abfd = abfd->link.next)
{
bfd_map_over_sections (abfd, eval_lower_either_sections,
- base_sec_name);
+ (void *) base_sec_name);
}
}
else if (placement_stage == UPPER_TO_LOWER)
abfd = abfd->link.next)
{
bfd_map_over_sections (abfd, eval_upper_either_sections,
- base_sec_name);
+ (void *) base_sec_name);
}
}
}
- free (base_sec_name);
}
gld${EMULATION_NAME}_after_allocation ();
}
${LDEMUL_HLL-hll_default},
${LDEMUL_AFTER_PARSE-after_parse_default},
msp430_elf_after_open,
+ after_check_relocs_default,
+ before_place_orphans_default,
msp430_elf_after_allocation,
${LDEMUL_SET_OUTPUT_ARCH-set_output_arch_default},
${LDEMUL_CHOOSE_TARGET-ldemul_default_target},
${LDEMUL_RECOGNIZED_FILE-NULL},
${LDEMUL_FIND_POTENTIAL_LIBRARIES-NULL},
${LDEMUL_NEW_VERS_PATTERN-NULL},
- ${LDEMUL_EXTRA_MAP_FILE_TEXT-NULL}
+ ${LDEMUL_EXTRA_MAP_FILE_TEXT-NULL},
+ ${LDEMUL_EMIT_CTF_EARLY-NULL},
+ ${LDEMUL_EXAMINE_STRTAB_FOR_CTF-NULL},
+ ${LDEMUL_PRINT_SYMBOL-NULL}
};
EOF
# \f