1 /* objcopy.c -- copy object file from input to output, optionally massaging it.
2 Copyright 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
4 Free Software Foundation, Inc.
6 This file is part of GNU Binutils.
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
27 #include "libiberty.h"
29 #include "filenames.h"
32 /* A list of symbols to explicitly strip out, or to keep. A linked
33 list is good enough for a small number from the command line, but
34 this will slow things down a lot if many symbols are being
43 /* A list to support redefine_sym. */
48 struct redefine_node
*next
;
51 static void copy_usage
PARAMS ((FILE *, int));
52 static void strip_usage
PARAMS ((FILE *, int));
53 static flagword parse_flags
PARAMS ((const char *));
54 static struct section_list
*find_section_list
PARAMS ((const char *, boolean
));
55 static void setup_section
PARAMS ((bfd
*, asection
*, PTR
));
56 static void copy_section
PARAMS ((bfd
*, asection
*, PTR
));
57 static void get_sections
PARAMS ((bfd
*, asection
*, PTR
));
58 static int compare_section_lma
PARAMS ((const PTR
, const PTR
));
59 static void add_specific_symbol
PARAMS ((const char *, struct symlist
**));
60 static void add_specific_symbols
PARAMS ((const char *, struct symlist
**));
61 static boolean is_specified_symbol
PARAMS ((const char *, struct symlist
*));
62 static boolean is_strip_section
PARAMS ((bfd
*, asection
*));
63 static unsigned int filter_symbols
64 PARAMS ((bfd
*, bfd
*, asymbol
**, asymbol
**, long));
65 static void mark_symbols_used_in_relocations
PARAMS ((bfd
*, asection
*, PTR
));
66 static void filter_bytes
PARAMS ((char *, bfd_size_type
*));
67 static boolean write_debugging_info
PARAMS ((bfd
*, PTR
, long *, asymbol
***));
68 static void copy_object
PARAMS ((bfd
*, bfd
*));
69 static void copy_archive
PARAMS ((bfd
*, bfd
*, const char *));
71 PARAMS ((const char *, const char *, const char *, const char *));
72 static int strip_main
PARAMS ((int, char **));
73 static int copy_main
PARAMS ((int, char **));
74 static const char *lookup_sym_redefinition
PARAMS((const char *));
75 static void redefine_list_append
PARAMS ((const char *, const char *));
77 #define RETURN_NONFATAL(s) {bfd_nonfatal (s); status = 1; return;}
79 static asymbol
**isympp
= NULL
; /* Input symbols */
80 static asymbol
**osympp
= NULL
; /* Output symbols that survive stripping */
82 /* If `copy_byte' >= 0, copy only that byte of every `interleave' bytes. */
83 static int copy_byte
= -1;
84 static int interleave
= 4;
86 static boolean verbose
; /* Print file and target names. */
87 static boolean preserve_dates
; /* Preserve input file timestamp. */
88 static int status
= 0; /* Exit status. */
93 STRIP_NONE
, /* don't strip */
94 STRIP_DEBUG
, /* strip all debugger symbols */
95 STRIP_UNNEEDED
, /* strip unnecessary symbols */
96 STRIP_ALL
/* strip all symbols */
99 /* Which symbols to remove. */
100 static enum strip_action strip_symbols
;
105 LOCALS_START_L
, /* discard locals starting with L */
106 LOCALS_ALL
/* discard all locals */
109 /* Which local symbols to remove. Overrides STRIP_ALL. */
110 static enum locals_action discard_locals
;
112 /* What kind of change to perform. */
120 /* Structure used to hold lists of sections and actions to take. */
123 struct section_list
* next
; /* Next section to change. */
124 const char * name
; /* Section name. */
125 boolean used
; /* Whether this entry was used. */
126 boolean remove
; /* Whether to remove this section. */
127 boolean copy
; /* Whether to copy this section. */
128 enum change_action change_vma
;/* Whether to change or set VMA. */
129 bfd_vma vma_val
; /* Amount to change by or set to. */
130 enum change_action change_lma
;/* Whether to change or set LMA. */
131 bfd_vma lma_val
; /* Amount to change by or set to. */
132 boolean set_flags
; /* Whether to set the section flags. */
133 flagword flags
; /* What to set the section flags to. */
136 static struct section_list
*change_sections
;
137 static boolean sections_removed
;
138 static boolean sections_copied
;
140 /* Changes to the start address. */
141 static bfd_vma change_start
= 0;
142 static boolean set_start_set
= false;
143 static bfd_vma set_start
;
145 /* Changes to section addresses. */
146 static bfd_vma change_section_address
= 0;
148 /* Filling gaps between sections. */
149 static boolean gap_fill_set
= false;
150 static bfd_byte gap_fill
= 0;
152 /* Pad to a given address. */
153 static boolean pad_to_set
= false;
154 static bfd_vma pad_to
;
156 /* List of sections to add. */
160 /* Next section to add. */
161 struct section_add
*next
;
162 /* Name of section to add. */
164 /* Name of file holding section contents. */
165 const char *filename
;
168 /* Contents of file. */
170 /* BFD section, after it has been added. */
174 static struct section_add
*add_sections
;
176 /* Whether to convert debugging information. */
178 static boolean convert_debugging
= false;
180 /* Whether to change the leading character in symbol names. */
182 static boolean change_leading_char
= false;
184 /* Whether to remove the leading character from global symbol names. */
186 static boolean remove_leading_char
= false;
188 /* List of symbols to strip, keep, localize, keep-global, weaken,
191 static struct symlist
*strip_specific_list
= NULL
;
192 static struct symlist
*keep_specific_list
= NULL
;
193 static struct symlist
*localize_specific_list
= NULL
;
194 static struct symlist
*keepglobal_specific_list
= NULL
;
195 static struct symlist
*weaken_specific_list
= NULL
;
196 static struct redefine_node
*redefine_sym_list
= NULL
;
198 /* If this is true, we weaken global symbols (set BSF_WEAK). */
200 static boolean weaken
= false;
202 /* 150 isn't special; it's just an arbitrary non-ASCII char value. */
204 #define OPTION_ADD_SECTION 150
205 #define OPTION_CHANGE_ADDRESSES (OPTION_ADD_SECTION + 1)
206 #define OPTION_CHANGE_LEADING_CHAR (OPTION_CHANGE_ADDRESSES + 1)
207 #define OPTION_CHANGE_START (OPTION_CHANGE_LEADING_CHAR + 1)
208 #define OPTION_CHANGE_SECTION_ADDRESS (OPTION_CHANGE_START + 1)
209 #define OPTION_CHANGE_SECTION_LMA (OPTION_CHANGE_SECTION_ADDRESS + 1)
210 #define OPTION_CHANGE_SECTION_VMA (OPTION_CHANGE_SECTION_LMA + 1)
211 #define OPTION_CHANGE_WARNINGS (OPTION_CHANGE_SECTION_VMA + 1)
212 #define OPTION_DEBUGGING (OPTION_CHANGE_WARNINGS + 1)
213 #define OPTION_GAP_FILL (OPTION_DEBUGGING + 1)
214 #define OPTION_NO_CHANGE_WARNINGS (OPTION_GAP_FILL + 1)
215 #define OPTION_PAD_TO (OPTION_NO_CHANGE_WARNINGS + 1)
216 #define OPTION_REMOVE_LEADING_CHAR (OPTION_PAD_TO + 1)
217 #define OPTION_SET_SECTION_FLAGS (OPTION_REMOVE_LEADING_CHAR + 1)
218 #define OPTION_SET_START (OPTION_SET_SECTION_FLAGS + 1)
219 #define OPTION_STRIP_UNNEEDED (OPTION_SET_START + 1)
220 #define OPTION_WEAKEN (OPTION_STRIP_UNNEEDED + 1)
221 #define OPTION_REDEFINE_SYM (OPTION_WEAKEN + 1)
222 #define OPTION_SREC_LEN (OPTION_REDEFINE_SYM + 1)
223 #define OPTION_SREC_FORCES3 (OPTION_SREC_LEN + 1)
224 #define OPTION_STRIP_SYMBOLS (OPTION_SREC_FORCES3 + 1)
225 #define OPTION_KEEP_SYMBOLS (OPTION_STRIP_SYMBOLS + 1)
226 #define OPTION_LOCALIZE_SYMBOLS (OPTION_KEEP_SYMBOLS + 1)
227 #define OPTION_KEEPGLOBAL_SYMBOLS (OPTION_LOCALIZE_SYMBOLS + 1)
228 #define OPTION_WEAKEN_SYMBOLS (OPTION_KEEPGLOBAL_SYMBOLS + 1)
230 /* Options to handle if running as "strip". */
232 static struct option strip_options
[] =
234 {"discard-all", no_argument
, 0, 'x'},
235 {"discard-locals", no_argument
, 0, 'X'},
236 {"format", required_argument
, 0, 'F'}, /* Obsolete */
237 {"help", no_argument
, 0, 'h'},
238 {"input-format", required_argument
, 0, 'I'}, /* Obsolete */
239 {"input-target", required_argument
, 0, 'I'},
240 {"keep-symbol", required_argument
, 0, 'K'},
241 {"output-format", required_argument
, 0, 'O'}, /* Obsolete */
242 {"output-target", required_argument
, 0, 'O'},
243 {"preserve-dates", no_argument
, 0, 'p'},
244 {"remove-section", required_argument
, 0, 'R'},
245 {"strip-all", no_argument
, 0, 's'},
246 {"strip-debug", no_argument
, 0, 'S'},
247 {"strip-unneeded", no_argument
, 0, OPTION_STRIP_UNNEEDED
},
248 {"strip-symbol", required_argument
, 0, 'N'},
249 {"target", required_argument
, 0, 'F'},
250 {"verbose", no_argument
, 0, 'v'},
251 {"version", no_argument
, 0, 'V'},
252 {0, no_argument
, 0, 0}
255 /* Options to handle if running as "objcopy". */
257 static struct option copy_options
[] =
259 {"add-section", required_argument
, 0, OPTION_ADD_SECTION
},
260 {"adjust-start", required_argument
, 0, OPTION_CHANGE_START
},
261 {"adjust-vma", required_argument
, 0, OPTION_CHANGE_ADDRESSES
},
262 {"adjust-section-vma", required_argument
, 0, OPTION_CHANGE_SECTION_ADDRESS
},
263 {"adjust-warnings", no_argument
, 0, OPTION_CHANGE_WARNINGS
},
264 {"byte", required_argument
, 0, 'b'},
265 {"change-addresses", required_argument
, 0, OPTION_CHANGE_ADDRESSES
},
266 {"change-leading-char", no_argument
, 0, OPTION_CHANGE_LEADING_CHAR
},
267 {"change-section-address", required_argument
, 0, OPTION_CHANGE_SECTION_ADDRESS
},
268 {"change-section-lma", required_argument
, 0, OPTION_CHANGE_SECTION_LMA
},
269 {"change-section-vma", required_argument
, 0, OPTION_CHANGE_SECTION_VMA
},
270 {"change-start", required_argument
, 0, OPTION_CHANGE_START
},
271 {"change-warnings", no_argument
, 0, OPTION_CHANGE_WARNINGS
},
272 {"debugging", no_argument
, 0, OPTION_DEBUGGING
},
273 {"discard-all", no_argument
, 0, 'x'},
274 {"discard-locals", no_argument
, 0, 'X'},
275 {"only-section", required_argument
, 0, 'j'},
276 {"format", required_argument
, 0, 'F'}, /* Obsolete */
277 {"gap-fill", required_argument
, 0, OPTION_GAP_FILL
},
278 {"help", no_argument
, 0, 'h'},
279 {"input-format", required_argument
, 0, 'I'}, /* Obsolete */
280 {"input-target", required_argument
, 0, 'I'},
281 {"interleave", required_argument
, 0, 'i'},
282 {"keep-symbol", required_argument
, 0, 'K'},
283 {"no-adjust-warnings", no_argument
, 0, OPTION_NO_CHANGE_WARNINGS
},
284 {"no-change-warnings", no_argument
, 0, OPTION_NO_CHANGE_WARNINGS
},
285 {"output-format", required_argument
, 0, 'O'}, /* Obsolete */
286 {"output-target", required_argument
, 0, 'O'},
287 {"pad-to", required_argument
, 0, OPTION_PAD_TO
},
288 {"preserve-dates", no_argument
, 0, 'p'},
289 {"localize-symbol", required_argument
, 0, 'L'},
290 {"keep-global-symbol", required_argument
, 0, 'G'},
291 {"remove-leading-char", no_argument
, 0, OPTION_REMOVE_LEADING_CHAR
},
292 {"remove-section", required_argument
, 0, 'R'},
293 {"set-section-flags", required_argument
, 0, OPTION_SET_SECTION_FLAGS
},
294 {"set-start", required_argument
, 0, OPTION_SET_START
},
295 {"strip-all", no_argument
, 0, 'S'},
296 {"strip-debug", no_argument
, 0, 'g'},
297 {"strip-unneeded", no_argument
, 0, OPTION_STRIP_UNNEEDED
},
298 {"strip-symbol", required_argument
, 0, 'N'},
299 {"target", required_argument
, 0, 'F'},
300 {"verbose", no_argument
, 0, 'v'},
301 {"version", no_argument
, 0, 'V'},
302 {"weaken", no_argument
, 0, OPTION_WEAKEN
},
303 {"weaken-symbol", required_argument
, 0, 'W'},
304 {"redefine-sym", required_argument
, 0, OPTION_REDEFINE_SYM
},
305 {"srec-len", required_argument
, 0, OPTION_SREC_LEN
},
306 {"srec-forceS3", no_argument
, 0, OPTION_SREC_FORCES3
},
307 {"keep-symbols", required_argument
, 0, OPTION_KEEP_SYMBOLS
},
308 {"strip-symbols", required_argument
, 0, OPTION_STRIP_SYMBOLS
},
309 {"keep-global-symbols", required_argument
, 0, OPTION_KEEPGLOBAL_SYMBOLS
},
310 {"localize-symbols", required_argument
, 0, OPTION_LOCALIZE_SYMBOLS
},
311 {"weaken-symbols", required_argument
, 0, OPTION_WEAKEN_SYMBOLS
},
312 {0, no_argument
, 0, 0}
316 extern char *program_name
;
318 /* This flag distinguishes between strip and objcopy:
319 1 means this is 'strip'; 0 means this is 'objcopy'.
320 -1 means if we should use argv[0] to decide. */
323 /* The maximum length of an S record. This variable is declared in srec.c
324 and can be modified by the --srec-len parameter. */
325 extern unsigned int Chunk
;
327 /* Restrict the generation of Srecords to type S3 only.
328 This variable is declare in bfd/srec.c and can be toggled
329 on by the --srec-forceS3 command line switch. */
330 extern boolean S3Forced
;
333 copy_usage (stream
, exit_status
)
337 fprintf (stream
, _("Usage: %s <switches> in-file [out-file]\n"), program_name
);
338 fprintf (stream
, _(" The switches are:\n"));
339 fprintf (stream
, _("\
340 -I --input-target <bfdname> Assume input file is in format <bfdname>\n\
341 -O --output-target <bfdname> Create an output file in format <bfdname>\n\
342 -F --target <bfdname> Set both input and output format to <bfdname>\n\
343 --debugging Convert debugging information, if possible\n\
344 -p --preserve-dates Copy modified/access timestamps to the output\n\
345 -j --only-section <name> Only copy section <name> into the output\n\
346 -R --remove-section <name> Remove section <name> from the output\n\
347 -S --strip-all Remove all symbol and relocation information\n\
348 -g --strip-debug Remove all debugging symbols\n\
349 --strip-unneeded Remove all symbols not needed by relocations\n\
350 -N --strip-symbol <name> Do not copy symbol <name>\n\
351 -K --keep-symbol <name> Only copy symbol <name>\n\
352 -L --localize-symbol <name> Force symbol <name> to be marked as a local\n\
353 -G --keep-global-symbol <name> Localize all symbols except <name>\n\
354 -W --weaken-symbol <name> Force symbol <name> to be marked as a weak\n\
355 --weaken Force all global symbols to be marked as weak\n\
356 -x --discard-all Remove all non-global symbols\n\
357 -X --discard-locals Remove any compiler-generated symbols\n\
358 -i --interleave <number> Only copy one out of every <number> bytes\n\
359 -b --byte <num> Select byte <num> in every interleaved block\n\
360 --gap-fill <val> Fill gaps between sections with <val>\n\
361 --pad-to <addr> Pad the last section up to address <addr>\n\
362 --set-start <addr> Set the start address to <addr>\n\
363 {--change-start|--adjust-start} <incr>\n\
364 Add <incr> to the start address\n\
365 {--change-addresses|--adjust-vma} <incr>\n\
366 Add <incr> to LMA, VMA and start addresses\n\
367 {--change-section-address|--adjust-section-vma} <name>{=|+|-}<val>\n\
368 Change LMA and VMA of section <name> by <val>\n\
369 --change-section-lma <name>{=|+|-}<val>\n\
370 Change the LMA of section <name> by <val>\n\
371 --change-section-vma <name>{=|+|-}<val>\n\
372 Change the VMA of section <name> by <val>\n\
373 {--[no-]change-warnings|--[no-]adjust-warnings}\n\
374 Warn if a named section does not exist\n\
375 --set-section-flags <name>=<flags>\n\
376 Set section <name>'s properties to <flags>\n\
377 --add-section <name>=<file> Add section <name> found in <file> to output\n\
378 --change-leading-char Force output format's leading character style\n\
379 --remove-leading-char Remove leading character from global symbols\n\
380 --redefine-sym <old>=<new> Redefine symbol name <old> to <new>\n\
381 --srec-len <number> Restrict the length of generated Srecords\n\
382 --srec-forceS3 Restrict the type of generated Srecords to S3\n\
383 --strip-symbols <file> -N for all symbols listed in <file>\n\
384 --keep-symbols <file> -K for all symbols listed in <file>\n\
385 --localize-symbols <file> -L for all symbols listed in <file>\n\
386 --keep-global-symbols <file> -G for all symbols listed in <file>\n\
387 --weaken-symbols <file> -W for all symbols listed in <file>\n\
388 -v --verbose List all object files modified\n\
389 -V --version Display this program's version number\n\
390 -h --help Display this output\n\
392 list_supported_targets (program_name
, stream
);
393 if (exit_status
== 0)
394 fprintf (stream
, _("Report bugs to %s\n"), REPORT_BUGS_TO
);
399 strip_usage (stream
, exit_status
)
403 fprintf (stream
, _("Usage: %s <switches> in-file(s)\n"), program_name
);
404 fprintf (stream
, _(" The switches are:\n"));
405 fprintf (stream
, _("\
406 -I --input-target <bfdname> Assume input file is in format <bfdname>\n\
407 -O --output-target <bfdname> Create an output file in format <bfdname>\n\
408 -F --target <bfdname> Set both input and output format to <bfdname>\n\
409 -p --preserve-dates Copy modified/access timestamps to the output\n\
410 -R --remove-section <name> Remove section <name> from the output\n\
411 -s --strip-all Remove all symbol and relocation information\n\
412 -g -S --strip-debug Remove all debugging symbols\n\
413 --strip-unneeded Remove all symbols not needed by relocations\n\
414 -N --strip-symbol <name> Do not copy symbol <name>\n\
415 -K --keep-symbol <name> Only copy symbol <name>\n\
416 -x --discard-all Remove all non-global symbols\n\
417 -X --discard-locals Remove any compiler-generated symbols\n\
418 -v --verbose List all object files modified\n\
419 -V --version Display this program's version number\n\
420 -h --help Display this output\n\
421 -o <file> Place stripped output into <file>\n\
424 list_supported_targets (program_name
, stream
);
425 if (exit_status
== 0)
426 fprintf (stream
, _("Report bugs to %s\n"), REPORT_BUGS_TO
);
430 /* Parse section flags into a flagword, with a fatal error if the
431 string can't be parsed. */
445 snext
= strchr (s
, ',');
455 #define PARSE_FLAG(fname,fval) \
456 else if (strncasecmp (fname, s, len) == 0) ret |= fval
457 PARSE_FLAG ("alloc", SEC_ALLOC
);
458 PARSE_FLAG ("load", SEC_LOAD
);
459 PARSE_FLAG ("noload", SEC_NEVER_LOAD
);
460 PARSE_FLAG ("readonly", SEC_READONLY
);
461 PARSE_FLAG ("debug", SEC_DEBUGGING
);
462 PARSE_FLAG ("code", SEC_CODE
);
463 PARSE_FLAG ("data", SEC_DATA
);
464 PARSE_FLAG ("rom", SEC_ROM
);
465 PARSE_FLAG ("share", SEC_SHARED
);
466 PARSE_FLAG ("contents", SEC_HAS_CONTENTS
);
472 copy
= xmalloc (len
+ 1);
473 strncpy (copy
, s
, len
);
475 non_fatal (_("unrecognized section flag `%s'"), copy
);
476 fatal (_("supported flags: %s"),
477 "alloc, load, noload, readonly, debug, code, data, rom, share, contents");
487 /* Find and optionally add an entry in the change_sections list. */
489 static struct section_list
*
490 find_section_list (name
, add
)
494 register struct section_list
*p
;
496 for (p
= change_sections
; p
!= NULL
; p
= p
->next
)
497 if (strcmp (p
->name
, name
) == 0)
503 p
= (struct section_list
*) xmalloc (sizeof (struct section_list
));
508 p
->change_vma
= CHANGE_IGNORE
;
509 p
->change_lma
= CHANGE_IGNORE
;
512 p
->set_flags
= false;
515 p
->next
= change_sections
;
521 /* Add a symbol to strip_specific_list. */
524 add_specific_symbol (name
, list
)
526 struct symlist
**list
;
528 struct symlist
*tmp_list
;
530 tmp_list
= (struct symlist
*) xmalloc (sizeof (struct symlist
));
531 tmp_list
->name
= name
;
532 tmp_list
->next
= *list
;
536 /* Add symbols listed in `filename' to strip_specific_list. */
538 #define IS_WHITESPACE(c) ((c) == ' ' || (c) == '\t')
539 #define IS_LINE_TERMINATOR(c) ((c) == '\n' || (c) == '\r' || (c) == '\0')
542 add_specific_symbols (filename
, list
)
543 const char *filename
;
544 struct symlist
**list
;
550 unsigned int line_count
;
552 if (stat (filename
, & st
) < 0)
553 fatal (_("cannot stat: %s: %s"), filename
, strerror (errno
));
557 buffer
= (char *) xmalloc (st
.st_size
+ 2);
558 f
= fopen (filename
, FOPEN_RT
);
560 fatal (_("cannot open: %s: %s"), filename
, strerror (errno
));
562 if (fread (buffer
, 1, st
.st_size
, f
) == 0 || ferror (f
))
563 fatal (_("%s: fread failed"), filename
);
566 buffer
[st
.st_size
] = '\n';
567 buffer
[st
.st_size
+ 1] = '\0';
571 for (line
= buffer
; * line
!= '\0'; line
++)
576 int finished
= false;
578 for (eol
= line
;; eol
++)
584 /* Cope with \n\r. */
592 /* Cope with \r\n. */
603 /* Line comment, Terminate the line here, in case a
604 name is present and then allow the rest of the
605 loop to find the real end of the line. */
617 /* A name may now exist somewhere between 'line' and 'eol'.
618 Strip off leading whitespace and trailing whitespace,
619 then add it to the list. */
620 for (name
= line
; IS_WHITESPACE (* name
); name
++)
622 for (name_end
= name
;
623 (! IS_WHITESPACE (* name_end
))
624 && (! IS_LINE_TERMINATOR (* name_end
));
628 if (! IS_LINE_TERMINATOR (* name_end
))
632 for (extra
= name_end
+ 1; IS_WHITESPACE (* extra
); extra
++)
635 if (! IS_LINE_TERMINATOR (* extra
))
636 non_fatal (_("Ignoring rubbish found on line %d of %s"),
637 line_count
, filename
);
643 add_specific_symbol (name
, list
);
645 /* Advance line pointer to end of line. The 'eol ++' in the for
646 loop above will then advance us to the start of the next line. */
652 /* See whether a symbol should be stripped or kept based on
653 strip_specific_list and keep_symbols. */
656 is_specified_symbol (name
, list
)
658 struct symlist
*list
;
660 struct symlist
*tmp_list
;
662 for (tmp_list
= list
; tmp_list
; tmp_list
= tmp_list
->next
)
664 if (strcmp (name
, tmp_list
->name
) == 0)
670 /* See if a section is being removed. */
673 is_strip_section (abfd
, sec
)
674 bfd
*abfd ATTRIBUTE_UNUSED
;
677 struct section_list
*p
;
679 if ((bfd_get_section_flags (abfd
, sec
) & SEC_DEBUGGING
) != 0
680 && (strip_symbols
== STRIP_DEBUG
681 || strip_symbols
== STRIP_UNNEEDED
682 || strip_symbols
== STRIP_ALL
683 || discard_locals
== LOCALS_ALL
684 || convert_debugging
))
687 if (! sections_removed
&& ! sections_copied
)
690 p
= find_section_list (bfd_get_section_name (abfd
, sec
), false);
691 if (sections_removed
&& p
!= NULL
&& p
->remove
)
693 if (sections_copied
&& (p
== NULL
|| ! p
->copy
))
698 /* Choose which symbol entries to copy; put the result in OSYMS.
699 We don't copy in place, because that confuses the relocs.
700 Return the number of symbols to print. */
703 filter_symbols (abfd
, obfd
, osyms
, isyms
, symcount
)
706 asymbol
**osyms
, **isyms
;
709 register asymbol
**from
= isyms
, **to
= osyms
;
710 long src_count
= 0, dst_count
= 0;
711 int relocatable
= (abfd
->flags
& (HAS_RELOC
| EXEC_P
| DYNAMIC
))
714 for (; src_count
< symcount
; src_count
++)
716 asymbol
*sym
= from
[src_count
];
717 flagword flags
= sym
->flags
;
718 const char *name
= bfd_asymbol_name (sym
);
721 if (redefine_sym_list
)
723 const char *old_name
, *new_name
;
725 old_name
= bfd_asymbol_name (sym
);
726 new_name
= lookup_sym_redefinition (old_name
);
727 name
= bfd_asymbol_name (sym
) = new_name
;
730 if (change_leading_char
731 && (bfd_get_symbol_leading_char (abfd
)
732 != bfd_get_symbol_leading_char (obfd
))
733 && (bfd_get_symbol_leading_char (abfd
) == '\0'
734 || (name
[0] == bfd_get_symbol_leading_char (abfd
))))
736 if (bfd_get_symbol_leading_char (obfd
) == '\0')
737 name
= bfd_asymbol_name (sym
) = name
+ 1;
742 n
= xmalloc (strlen (name
) + 2);
743 n
[0] = bfd_get_symbol_leading_char (obfd
);
744 if (bfd_get_symbol_leading_char (abfd
) == '\0')
745 strcpy (n
+ 1, name
);
747 strcpy (n
+ 1, name
+ 1);
748 name
= bfd_asymbol_name (sym
) = n
;
752 if (remove_leading_char
753 && ((flags
& BSF_GLOBAL
) != 0
754 || (flags
& BSF_WEAK
) != 0
755 || bfd_is_und_section (bfd_get_section (sym
))
756 || bfd_is_com_section (bfd_get_section (sym
)))
757 && name
[0] == bfd_get_symbol_leading_char (abfd
))
758 name
= bfd_asymbol_name (sym
) = name
+ 1;
760 if (strip_symbols
== STRIP_ALL
)
762 else if ((flags
& BSF_KEEP
) != 0 /* Used in relocation. */
763 || ((flags
& BSF_SECTION_SYM
) != 0
764 && ((*bfd_get_section (sym
)->symbol_ptr_ptr
)->flags
767 else if (relocatable
/* Relocatable file. */
768 && (flags
& (BSF_GLOBAL
| BSF_WEAK
)) != 0)
770 else if (bfd_decode_symclass (sym
) == 'I')
771 /* Global symbols in $idata sections need to be retained
772 even if relocatable is false. External users of the
773 library containing the $idata section may reference these
776 else if ((flags
& BSF_GLOBAL
) != 0 /* Global symbol. */
777 || (flags
& BSF_WEAK
) != 0
778 || bfd_is_und_section (bfd_get_section (sym
))
779 || bfd_is_com_section (bfd_get_section (sym
)))
780 keep
= strip_symbols
!= STRIP_UNNEEDED
;
781 else if ((flags
& BSF_DEBUGGING
) != 0) /* Debugging symbol. */
782 keep
= (strip_symbols
!= STRIP_DEBUG
783 && strip_symbols
!= STRIP_UNNEEDED
784 && ! convert_debugging
);
785 else /* Local symbol. */
786 keep
= (strip_symbols
!= STRIP_UNNEEDED
787 && (discard_locals
!= LOCALS_ALL
788 && (discard_locals
!= LOCALS_START_L
789 || ! bfd_is_local_label (abfd
, sym
))));
791 if (keep
&& is_specified_symbol (name
, strip_specific_list
))
793 if (!keep
&& is_specified_symbol (name
, keep_specific_list
))
795 if (keep
&& is_strip_section (abfd
, bfd_get_section (sym
)))
798 if (keep
&& (flags
& BSF_GLOBAL
) != 0
799 && (weaken
|| is_specified_symbol (name
, weaken_specific_list
)))
801 sym
->flags
&=~ BSF_GLOBAL
;
802 sym
->flags
|= BSF_WEAK
;
804 if (keep
&& (flags
& (BSF_GLOBAL
| BSF_WEAK
))
805 && (is_specified_symbol (name
, localize_specific_list
)
806 || (keepglobal_specific_list
!= NULL
807 && ! is_specified_symbol (name
, keepglobal_specific_list
))))
809 sym
->flags
&= ~(BSF_GLOBAL
| BSF_WEAK
);
810 sym
->flags
|= BSF_LOCAL
;
814 to
[dst_count
++] = sym
;
817 to
[dst_count
] = NULL
;
823 lookup_sym_redefinition (source
)
827 struct redefine_node
*list
;
831 for (list
= redefine_sym_list
; list
!= NULL
; list
= list
->next
)
833 if (strcmp (source
, list
->source
) == 0)
835 result
= list
->target
;
842 /* Add a node to a symbol redefine list */
845 redefine_list_append (source
, target
)
849 struct redefine_node
**p
;
850 struct redefine_node
*list
;
851 struct redefine_node
*new_node
;
853 for (p
= &redefine_sym_list
; (list
= *p
) != NULL
; p
= &list
->next
)
855 if (strcmp (source
, list
->source
) == 0)
857 fatal (_("%s: Multiple redefinition of symbol \"%s\""),
862 if (strcmp (target
, list
->target
) == 0)
864 fatal (_("%s: Symbol \"%s\" is target of more than one redefinition"),
870 new_node
= (struct redefine_node
*) xmalloc (sizeof (struct redefine_node
));
872 new_node
->source
= strdup (source
);
873 new_node
->target
= strdup (target
);
874 new_node
->next
= NULL
;
880 /* Keep only every `copy_byte'th byte in MEMHUNK, which is *SIZE bytes long.
884 filter_bytes (memhunk
, size
)
888 char *from
= memhunk
+ copy_byte
, *to
= memhunk
, *end
= memhunk
+ *size
;
890 for (; from
< end
; from
+= interleave
)
892 if (*size
% interleave
> (bfd_size_type
) copy_byte
)
893 *size
= (*size
/ interleave
) + 1;
898 /* Copy object file IBFD onto OBFD. */
901 copy_object (ibfd
, obfd
)
907 asection
**osections
= NULL
;
908 bfd_size_type
*gaps
= NULL
;
909 bfd_size_type max_gap
= 0;
913 if (ibfd
->xvec
->byteorder
!= obfd
->xvec
->byteorder
914 && ibfd
->xvec
->byteorder
!= BFD_ENDIAN_UNKNOWN
915 && obfd
->xvec
->byteorder
!= BFD_ENDIAN_UNKNOWN
)
917 fatal (_("Unable to change endianness of input file(s)"));
921 if (!bfd_set_format (obfd
, bfd_get_format (ibfd
)))
922 RETURN_NONFATAL (bfd_get_filename (obfd
));
925 printf (_("copy from %s(%s) to %s(%s)\n"),
926 bfd_get_filename (ibfd
), bfd_get_target (ibfd
),
927 bfd_get_filename (obfd
), bfd_get_target (obfd
));
932 start
= bfd_get_start_address (ibfd
);
933 start
+= change_start
;
935 if (!bfd_set_start_address (obfd
, start
)
936 || !bfd_set_file_flags (obfd
,
937 (bfd_get_file_flags (ibfd
)
938 & bfd_applicable_file_flags (obfd
))))
939 RETURN_NONFATAL (bfd_get_filename (ibfd
));
941 /* Copy architecture of input file to output file */
942 if (!bfd_set_arch_mach (obfd
, bfd_get_arch (ibfd
),
943 bfd_get_mach (ibfd
)))
944 non_fatal (_("Warning: Output file cannot represent architecture %s"),
945 bfd_printable_arch_mach (bfd_get_arch (ibfd
),
946 bfd_get_mach (ibfd
)));
948 if (!bfd_set_format (obfd
, bfd_get_format (ibfd
)))
949 RETURN_NONFATAL (bfd_get_filename (ibfd
));
954 if (osympp
!= isympp
)
957 /* BFD mandates that all output sections be created and sizes set before
958 any output is done. Thus, we traverse all sections multiple times. */
959 bfd_map_over_sections (ibfd
, setup_section
, (void *) obfd
);
961 if (add_sections
!= NULL
)
963 struct section_add
*padd
;
964 struct section_list
*pset
;
966 for (padd
= add_sections
; padd
!= NULL
; padd
= padd
->next
)
968 padd
->section
= bfd_make_section (obfd
, padd
->name
);
969 if (padd
->section
== NULL
)
971 non_fatal (_("can't create section `%s': %s"),
972 padd
->name
, bfd_errmsg (bfd_get_error ()));
980 if (! bfd_set_section_size (obfd
, padd
->section
, padd
->size
))
981 RETURN_NONFATAL (bfd_get_filename (obfd
));
983 pset
= find_section_list (padd
->name
, false);
987 if (pset
!= NULL
&& pset
->set_flags
)
988 flags
= pset
->flags
| SEC_HAS_CONTENTS
;
990 flags
= SEC_HAS_CONTENTS
| SEC_READONLY
| SEC_DATA
;
992 if (! bfd_set_section_flags (obfd
, padd
->section
, flags
))
993 RETURN_NONFATAL (bfd_get_filename (obfd
));
997 if (pset
->change_vma
!= CHANGE_IGNORE
)
998 if (! bfd_set_section_vma (obfd
, padd
->section
, pset
->vma_val
))
999 RETURN_NONFATAL (bfd_get_filename (obfd
));
1001 if (pset
->change_lma
!= CHANGE_IGNORE
)
1003 padd
->section
->lma
= pset
->lma_val
;
1005 if (! bfd_set_section_alignment
1006 (obfd
, padd
->section
,
1007 bfd_section_alignment (obfd
, padd
->section
)))
1008 RETURN_NONFATAL (bfd_get_filename (obfd
));
1015 if (gap_fill_set
|| pad_to_set
)
1020 /* We must fill in gaps between the sections and/or we must pad
1021 the last section to a specified address. We do this by
1022 grabbing a list of the sections, sorting them by VMA, and
1023 increasing the section sizes as required to fill the gaps.
1024 We write out the gap contents below. */
1026 c
= bfd_count_sections (obfd
);
1027 osections
= (asection
**) xmalloc (c
* sizeof (asection
*));
1029 bfd_map_over_sections (obfd
, get_sections
, (void *) &set
);
1031 qsort (osections
, c
, sizeof (asection
*), compare_section_lma
);
1033 gaps
= (bfd_size_type
*) xmalloc (c
* sizeof (bfd_size_type
));
1034 memset (gaps
, 0, c
* sizeof (bfd_size_type
));
1038 for (i
= 0; i
< c
- 1; i
++)
1042 bfd_vma gap_start
, gap_stop
;
1044 flags
= bfd_get_section_flags (obfd
, osections
[i
]);
1045 if ((flags
& SEC_HAS_CONTENTS
) == 0
1046 || (flags
& SEC_LOAD
) == 0)
1049 size
= bfd_section_size (obfd
, osections
[i
]);
1050 gap_start
= bfd_section_lma (obfd
, osections
[i
]) + size
;
1051 gap_stop
= bfd_section_lma (obfd
, osections
[i
+ 1]);
1052 if (gap_start
< gap_stop
)
1054 if (! bfd_set_section_size (obfd
, osections
[i
],
1055 size
+ (gap_stop
- gap_start
)))
1057 non_fatal (_("Can't fill gap after %s: %s"),
1058 bfd_get_section_name (obfd
, osections
[i
]),
1059 bfd_errmsg (bfd_get_error ()));
1063 gaps
[i
] = gap_stop
- gap_start
;
1064 if (max_gap
< gap_stop
- gap_start
)
1065 max_gap
= gap_stop
- gap_start
;
1075 lma
= bfd_section_lma (obfd
, osections
[c
- 1]);
1076 size
= bfd_section_size (obfd
, osections
[c
- 1]);
1077 if (lma
+ size
< pad_to
)
1079 if (! bfd_set_section_size (obfd
, osections
[c
- 1],
1082 non_fatal (_("Can't add padding to %s: %s"),
1083 bfd_get_section_name (obfd
, osections
[c
- 1]),
1084 bfd_errmsg (bfd_get_error ()));
1089 gaps
[c
- 1] = pad_to
- (lma
+ size
);
1090 if (max_gap
< pad_to
- (lma
+ size
))
1091 max_gap
= pad_to
- (lma
+ size
);
1097 /* Symbol filtering must happen after the output sections have
1098 been created, but before their contents are set. */
1100 symsize
= bfd_get_symtab_upper_bound (ibfd
);
1102 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1104 osympp
= isympp
= (asymbol
**) xmalloc (symsize
);
1105 symcount
= bfd_canonicalize_symtab (ibfd
, isympp
);
1107 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1109 if (convert_debugging
)
1110 dhandle
= read_debugging_info (ibfd
, isympp
, symcount
);
1112 if (strip_symbols
== STRIP_DEBUG
1113 || strip_symbols
== STRIP_ALL
1114 || strip_symbols
== STRIP_UNNEEDED
1115 || discard_locals
!= LOCALS_UNDEF
1116 || strip_specific_list
!= NULL
1117 || keep_specific_list
!= NULL
1118 || localize_specific_list
!= NULL
1119 || keepglobal_specific_list
!= NULL
1120 || weaken_specific_list
!= NULL
1123 || convert_debugging
1124 || change_leading_char
1125 || remove_leading_char
1126 || redefine_sym_list
1129 /* Mark symbols used in output relocations so that they
1130 are kept, even if they are local labels or static symbols.
1132 Note we iterate over the input sections examining their
1133 relocations since the relocations for the output sections
1134 haven't been set yet. mark_symbols_used_in_relocations will
1135 ignore input sections which have no corresponding output
1137 if (strip_symbols
!= STRIP_ALL
)
1138 bfd_map_over_sections (ibfd
,
1139 mark_symbols_used_in_relocations
,
1141 osympp
= (asymbol
**) xmalloc ((symcount
+ 1) * sizeof (asymbol
*));
1142 symcount
= filter_symbols (ibfd
, obfd
, osympp
, isympp
, symcount
);
1145 if (convert_debugging
&& dhandle
!= NULL
)
1147 if (! write_debugging_info (obfd
, dhandle
, &symcount
, &osympp
))
1154 bfd_set_symtab (obfd
, osympp
, symcount
);
1156 /* This has to happen after the symbol table has been set. */
1157 bfd_map_over_sections (ibfd
, copy_section
, (void *) obfd
);
1159 if (add_sections
!= NULL
)
1161 struct section_add
*padd
;
1163 for (padd
= add_sections
; padd
!= NULL
; padd
= padd
->next
)
1165 if (! bfd_set_section_contents (obfd
, padd
->section
,
1166 (PTR
) padd
->contents
,
1168 (bfd_size_type
) padd
->size
))
1169 RETURN_NONFATAL (bfd_get_filename (obfd
));
1173 if (gap_fill_set
|| pad_to_set
)
1178 /* Fill in the gaps. */
1182 buf
= (bfd_byte
*) xmalloc (max_gap
);
1183 memset (buf
, gap_fill
, (size_t) max_gap
);
1185 c
= bfd_count_sections (obfd
);
1186 for (i
= 0; i
< c
; i
++)
1194 off
= bfd_section_size (obfd
, osections
[i
]) - left
;
1204 if (! bfd_set_section_contents (obfd
, osections
[i
], buf
,
1206 RETURN_NONFATAL (bfd_get_filename (obfd
));
1215 /* Allow the BFD backend to copy any private data it understands
1216 from the input BFD to the output BFD. This is done last to
1217 permit the routine to look at the filtered symbol table, which is
1218 important for the ECOFF code at least. */
1219 if (!bfd_copy_private_bfd_data (ibfd
, obfd
))
1221 non_fatal (_("%s: error copying private BFD data: %s"),
1222 bfd_get_filename (obfd
),
1223 bfd_errmsg (bfd_get_error ()));
1229 /* Read each archive element in turn from IBFD, copy the
1230 contents to temp file, and keep the temp file handle. */
1233 copy_archive (ibfd
, obfd
, output_target
)
1236 const char *output_target
;
1240 struct name_list
*next
;
1244 bfd
**ptr
= &obfd
->archive_head
;
1246 char *dir
= make_tempname (bfd_get_filename (obfd
));
1248 /* Make a temp directory to hold the contents. */
1249 #if defined (_WIN32) && !defined (__CYGWIN32__)
1250 if (mkdir (dir
) != 0)
1252 if (mkdir (dir
, 0700) != 0)
1255 fatal (_("cannot mkdir %s for archive copying (error: %s)"),
1256 dir
, strerror (errno
));
1258 obfd
->has_armap
= ibfd
->has_armap
;
1262 this_element
= bfd_openr_next_archived_file (ibfd
, NULL
);
1263 while (!status
&& this_element
!= (bfd
*) NULL
)
1265 /* Create an output file for this member. */
1266 char *output_name
= concat (dir
, "/", bfd_get_filename (this_element
),
1268 bfd
*output_bfd
= bfd_openw (output_name
, output_target
);
1271 int stat_status
= 0;
1275 stat_status
= bfd_stat_arch_elt (this_element
, &buf
);
1276 if (stat_status
!= 0)
1277 non_fatal (_("internal stat error on %s"),
1278 bfd_get_filename (this_element
));
1281 l
= (struct name_list
*) xmalloc (sizeof (struct name_list
));
1282 l
->name
= output_name
;
1286 if (output_bfd
== (bfd
*) NULL
)
1287 RETURN_NONFATAL (output_name
);
1289 if (!bfd_set_format (obfd
, bfd_get_format (ibfd
)))
1290 RETURN_NONFATAL (bfd_get_filename (obfd
));
1292 if (bfd_check_format (this_element
, bfd_object
) == true)
1293 copy_object (this_element
, output_bfd
);
1295 if (!bfd_close (output_bfd
))
1297 bfd_nonfatal (bfd_get_filename (output_bfd
));
1298 /* Error in new object file. Don't change archive. */
1302 if (preserve_dates
&& stat_status
== 0)
1303 set_times (output_name
, &buf
);
1305 /* Open the newly output file and attach to our list. */
1306 output_bfd
= bfd_openr (output_name
, output_target
);
1308 l
->obfd
= output_bfd
;
1311 ptr
= &output_bfd
->next
;
1313 last_element
= this_element
;
1315 this_element
= bfd_openr_next_archived_file (ibfd
, last_element
);
1317 bfd_close (last_element
);
1319 *ptr
= (bfd
*) NULL
;
1321 if (!bfd_close (obfd
))
1322 RETURN_NONFATAL (bfd_get_filename (obfd
));
1324 if (!bfd_close (ibfd
))
1325 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1327 /* Delete all the files that we opened. */
1328 for (l
= list
; l
!= NULL
; l
= l
->next
)
1330 bfd_close (l
->obfd
);
1336 /* The top-level control. */
1339 copy_file (input_filename
, output_filename
, input_target
, output_target
)
1340 const char *input_filename
;
1341 const char *output_filename
;
1342 const char *input_target
;
1343 const char *output_target
;
1348 /* To allow us to do "strip *" without dying on the first
1349 non-object file, failures are nonfatal. */
1351 ibfd
= bfd_openr (input_filename
, input_target
);
1353 RETURN_NONFATAL (input_filename
);
1355 if (bfd_check_format (ibfd
, bfd_archive
))
1359 /* bfd_get_target does not return the correct value until
1360 bfd_check_format succeeds. */
1361 if (output_target
== NULL
)
1362 output_target
= bfd_get_target (ibfd
);
1364 obfd
= bfd_openw (output_filename
, output_target
);
1366 RETURN_NONFATAL (output_filename
);
1368 copy_archive (ibfd
, obfd
, output_target
);
1370 else if (bfd_check_format_matches (ibfd
, bfd_object
, &matching
))
1374 /* bfd_get_target does not return the correct value until
1375 bfd_check_format succeeds. */
1376 if (output_target
== NULL
)
1377 output_target
= bfd_get_target (ibfd
);
1379 obfd
= bfd_openw (output_filename
, output_target
);
1381 RETURN_NONFATAL (output_filename
);
1383 copy_object (ibfd
, obfd
);
1385 if (!bfd_close (obfd
))
1386 RETURN_NONFATAL (output_filename
);
1388 if (!bfd_close (ibfd
))
1389 RETURN_NONFATAL (input_filename
);
1393 bfd_nonfatal (input_filename
);
1395 if (bfd_get_error () == bfd_error_file_ambiguously_recognized
)
1397 list_matching_formats (matching
);
1405 /* Create a section in OBFD with the same name and attributes
1406 as ISECTION in IBFD. */
1409 setup_section (ibfd
, isection
, obfdarg
)
1414 bfd
*obfd
= (bfd
*) obfdarg
;
1415 struct section_list
*p
;
1423 if ((bfd_get_section_flags (ibfd
, isection
) & SEC_DEBUGGING
) != 0
1424 && (strip_symbols
== STRIP_DEBUG
1425 || strip_symbols
== STRIP_UNNEEDED
1426 || strip_symbols
== STRIP_ALL
1427 || discard_locals
== LOCALS_ALL
1428 || convert_debugging
))
1431 p
= find_section_list (bfd_section_name (ibfd
, isection
), false);
1435 if (sections_removed
&& p
!= NULL
&& p
->remove
)
1437 if (sections_copied
&& (p
== NULL
|| ! p
->copy
))
1440 osection
= bfd_make_section_anyway (obfd
, bfd_section_name (ibfd
, isection
));
1442 if (osection
== NULL
)
1448 size
= bfd_section_size (ibfd
, isection
);
1450 size
= (size
+ interleave
- 1) / interleave
;
1451 if (! bfd_set_section_size (obfd
, osection
, size
))
1457 vma
= bfd_section_vma (ibfd
, isection
);
1458 if (p
!= NULL
&& p
->change_vma
== CHANGE_MODIFY
)
1460 else if (p
!= NULL
&& p
->change_vma
== CHANGE_SET
)
1463 vma
+= change_section_address
;
1465 if (! bfd_set_section_vma (obfd
, osection
, vma
))
1471 lma
= isection
->lma
;
1472 if ((p
!= NULL
) && p
->change_lma
!= CHANGE_IGNORE
)
1474 if (p
->change_lma
== CHANGE_MODIFY
)
1476 else if (p
->change_lma
== CHANGE_SET
)
1482 lma
+= change_section_address
;
1484 osection
->lma
= lma
;
1486 /* FIXME: This is probably not enough. If we change the LMA we
1487 may have to recompute the header for the file as well. */
1488 if (bfd_set_section_alignment (obfd
,
1490 bfd_section_alignment (ibfd
, isection
))
1493 err
= _("alignment");
1497 flags
= bfd_get_section_flags (ibfd
, isection
);
1498 if (p
!= NULL
&& p
->set_flags
)
1499 flags
= p
->flags
| (flags
& SEC_HAS_CONTENTS
);
1500 if (!bfd_set_section_flags (obfd
, osection
, flags
))
1506 /* This used to be mangle_section; we do here to avoid using
1507 bfd_get_section_by_name since some formats allow multiple
1508 sections with the same name. */
1509 isection
->output_section
= osection
;
1510 isection
->output_offset
= 0;
1512 /* Allow the BFD backend to copy any private data it understands
1513 from the input section to the output section. */
1514 if (!bfd_copy_private_section_data (ibfd
, isection
, obfd
, osection
))
1516 err
= _("private data");
1524 non_fatal (_("%s: section `%s': error in %s: %s"),
1525 bfd_get_filename (ibfd
),
1526 bfd_section_name (ibfd
, isection
),
1527 err
, bfd_errmsg (bfd_get_error ()));
1531 /* Copy the data of input section ISECTION of IBFD
1532 to an output section with the same name in OBFD.
1533 If stripping then don't copy any relocation info. */
1536 copy_section (ibfd
, isection
, obfdarg
)
1541 bfd
*obfd
= (bfd
*) obfdarg
;
1542 struct section_list
*p
;
1549 /* If we have already failed earlier on, do not keep on generating
1554 if ((bfd_get_section_flags (ibfd
, isection
) & SEC_DEBUGGING
) != 0
1555 && (strip_symbols
== STRIP_DEBUG
1556 || strip_symbols
== STRIP_UNNEEDED
1557 || strip_symbols
== STRIP_ALL
1558 || discard_locals
== LOCALS_ALL
1559 || convert_debugging
))
1564 p
= find_section_list (bfd_section_name (ibfd
, isection
), false);
1566 if (sections_removed
&& p
!= NULL
&& p
->remove
)
1568 if (sections_copied
&& (p
== NULL
|| ! p
->copy
))
1571 osection
= isection
->output_section
;
1572 size
= bfd_get_section_size_before_reloc (isection
);
1574 if (size
== 0 || osection
== 0)
1578 relsize
= bfd_get_reloc_upper_bound (ibfd
, isection
);
1580 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1583 bfd_set_reloc (obfd
, osection
, (arelent
**) NULL
, 0);
1586 relpp
= (arelent
**) xmalloc (relsize
);
1587 relcount
= bfd_canonicalize_reloc (ibfd
, isection
, relpp
, isympp
);
1589 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1591 if (strip_symbols
== STRIP_ALL
)
1593 /* Remove relocations which are not in
1594 keep_strip_specific_list. */
1595 arelent
**temp_relpp
;
1596 long temp_relcount
= 0;
1599 temp_relpp
= (arelent
**) xmalloc (relsize
);
1600 for (i
= 0; i
< relcount
; i
++)
1601 if (is_specified_symbol
1602 (bfd_asymbol_name (*relpp
[i
]->sym_ptr_ptr
),
1603 keep_specific_list
))
1604 temp_relpp
[temp_relcount
++] = relpp
[i
];
1605 relcount
= temp_relcount
;
1609 bfd_set_reloc (obfd
, osection
,
1610 (relcount
== 0 ? (arelent
**) NULL
: relpp
), relcount
);
1613 isection
->_cooked_size
= isection
->_raw_size
;
1614 isection
->reloc_done
= true;
1616 if (bfd_get_section_flags (ibfd
, isection
) & SEC_HAS_CONTENTS
)
1618 PTR memhunk
= (PTR
) xmalloc ((unsigned) size
);
1620 if (!bfd_get_section_contents (ibfd
, isection
, memhunk
, (file_ptr
) 0,
1622 RETURN_NONFATAL (bfd_get_filename (ibfd
));
1625 filter_bytes (memhunk
, &size
);
1627 if (!bfd_set_section_contents (obfd
, osection
, memhunk
, (file_ptr
) 0,
1629 RETURN_NONFATAL (bfd_get_filename (obfd
));
1633 else if (p
!= NULL
&& p
->set_flags
&& (p
->flags
& SEC_HAS_CONTENTS
) != 0)
1635 PTR memhunk
= (PTR
) xmalloc ((unsigned) size
);
1637 /* We don't permit the user to turn off the SEC_HAS_CONTENTS
1638 flag--they can just remove the section entirely and add it
1639 back again. However, we do permit them to turn on the
1640 SEC_HAS_CONTENTS flag, and take it to mean that the section
1641 contents should be zeroed out. */
1643 memset (memhunk
, 0, size
);
1644 if (! bfd_set_section_contents (obfd
, osection
, memhunk
, (file_ptr
) 0,
1646 RETURN_NONFATAL (bfd_get_filename (obfd
));
1651 /* Get all the sections. This is used when --gap-fill or --pad-to is
1655 get_sections (obfd
, osection
, secppparg
)
1656 bfd
*obfd ATTRIBUTE_UNUSED
;
1660 asection
***secppp
= (asection
***) secppparg
;
1662 **secppp
= osection
;
1666 /* Sort sections by VMA. This is called via qsort, and is used when
1667 --gap-fill or --pad-to is used. We force non loadable or empty
1668 sections to the front, where they are easier to ignore. */
1671 compare_section_lma (arg1
, arg2
)
1675 const asection
**sec1
= (const asection
**) arg1
;
1676 const asection
**sec2
= (const asection
**) arg2
;
1677 flagword flags1
, flags2
;
1679 /* Sort non loadable sections to the front. */
1680 flags1
= (*sec1
)->flags
;
1681 flags2
= (*sec2
)->flags
;
1682 if ((flags1
& SEC_HAS_CONTENTS
) == 0
1683 || (flags1
& SEC_LOAD
) == 0)
1685 if ((flags2
& SEC_HAS_CONTENTS
) != 0
1686 && (flags2
& SEC_LOAD
) != 0)
1691 if ((flags2
& SEC_HAS_CONTENTS
) == 0
1692 || (flags2
& SEC_LOAD
) == 0)
1696 /* Sort sections by LMA. */
1697 if ((*sec1
)->lma
> (*sec2
)->lma
)
1699 else if ((*sec1
)->lma
< (*sec2
)->lma
)
1702 /* Sort sections with the same LMA by size. */
1703 if ((*sec1
)->_raw_size
> (*sec2
)->_raw_size
)
1705 else if ((*sec1
)->_raw_size
< (*sec2
)->_raw_size
)
1711 /* Mark all the symbols which will be used in output relocations with
1712 the BSF_KEEP flag so that those symbols will not be stripped.
1714 Ignore relocations which will not appear in the output file. */
1717 mark_symbols_used_in_relocations (ibfd
, isection
, symbolsarg
)
1722 asymbol
**symbols
= (asymbol
**) symbolsarg
;
1727 /* Ignore an input section with no corresponding output section. */
1728 if (isection
->output_section
== NULL
)
1731 relsize
= bfd_get_reloc_upper_bound (ibfd
, isection
);
1733 bfd_fatal (bfd_get_filename (ibfd
));
1738 relpp
= (arelent
**) xmalloc (relsize
);
1739 relcount
= bfd_canonicalize_reloc (ibfd
, isection
, relpp
, symbols
);
1741 bfd_fatal (bfd_get_filename (ibfd
));
1743 /* Examine each symbol used in a relocation. If it's not one of the
1744 special bfd section symbols, then mark it with BSF_KEEP. */
1745 for (i
= 0; i
< relcount
; i
++)
1747 if (*relpp
[i
]->sym_ptr_ptr
!= bfd_com_section_ptr
->symbol
1748 && *relpp
[i
]->sym_ptr_ptr
!= bfd_abs_section_ptr
->symbol
1749 && *relpp
[i
]->sym_ptr_ptr
!= bfd_und_section_ptr
->symbol
)
1750 (*relpp
[i
]->sym_ptr_ptr
)->flags
|= BSF_KEEP
;
1757 /* Write out debugging information. */
1760 write_debugging_info (obfd
, dhandle
, symcountp
, symppp
)
1763 long *symcountp ATTRIBUTE_UNUSED
;
1764 asymbol
***symppp ATTRIBUTE_UNUSED
;
1766 if (bfd_get_flavour (obfd
) == bfd_target_ieee_flavour
)
1767 return write_ieee_debugging_info (obfd
, dhandle
);
1769 if (bfd_get_flavour (obfd
) == bfd_target_coff_flavour
1770 || bfd_get_flavour (obfd
) == bfd_target_elf_flavour
)
1772 bfd_byte
*syms
, *strings
;
1773 bfd_size_type symsize
, stringsize
;
1774 asection
*stabsec
, *stabstrsec
;
1776 if (! write_stabs_in_sections_debugging_info (obfd
, dhandle
, &syms
,
1781 stabsec
= bfd_make_section (obfd
, ".stab");
1782 stabstrsec
= bfd_make_section (obfd
, ".stabstr");
1784 || stabstrsec
== NULL
1785 || ! bfd_set_section_size (obfd
, stabsec
, symsize
)
1786 || ! bfd_set_section_size (obfd
, stabstrsec
, stringsize
)
1787 || ! bfd_set_section_alignment (obfd
, stabsec
, 2)
1788 || ! bfd_set_section_alignment (obfd
, stabstrsec
, 0)
1789 || ! bfd_set_section_flags (obfd
, stabsec
,
1793 || ! bfd_set_section_flags (obfd
, stabstrsec
,
1798 non_fatal (_("%s: can't create debugging section: %s"),
1799 bfd_get_filename (obfd
),
1800 bfd_errmsg (bfd_get_error ()));
1804 /* We can get away with setting the section contents now because
1805 the next thing the caller is going to do is copy over the
1806 real sections. We may someday have to split the contents
1807 setting out of this function. */
1808 if (! bfd_set_section_contents (obfd
, stabsec
, syms
, (file_ptr
) 0,
1810 || ! bfd_set_section_contents (obfd
, stabstrsec
, strings
,
1811 (file_ptr
) 0, stringsize
))
1813 non_fatal (_("%s: can't set debugging section contents: %s"),
1814 bfd_get_filename (obfd
),
1815 bfd_errmsg (bfd_get_error ()));
1822 non_fatal (_("%s: don't know how to write debugging information for %s"),
1823 bfd_get_filename (obfd
), bfd_get_target (obfd
));
1828 strip_main (argc
, argv
)
1832 char *input_target
= NULL
, *output_target
= NULL
;
1833 boolean show_version
= false;
1835 struct section_list
*p
;
1836 char *output_file
= NULL
;
1838 while ((c
= getopt_long (argc
, argv
, "b:i:I:j:K:N:s:O:d:F:L:G:R:SpgxXVvW:",
1839 strip_options
, (int *) 0)) != EOF
)
1844 input_target
= optarg
;
1847 output_target
= optarg
;
1850 input_target
= output_target
= optarg
;
1853 p
= find_section_list (optarg
, true);
1855 sections_removed
= true;
1858 strip_symbols
= STRIP_ALL
;
1862 case 'd': /* Historic BSD alias for -g. Used by early NetBSD. */
1863 strip_symbols
= STRIP_DEBUG
;
1865 case OPTION_STRIP_UNNEEDED
:
1866 strip_symbols
= STRIP_UNNEEDED
;
1869 add_specific_symbol (optarg
, &keep_specific_list
);
1872 add_specific_symbol (optarg
, &strip_specific_list
);
1875 output_file
= optarg
;
1878 preserve_dates
= true;
1881 discard_locals
= LOCALS_ALL
;
1884 discard_locals
= LOCALS_START_L
;
1890 show_version
= true;
1893 break; /* we've been given a long option */
1895 strip_usage (stdout
, 0);
1897 strip_usage (stderr
, 1);
1902 print_version ("strip");
1904 /* Default is to strip all symbols. */
1905 if (strip_symbols
== STRIP_UNDEF
1906 && discard_locals
== LOCALS_UNDEF
1907 && strip_specific_list
== NULL
)
1908 strip_symbols
= STRIP_ALL
;
1910 if (output_target
== (char *) NULL
)
1911 output_target
= input_target
;
1915 || (output_file
!= NULL
&& (i
+ 1) < argc
))
1916 strip_usage (stderr
, 1);
1918 for (; i
< argc
; i
++)
1920 int hold_status
= status
;
1921 struct stat statbuf
;
1926 if (stat (argv
[i
], &statbuf
) < 0)
1928 non_fatal (_("%s: cannot stat: %s"), argv
[i
], strerror (errno
));
1933 if (output_file
!= NULL
)
1934 tmpname
= output_file
;
1936 tmpname
= make_tempname (argv
[i
]);
1939 copy_file (argv
[i
], tmpname
, input_target
, output_target
);
1943 set_times (tmpname
, &statbuf
);
1944 if (output_file
== NULL
)
1945 smart_rename (tmpname
, argv
[i
], preserve_dates
);
1946 status
= hold_status
;
1950 if (output_file
== NULL
)
1958 copy_main (argc
, argv
)
1962 char *input_filename
= NULL
, *output_filename
= NULL
;
1963 char *input_target
= NULL
, *output_target
= NULL
;
1964 boolean show_version
= false;
1965 boolean change_warn
= true;
1967 struct section_list
*p
;
1968 struct stat statbuf
;
1970 while ((c
= getopt_long (argc
, argv
, "b:i:I:j:K:N:s:O:d:F:L:R:SpgxXVvW:",
1971 copy_options
, (int *) 0)) != EOF
)
1976 copy_byte
= atoi (optarg
);
1978 fatal (_("byte number must be non-negative"));
1982 interleave
= atoi (optarg
);
1984 fatal (_("interleave must be positive"));
1988 case 's': /* "source" - 'I' is preferred */
1989 input_target
= optarg
;
1993 case 'd': /* "destination" - 'O' is preferred */
1994 output_target
= optarg
;
1998 input_target
= output_target
= optarg
;
2002 p
= find_section_list (optarg
, true);
2004 fatal (_("%s both copied and removed"), optarg
);
2006 sections_copied
= true;
2010 p
= find_section_list (optarg
, true);
2012 fatal (_("%s both copied and removed"), optarg
);
2014 sections_removed
= true;
2018 strip_symbols
= STRIP_ALL
;
2022 strip_symbols
= STRIP_DEBUG
;
2025 case OPTION_STRIP_UNNEEDED
:
2026 strip_symbols
= STRIP_UNNEEDED
;
2030 add_specific_symbol (optarg
, &keep_specific_list
);
2034 add_specific_symbol (optarg
, &strip_specific_list
);
2038 add_specific_symbol (optarg
, &localize_specific_list
);
2042 add_specific_symbol (optarg
, &keepglobal_specific_list
);
2046 add_specific_symbol (optarg
, &weaken_specific_list
);
2050 preserve_dates
= true;
2054 discard_locals
= LOCALS_ALL
;
2058 discard_locals
= LOCALS_START_L
;
2066 show_version
= true;
2073 case OPTION_ADD_SECTION
:
2077 struct section_add
*pa
;
2082 s
= strchr (optarg
, '=');
2085 fatal (_("bad format for %s"), "--add-section");
2087 if (stat (s
+ 1, & st
) < 0)
2088 fatal (_("cannot stat: %s: %s"), s
+ 1, strerror (errno
));
2090 pa
= (struct section_add
*) xmalloc (sizeof (struct section_add
));
2093 name
= (char *) xmalloc (len
+ 1);
2094 strncpy (name
, optarg
, len
);
2098 pa
->filename
= s
+ 1;
2100 pa
->size
= st
.st_size
;
2102 pa
->contents
= (bfd_byte
*) xmalloc (pa
->size
);
2103 f
= fopen (pa
->filename
, FOPEN_RB
);
2106 fatal (_("cannot open: %s: %s"), pa
->filename
, strerror (errno
));
2108 if (fread (pa
->contents
, 1, pa
->size
, f
) == 0
2110 fatal (_("%s: fread failed"), pa
->filename
);
2114 pa
->next
= add_sections
;
2119 case OPTION_CHANGE_START
:
2120 change_start
= parse_vma (optarg
, "--change-start");
2123 case OPTION_CHANGE_SECTION_ADDRESS
:
2124 case OPTION_CHANGE_SECTION_LMA
:
2125 case OPTION_CHANGE_SECTION_VMA
:
2130 char *option
= NULL
;
2132 enum change_action what
= CHANGE_IGNORE
;
2136 case OPTION_CHANGE_SECTION_ADDRESS
:
2137 option
= "--change-section-address";
2139 case OPTION_CHANGE_SECTION_LMA
:
2140 option
= "--change-section-lma";
2142 case OPTION_CHANGE_SECTION_VMA
:
2143 option
= "--change-section-vma";
2147 s
= strchr (optarg
, '=');
2150 s
= strchr (optarg
, '+');
2153 s
= strchr (optarg
, '-');
2155 fatal (_("bad format for %s"), option
);
2160 name
= (char *) xmalloc (len
+ 1);
2161 strncpy (name
, optarg
, len
);
2164 p
= find_section_list (name
, true);
2166 val
= parse_vma (s
+ 1, option
);
2170 case '=': what
= CHANGE_SET
; break;
2171 case '-': val
= - val
; /* Drop through. */
2172 case '+': what
= CHANGE_MODIFY
; break;
2177 case OPTION_CHANGE_SECTION_ADDRESS
:
2178 p
->change_vma
= what
;
2182 case OPTION_CHANGE_SECTION_LMA
:
2183 p
->change_lma
= what
;
2187 case OPTION_CHANGE_SECTION_VMA
:
2188 p
->change_vma
= what
;
2195 case OPTION_CHANGE_ADDRESSES
:
2196 change_section_address
= parse_vma (optarg
, "--change-addresses");
2197 change_start
= change_section_address
;
2200 case OPTION_CHANGE_WARNINGS
:
2204 case OPTION_CHANGE_LEADING_CHAR
:
2205 change_leading_char
= true;
2208 case OPTION_DEBUGGING
:
2209 convert_debugging
= true;
2212 case OPTION_GAP_FILL
:
2214 bfd_vma gap_fill_vma
;
2216 gap_fill_vma
= parse_vma (optarg
, "--gap-fill");
2217 gap_fill
= (bfd_byte
) gap_fill_vma
;
2218 if ((bfd_vma
) gap_fill
!= gap_fill_vma
)
2222 sprintf_vma (buff
, gap_fill_vma
);
2224 non_fatal (_("Warning: truncating gap-fill from 0x%s to 0x%x"),
2227 gap_fill_set
= true;
2231 case OPTION_NO_CHANGE_WARNINGS
:
2232 change_warn
= false;
2236 pad_to
= parse_vma (optarg
, "--pad-to");
2240 case OPTION_REMOVE_LEADING_CHAR
:
2241 remove_leading_char
= true;
2244 case OPTION_REDEFINE_SYM
:
2246 /* Push this redefinition onto redefine_symbol_list. */
2250 const char *nextarg
;
2251 char *source
, *target
;
2253 s
= strchr (optarg
, '=');
2256 fatal (_("bad format for %s"), "--redefine-sym");
2260 source
= (char *) xmalloc (len
+ 1);
2261 strncpy (source
, optarg
, len
);
2265 len
= strlen (nextarg
);
2266 target
= (char *) xmalloc (len
+ 1);
2267 strcpy (target
, nextarg
);
2269 redefine_list_append (source
, target
);
2276 case OPTION_SET_SECTION_FLAGS
:
2282 s
= strchr (optarg
, '=');
2284 fatal (_("bad format for %s"), "--set-section-flags");
2287 name
= (char *) xmalloc (len
+ 1);
2288 strncpy (name
, optarg
, len
);
2291 p
= find_section_list (name
, true);
2293 p
->set_flags
= true;
2294 p
->flags
= parse_flags (s
+ 1);
2298 case OPTION_SET_START
:
2299 set_start
= parse_vma (optarg
, "--set-start");
2300 set_start_set
= true;
2303 case OPTION_SREC_LEN
:
2304 Chunk
= parse_vma (optarg
, "--srec-len");
2307 case OPTION_SREC_FORCES3
:
2311 case OPTION_STRIP_SYMBOLS
:
2312 add_specific_symbols (optarg
, &strip_specific_list
);
2315 case OPTION_KEEP_SYMBOLS
:
2316 add_specific_symbols (optarg
, &keep_specific_list
);
2319 case OPTION_LOCALIZE_SYMBOLS
:
2320 add_specific_symbols (optarg
, &localize_specific_list
);
2323 case OPTION_KEEPGLOBAL_SYMBOLS
:
2324 add_specific_symbols (optarg
, &keepglobal_specific_list
);
2327 case OPTION_WEAKEN_SYMBOLS
:
2328 add_specific_symbols (optarg
, &weaken_specific_list
);
2332 break; /* we've been given a long option */
2335 copy_usage (stdout
, 0);
2338 copy_usage (stderr
, 1);
2343 print_version ("objcopy");
2345 if (copy_byte
>= interleave
)
2346 fatal (_("byte number must be less than interleave"));
2348 if (optind
== argc
|| optind
+ 2 < argc
)
2349 copy_usage (stderr
, 1);
2351 input_filename
= argv
[optind
];
2352 if (optind
+ 1 < argc
)
2353 output_filename
= argv
[optind
+ 1];
2355 /* Default is to strip no symbols. */
2356 if (strip_symbols
== STRIP_UNDEF
&& discard_locals
== LOCALS_UNDEF
)
2357 strip_symbols
= STRIP_NONE
;
2359 if (output_target
== (char *) NULL
)
2360 output_target
= input_target
;
2364 if (stat (input_filename
, &statbuf
) < 0)
2365 fatal (_("Cannot stat: %s: %s"), input_filename
, strerror (errno
));
2368 /* If there is no destination file then create a temp and rename
2369 the result into the input. */
2371 if (output_filename
== (char *) NULL
)
2373 char *tmpname
= make_tempname (input_filename
);
2375 copy_file (input_filename
, tmpname
, input_target
, output_target
);
2379 set_times (tmpname
, &statbuf
);
2380 smart_rename (tmpname
, input_filename
, preserve_dates
);
2387 copy_file (input_filename
, output_filename
, input_target
, output_target
);
2388 if (status
== 0 && preserve_dates
)
2389 set_times (output_filename
, &statbuf
);
2394 for (p
= change_sections
; p
!= NULL
; p
= p
->next
)
2398 if (p
->change_vma
!= CHANGE_IGNORE
)
2402 sprintf_vma (buff
, p
->vma_val
);
2404 /* xgettext:c-format */
2405 non_fatal (_("%s %s%c0x%s never used"),
2406 "--change-section-vma",
2408 p
->change_vma
== CHANGE_SET
? '=' : '+',
2412 if (p
->change_lma
!= CHANGE_IGNORE
)
2416 sprintf_vma (buff
, p
->lma_val
);
2418 /* xgettext:c-format */
2419 non_fatal (_("%s %s%c0x%s never used"),
2420 "--change-section-lma",
2422 p
->change_lma
== CHANGE_SET
? '=' : '+',
2437 #if defined (HAVE_SETLOCALE) && defined (HAVE_LC_MESSAGES)
2438 setlocale (LC_MESSAGES
, "");
2440 bindtextdomain (PACKAGE
, LOCALEDIR
);
2441 textdomain (PACKAGE
);
2443 program_name
= argv
[0];
2444 xmalloc_set_program_name (program_name
);
2446 START_PROGRESS (program_name
, 0);
2448 strip_symbols
= STRIP_UNDEF
;
2449 discard_locals
= LOCALS_UNDEF
;
2452 set_default_bfd_target ();
2456 int i
= strlen (program_name
);
2457 #ifdef HAVE_DOS_BASED_FILE_SYSTEM
2458 /* Drop the .exe suffix, if any. */
2459 if (i
> 4 && FILENAME_CMP (program_name
+ i
- 4, ".exe") == 0)
2462 program_name
[i
] = '\0';
2465 is_strip
= (i
>= 5 && FILENAME_CMP (program_name
+ i
- 5, "strip") == 0);
2469 strip_main (argc
, argv
);
2471 copy_main (argc
, argv
);
2473 END_PROGRESS (program_name
);