OSDN Git Service

* objcopy.c (redefine_list_append): Add an argument that
authorJason Thorpe <thorpej@netbsd.org>
Mon, 2 Jun 2003 14:45:13 +0000 (14:45 +0000)
committerJason Thorpe <thorpej@netbsd.org>
Mon, 2 Jun 2003 14:45:13 +0000 (14:45 +0000)
indicates the context from which this function is being
called.  Change all callers.
(copy_options): Add a new option, --redefine-syms.
(copy_usage): Document new option.
(copy_main): Handle the --redefine-syms option.
* doc/binutils.text (objcopy): Document new option.

binutils/ChangeLog
binutils/doc/binutils.texi
binutils/objcopy.c

index 85d4f97..536d761 100644 (file)
@@ -1,3 +1,14 @@
+2003-06-02  Chris Demetriou  <cgd@broadcom.com>
+            Jason Thorpe  <thorpej@wasabisystems.com>
+
+       * objcopy.c (redefine_list_append): Add an argument that
+       indicates the context from which this function is being
+       called.  Change all callers.
+       (copy_options): Add a new option, --redefine-syms.
+       (copy_usage): Document new option.
+       (copy_main): Handle the --redefine-syms option.
+       * doc/binutils.text (objcopy): Document new option.
+
 2003-05-31  Richard Henderson  <rth@redhat.com>
 
        * readelf.c (byte_get_signed): New.
index f5f06e3..9c12f78 100644 (file)
@@ -958,6 +958,7 @@ objcopy [@option{-F} @var{bfdname}|@option{--target=}@var{bfdname}]
         [@option{--change-leading-char} ] [@option{--remove-leading-char}]
         [@option{--srec-len=}@var{ival} ] [@option{--srec-forceS3}]
         [@option{--redefine-sym} @var{old}=@var{new} ]
+        [@option{--redefine-syms=}@var{filename} ]
         [@option{--weaken}]
         [@option{--keep-symbols=}@var{filename}]
         [@option{--strip-symbols=}@var{filename}]
@@ -1284,6 +1285,12 @@ Change the name of a symbol @var{old}, to @var{new}.  This can be useful
 when one is trying link two things together for which you have no
 source, and there are name collisions.
 
+@item --redefine-syms=@var{filename}
+Apply @option{--redefine-sym} to each symbol pair "@var{old} @var{new}"
+listed in the file @var{filename}.  @var{filename} is simply a flat file,
+with one symbol pair per line.  Line comments may be introduced by the hash
+character.  This option may be given more than once.
+
 @item --weaken
 Change all global symbols in the file to be weak.  This can be useful
 when building an object which will be linked against other objects using
index 27c844f..68402e8 100644 (file)
@@ -105,7 +105,7 @@ static int copy_main
 static const char *lookup_sym_redefinition
   PARAMS((const char *));
 static void redefine_list_append
-  PARAMS ((const char *, const char *));
+  PARAMS ((const char *, const char *, const char *));
 static const char * find_section_rename
   PARAMS ((bfd *, sec_ptr, flagword *));
 static void add_section_rename
@@ -263,7 +263,8 @@ static char *prefix_alloc_sections_string = 0;
 #define OPTION_STRIP_UNNEEDED (OPTION_SET_START + 1)
 #define OPTION_WEAKEN (OPTION_STRIP_UNNEEDED + 1)
 #define OPTION_REDEFINE_SYM (OPTION_WEAKEN + 1)
-#define OPTION_SREC_LEN (OPTION_REDEFINE_SYM + 1)
+#define OPTION_REDEFINE_SYMS (OPTION_REDEFINE_SYM + 1)
+#define OPTION_SREC_LEN (OPTION_REDEFINE_SYMS + 1)
 #define OPTION_SREC_FORCES3 (OPTION_SREC_LEN + 1)
 #define OPTION_STRIP_SYMBOLS (OPTION_SREC_FORCES3 + 1)
 #define OPTION_KEEP_SYMBOLS (OPTION_STRIP_SYMBOLS + 1)
@@ -350,6 +351,7 @@ static struct option copy_options[] =
   {"prefix-alloc-sections", required_argument, 0, OPTION_PREFIX_ALLOC_SECTIONS},
   {"preserve-dates", no_argument, 0, 'p'},
   {"redefine-sym", required_argument, 0, OPTION_REDEFINE_SYM},
+  {"redefine-syms", required_argument, 0, OPTION_REDEFINE_SYMS},
   {"remove-leading-char", no_argument, 0, OPTION_REMOVE_LEADING_CHAR},
   {"remove-section", required_argument, 0, 'R'},
   {"rename-section", required_argument, 0, OPTION_RENAME_SECTION},
@@ -444,6 +446,8 @@ copy_usage (stream, exit_status)
      --change-leading-char         Force output format's leading character style\n\
      --remove-leading-char         Remove leading character from global symbols\n\
      --redefine-sym <old>=<new>    Redefine symbol name <old> to <new>\n\
+     --redefine-syms <file>        --redefine-sym for all symbol pairs \n\
+                                     listed in <file>\n\
      --srec-len <number>           Restrict the length of generated Srecords\n\
      --srec-forceS3                Restrict the type of generated Srecords to S3\n\
      --strip-symbols <file>        -N for all symbols listed in <file>\n\
@@ -940,7 +944,8 @@ lookup_sym_redefinition (source)
 /* Add a node to a symbol redefine list.  */
 
 static void
-redefine_list_append (source, target)
+redefine_list_append (cause, source, target)
+     const char *cause;
      const char *source;
      const char *target;
 {
@@ -952,13 +957,11 @@ redefine_list_append (source, target)
     {
       if (strcmp (source, list->source) == 0)
        fatal (_("%s: Multiple redefinition of symbol \"%s\""),
-              "--redefine-sym",
-              source);
+              cause, source);
 
       if (strcmp (target, list->target) == 0)
        fatal (_("%s: Symbol \"%s\" is target of more than one redefinition"),
-              "--redefine-sym",
-              target);
+              cause, target);
     }
 
   new_node = (struct redefine_node *) xmalloc (sizeof (struct redefine_node));
@@ -970,6 +973,116 @@ redefine_list_append (source, target)
   *p = new_node;
 }
 
+/* Handle the --redefine-syms option.  Read lines containing "old new"
+   from the file, and add them to the symbol redefine list.  */
+
+void
+add_redefine_syms_file (filename)
+     const char *filename;
+{
+  FILE *file;
+  char *buf;
+  size_t bufsize, len, outsym_off;
+  int c, lineno;
+
+  file = fopen (filename, "r");
+  if (file == (FILE *) NULL)
+    fatal (_("couldn't open symbol redefinition file %s (error: %s)"),
+          filename, strerror (errno));
+
+  bufsize = 100;
+  buf = (char *) xmalloc (bufsize);
+
+  lineno = 1;
+  c = getc (file);
+  len = 0;
+  outsym_off = 0;
+  while (c != EOF)
+    {
+      /* Collect the input symbol name.  */
+      while (! IS_WHITESPACE (c) && ! IS_LINE_TERMINATOR (c) && c != EOF)
+       {
+         if (c == '#')
+           goto comment;
+         buf[len++] = c;
+         if (len >= bufsize)
+           {
+             bufsize *= 2;
+             buf = xrealloc (buf, bufsize);
+           }
+         c = getc (file);
+       }
+      buf[len++] = '\0';
+      if (c == EOF)
+       break;
+
+      /* Eat white space between the symbol names.  */
+      while (IS_WHITESPACE (c))
+       c = getc (file);
+      if (c == '#' || IS_LINE_TERMINATOR (c))
+       goto comment;
+      if (c == EOF)
+       break;
+
+      /* Collect the output symbol name.  */
+      outsym_off = len;
+      while (! IS_WHITESPACE (c) && ! IS_LINE_TERMINATOR (c) && c != EOF)
+       {
+         if (c == '#')
+           goto comment;
+         buf[len++] = c;
+         if (len >= bufsize)
+           {
+             bufsize *= 2;
+             buf = xrealloc (buf, bufsize);
+           }
+         c = getc (file);
+       }
+      buf[len++] = '\0';
+      if (c == EOF)
+       break;
+
+      /* Eat white space at end of line.  */
+      while (! IS_LINE_TERMINATOR(c) && c != EOF && IS_WHITESPACE (c))
+       c = getc (file);
+      if (c == '#')
+       goto comment;
+      /* Handle \r\n.  */
+      if ((c == '\r' && (c = getc (file)) == '\n')
+         || c == '\n' || c == EOF)
+       {
+ end_of_line:
+         /* Append the redefinition to the list.  */
+         if (buf[0] != '\0')
+           redefine_list_append (filename, &buf[0], &buf[outsym_off]);
+
+         lineno++;     
+         len = 0;
+         outsym_off = 0;
+         if (c == EOF)
+           break;
+         c = getc (file);
+         continue;
+       }
+      else
+       fatal (_("%s: garbage at end of line %d"), filename, lineno);
+ comment:
+      if (len != 0 && (outsym_off == 0 || outsym_off == len))
+       fatal (_("%s: missing new symbol name at line %d"), filename, lineno);
+      buf[len++] = '\0';
+
+      /* Eat the rest of the line and finish it.  */
+      while (c != '\n' && c != EOF)
+       c = getc (file);
+      goto end_of_line;
+    }
+
+  if (len != 0)
+    fatal (_("%s: premature end of file at line %d"), filename, lineno);
+
+  free (buf);
+}
+
 /* Keep only every `copy_byte'th byte in MEMHUNK, which is *SIZE bytes long.
    Adjust *SIZE.  */
 
@@ -2547,13 +2660,17 @@ copy_main (argc, argv)
            target = (char *) xmalloc (len + 1);
            strcpy (target, nextarg);
 
-           redefine_list_append (source, target);
+           redefine_list_append ("--redefine-sym", source, target);
 
            free (source);
            free (target);
          }
          break;
 
+       case OPTION_REDEFINE_SYMS:
+         add_redefine_syms_file (optarg);
+         break;
+
        case OPTION_SET_SECTION_FLAGS:
          {
            const char *s;