1 /* Discard section not used at runtime from object files.
2 Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005 Red Hat, Inc.
3 This file is part of Red Hat elfutils.
4 Written by Ulrich Drepper <drepper@redhat.com>, 2000.
6 Red Hat elfutils is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by the
8 Free Software Foundation; version 2 of the License.
10 Red Hat elfutils is distributed in the hope that it will be useful, but
11 WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 General Public License for more details.
15 You should have received a copy of the GNU General Public License along
16 with Red Hat elfutils; if not, write to the Free Software Foundation,
17 Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
19 Red Hat elfutils is an included package of the Open Invention Network.
20 An included package of the Open Invention Network is a package for which
21 Open Invention Network licensees cross-license their patents. No patent
22 license is granted, either expressly or impliedly, by designation as an
23 included package. Should you wish to participate in the Open Invention
24 Network licensing program, please visit www.openinventionnetwork.com
25 <http://www.openinventionnetwork.com>. */
44 #include <stdio_ext.h>
48 #include <sys/param.h>
51 #include <elf-knowledge.h>
56 /* Name and version of program. */
57 static void print_version (FILE *stream, struct argp_state *state);
58 void (*argp_program_version_hook) (FILE *, struct argp_state *) = print_version;
60 /* Bug report address. */
61 const char *argp_program_bug_address = PACKAGE_BUGREPORT;
64 /* Values for the parameters which have no short form. */
65 #define OPT_REMOVE_COMMENT 0x100
66 #define OPT_PERMISSIVE 0x101
69 /* Definitions of arguments for argp functions. */
70 static const struct argp_option options[] =
72 { NULL, 0, NULL, 0, N_("Output selection:"), 0 },
73 { NULL, 'o', "FILE", 0, N_("Place stripped output into FILE"), 0 },
74 { NULL, 'f', "FILE", 0, N_("Extract the removed sections into FILE"), 0 },
75 { NULL, 'F', "FILE", 0, N_("Embed name FILE instead of -f argument"), 0 },
77 { NULL, 0, NULL, 0, N_("Output options:"), 0 },
78 { "strip-all", 's', NULL, OPTION_HIDDEN, NULL, 0 },
79 { "strip-debug", 'g', NULL, 0, N_("Remove all debugging symbols"), 0 },
80 { NULL, 'd', NULL, OPTION_ALIAS, NULL, 0 },
81 { NULL, 'S', NULL, OPTION_ALIAS, NULL, 0 },
82 { "preserve-dates", 'p', NULL, 0,
83 N_("Copy modified/access timestamps to the output"), 0 },
84 { "remove-comment", OPT_REMOVE_COMMENT, NULL, 0,
85 N_("Remove .comment section"), 0 },
86 { "remove-section", 'R', "SECTION", OPTION_HIDDEN, NULL, 0 },
87 { "permissive", OPT_PERMISSIVE, NULL, 0,
88 N_("Relax a few rules to handle slightly broken ELF files"), 0 },
89 { NULL, 0, NULL, 0, NULL, 0 }
92 /* Short description of program. */
93 static const char doc[] = N_("Discard symbols from object files.");
95 /* Strings for arguments in help texts. */
96 static const char args_doc[] = N_("[FILE...]");
98 /* Prototype for option handler. */
99 static error_t parse_opt (int key, char *arg, struct argp_state *state);
101 /* Data structure to communicate with argp functions. */
102 static struct argp argp =
104 options, parse_opt, args_doc, doc, NULL, NULL, NULL
108 /* Print symbols in file named FNAME. */
109 static int process_file (const char *fname);
111 /* Handle one ELF file. */
112 static int handle_elf (int fd, Elf *elf, const char *prefix,
113 const char *fname, mode_t mode, struct timeval tvp[2]);
115 /* Handle all files contained in the archive. */
116 static int handle_ar (int fd, Elf *elf, const char *prefix, const char *fname,
117 struct timeval tvp[2]);
119 #define INTERNAL_ERROR(fname) \
120 error (EXIT_FAILURE, 0, gettext ("%s: INTERNAL ERROR %d (%s-%s): %s"), \
121 fname, __LINE__, VERSION, __DATE__, elf_errmsg (-1))
124 /* Name of the output file. */
125 static const char *output_fname;
127 /* Name of the debug output file. */
128 static const char *debug_fname;
130 /* Name to pretend the debug output file has. */
131 static const char *debug_fname_embed;
133 /* If true output files shall have same date as the input file. */
134 static bool preserve_dates;
136 /* If true .comment sections will be removed. */
137 static bool remove_comment;
139 /* If true remove all debug sections. */
140 static bool remove_debug;
142 /* If true relax some ELF rules for input files. */
143 static bool permissive;
147 main (int argc, char *argv[])
152 /* Make memory leak detection possible. */
155 /* We use no threads here which can interfere with handling a stream. */
156 __fsetlocking (stdin, FSETLOCKING_BYCALLER);
157 __fsetlocking (stdout, FSETLOCKING_BYCALLER);
158 __fsetlocking (stderr, FSETLOCKING_BYCALLER);
161 setlocale (LC_ALL, "");
163 /* Make sure the message catalog can be found. */
164 bindtextdomain (PACKAGE, LOCALEDIR);
166 /* Initialize the message catalog. */
167 textdomain (PACKAGE);
169 /* Parse and process arguments. */
170 if (argp_parse (&argp, argc, argv, 0, &remaining, NULL) != 0)
173 /* Tell the library which version we are expecting. */
174 elf_version (EV_CURRENT);
176 if (remaining == argc)
177 /* The user didn't specify a name so we use a.out. */
178 result = process_file ("a.out");
181 /* If we have seen the '-o' or '-f' option there must be exactly one
183 if ((output_fname != NULL || debug_fname != NULL)
184 && remaining + 1 < argc)
185 error (EXIT_FAILURE, 0, gettext ("\
186 Only one input file allowed together with '-o' and '-f'"));
188 /* Process all the remaining files. */
190 result |= process_file (argv[remaining]);
191 while (++remaining < argc);
198 /* Print the version information. */
200 print_version (FILE *stream, struct argp_state *state __attribute__ ((unused)))
202 fprintf (stream, "strip (%s) %s\n", PACKAGE_NAME, VERSION);
203 fprintf (stream, gettext ("\
204 Copyright (C) %s Red Hat, Inc.\n\
205 This is free software; see the source for copying conditions. There is NO\n\
206 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\
208 fprintf (stream, gettext ("Written by %s.\n"), "Ulrich Drepper");
212 /* Handle program arguments. */
214 parse_opt (int key, char *arg, struct argp_state *state)
219 if (debug_fname != NULL)
221 error (0, 0, gettext ("-f option specified twice"));
228 if (debug_fname_embed != NULL)
230 error (0, 0, gettext ("-F option specified twice"));
233 debug_fname_embed = arg;
237 if (output_fname != NULL)
239 error (0, 0, gettext ("-o option specified twice"));
246 preserve_dates = true;
249 case OPT_REMOVE_COMMENT:
250 remove_comment = true;
254 if (!strcmp (arg, ".comment"))
255 remove_comment = true;
259 gettext ("-R option supports only .comment section"));
274 case 's': /* Ignored for compatibility. */
278 return ARGP_ERR_UNKNOWN;
285 process_file (const char *fname)
287 /* If we have to preserve the modify and access timestamps get them
288 now. We cannot use fstat() after opening the file since the open
289 would change the access time. */
290 struct stat64 pre_st;
291 struct timeval tv[2];
295 if (stat64 (fname, &pre_st) != 0)
297 error (0, errno, gettext ("cannot stat input file '%s'"), fname);
301 /* If we have to preserve the timestamp, we need it in the
302 format utimes() understands. */
303 TIMESPEC_TO_TIMEVAL (&tv[0], &pre_st.st_atim);
304 TIMESPEC_TO_TIMEVAL (&tv[1], &pre_st.st_mtim);
308 int fd = open (fname, output_fname == NULL ? O_RDWR : O_RDONLY);
311 error (0, errno, gettext ("while opening '%s'"), fname);
315 /* We always use fstat() even if we called stat() before. This is
316 done to make sure the information returned by stat() is for the
319 if (fstat64 (fd, &st) != 0)
321 error (0, errno, gettext ("cannot stat input file '%s'"), fname);
324 /* Paranoid mode on. */
326 && (st.st_ino != pre_st.st_ino || st.st_dev != pre_st.st_dev))
328 /* We detected a race. Try again. */
333 /* Now get the ELF descriptor. */
334 Elf *elf = elf_begin (fd, output_fname == NULL ? ELF_C_RDWR : ELF_C_READ,
337 switch (elf_kind (elf))
340 result = handle_elf (fd, elf, NULL, fname, st.st_mode & ACCESSPERMS,
341 preserve_dates ? tv : NULL);
345 /* It is not possible to strip the content of an archive direct
346 the output to a specific file. */
347 if (unlikely (output_fname != NULL))
349 error (0, 0, gettext ("%s: cannot use -o when stripping archive"),
354 result = handle_ar (fd, elf, NULL, fname, preserve_dates ? tv : NULL);
358 error (0, 0, gettext ("%s: File format not recognized"), fname);
363 if (unlikely (elf_end (elf) != 0))
364 INTERNAL_ERROR (fname);
372 /* Maximum size of array allocated on stack. */
373 #define MAX_STACK_ALLOC (400 * 1024)
376 handle_elf (int fd, Elf *elf, const char *prefix, const char *fname,
377 mode_t mode, struct timeval tvp[2])
379 size_t prefix_len = prefix == NULL ? 0 : strlen (prefix);
380 size_t fname_len = strlen (fname) + 1;
381 char *fullname = alloca (prefix_len + 1 + fname_len);
383 Elf *debugelf = NULL;
384 char *tmp_debug_fname = NULL;
393 Elf32_Word idx; /* Index in new file. */
394 Elf32_Word old_sh_link; /* Original value of shdr.sh_link. */
395 Elf32_Word symtab_idx;
396 Elf32_Word version_idx;
397 Elf32_Word group_idx;
398 Elf32_Word group_cnt;
400 struct Ebl_Strent *se;
401 Elf32_Word *newsymidx;
407 GElf_Ehdr newehdr_mem;
409 GElf_Ehdr debugehdr_mem;
410 GElf_Ehdr *debugehdr;
411 struct Ebl_Strtab *shst = NULL;
412 Elf_Data debuglink_crc_data;
413 bool any_symtab_changes = false;
414 Elf_Data *shstrtab_data = NULL;
416 /* Create the full name of the file. */
419 cp = mempcpy (cp, prefix, prefix_len);
422 memcpy (cp, fname, fname_len);
424 /* If we are not replacing the input file open a new file here. */
425 if (output_fname != NULL)
427 fd = open (output_fname, O_RDWR | O_CREAT, mode);
428 if (unlikely (fd == -1))
430 error (0, errno, gettext ("cannot open '%s'"), output_fname);
437 /* Get the EBL handling. The -g option is currently the only reason
438 we need EBL so dont open the backend unless necessary. */
442 ebl = ebl_openbackend (elf);
445 error (0, errno, gettext ("cannot open EBL backend"));
451 /* Open the additional file the debug information will be stored in. */
452 if (debug_fname != NULL)
454 /* Create a temporary file name. We do not want to overwrite
455 the debug file if the file would not contain any
457 size_t debug_fname_len = strlen (debug_fname);
458 tmp_debug_fname = (char *) alloca (debug_fname_len + sizeof (".XXXXXX"));
459 strcpy (mempcpy (tmp_debug_fname, debug_fname, debug_fname_len),
462 debug_fd = mkstemp (tmp_debug_fname);
463 if (unlikely (debug_fd == -1))
465 error (0, errno, gettext ("cannot open '%s'"), debug_fname);
471 /* Get the information from the old file. */
473 GElf_Ehdr *ehdr = gelf_getehdr (elf, &ehdr_mem);
475 INTERNAL_ERROR (fname);
477 /* Get the section header string table index. */
478 if (unlikely (elf_getshstrndx (elf, &shstrndx) < 0))
479 error (EXIT_FAILURE, 0,
480 gettext ("cannot get section header string table index"));
482 /* We now create a new ELF descriptor for the same file. We
483 construct it almost exactly in the same way with some information
486 if (output_fname != NULL)
487 newelf = elf_begin (fd, ELF_C_WRITE_MMAP, NULL);
489 newelf = elf_clone (elf, ELF_C_EMPTY);
491 if (unlikely (gelf_newehdr (newelf, gelf_getclass (elf)) == 0)
492 || (ehdr->e_type != ET_REL
493 && unlikely (gelf_newphdr (newelf, ehdr->e_phnum) == 0)))
495 error (0, 0, gettext ("cannot create new file '%s': %s"),
496 output_fname, elf_errmsg (-1));
500 /* Copy over the old program header if needed. */
501 if (ehdr->e_type != ET_REL)
502 for (cnt = 0; cnt < ehdr->e_phnum; ++cnt)
505 GElf_Phdr *phdr = gelf_getphdr (elf, cnt, &phdr_mem);
507 || unlikely (gelf_update_phdr (newelf, cnt, phdr) == 0))
508 INTERNAL_ERROR (fname);
511 if (debug_fname != NULL)
513 /* Also create an ELF descriptor for the debug file */
514 debugelf = elf_begin (debug_fd, ELF_C_WRITE_MMAP, NULL);
515 if (unlikely (gelf_newehdr (debugelf, gelf_getclass (elf)) == 0)
516 || (ehdr->e_type != ET_REL
517 && unlikely (gelf_newphdr (debugelf, ehdr->e_phnum) == 0)))
519 error (0, 0, gettext ("cannot create new file '%s': %s"),
520 debug_fname, elf_errmsg (-1));
524 /* Copy over the old program header if needed. */
525 if (ehdr->e_type != ET_REL)
526 for (cnt = 0; cnt < ehdr->e_phnum; ++cnt)
529 GElf_Phdr *phdr = gelf_getphdr (elf, cnt, &phdr_mem);
531 || unlikely (gelf_update_phdr (debugelf, cnt, phdr) == 0))
532 INTERNAL_ERROR (fname);
536 /* Number of sections. */
538 if (unlikely (elf_getshnum (elf, &shnum) < 0))
540 error (0, 0, gettext ("cannot determine number of sections: %s"),
545 /* Storage for section information. We leave room for two more
546 entries since we unconditionally create a section header string
547 table. Maybe some weird tool created an ELF file without one.
548 The other one is used for the debug link section. */
549 if ((shnum + 2) * sizeof (struct shdr_info) > MAX_STACK_ALLOC)
550 shdr_info = (struct shdr_info *) xcalloc (shnum + 2,
551 sizeof (struct shdr_info));
554 shdr_info = (struct shdr_info *) alloca ((shnum + 2)
555 * sizeof (struct shdr_info));
556 memset (shdr_info, '\0', (shnum + 2) * sizeof (struct shdr_info));
559 /* Prepare section information data structure. */
562 while ((scn = elf_nextscn (elf, scn)) != NULL)
564 /* This should always be true (i.e., there should not be any
565 holes in the numbering). */
566 assert (elf_ndxscn (scn) == cnt);
568 shdr_info[cnt].scn = scn;
570 /* Get the header. */
571 if (gelf_getshdr (scn, &shdr_info[cnt].shdr) == NULL)
572 INTERNAL_ERROR (fname);
574 /* Get the name of the section. */
575 shdr_info[cnt].name = elf_strptr (elf, shstrndx,
576 shdr_info[cnt].shdr.sh_name);
577 if (shdr_info[cnt].name == NULL)
579 error (0, 0, gettext ("illformed file '%s'"), fname);
583 /* Mark them as present but not yet investigated. */
584 shdr_info[cnt].idx = 1;
586 /* Remember the shdr.sh_link value. */
587 shdr_info[cnt].old_sh_link = shdr_info[cnt].shdr.sh_link;
589 /* Sections in files other than relocatable object files which
590 are not loaded can be freely moved by us. In relocatable
591 object files everything can be moved. */
592 if (ehdr->e_type == ET_REL
593 || (shdr_info[cnt].shdr.sh_flags & SHF_ALLOC) == 0)
594 shdr_info[cnt].shdr.sh_offset = 0;
596 /* If this is an extended section index table store an
597 appropriate reference. */
598 if (unlikely (shdr_info[cnt].shdr.sh_type == SHT_SYMTAB_SHNDX))
600 assert (shdr_info[shdr_info[cnt].shdr.sh_link].symtab_idx == 0);
601 shdr_info[shdr_info[cnt].shdr.sh_link].symtab_idx = cnt;
603 else if (unlikely (shdr_info[cnt].shdr.sh_type == SHT_GROUP))
605 /* Cross-reference the sections contained in the section
607 shdr_info[cnt].data = elf_getdata (shdr_info[cnt].scn, NULL);
608 if (shdr_info[cnt].data == NULL)
609 INTERNAL_ERROR (fname);
611 /* XXX Fix for unaligned access. */
612 Elf32_Word *grpref = (Elf32_Word *) shdr_info[cnt].data->d_buf;
615 inner < shdr_info[cnt].data->d_size / sizeof (Elf32_Word);
617 shdr_info[grpref[inner]].group_idx = cnt;
619 if (inner == 1 || (inner == 2 && (grpref[0] & GRP_COMDAT) == 0))
620 /* If the section group contains only one element and this
621 is n COMDAT section we can drop it right away. */
622 shdr_info[cnt].idx = 0;
624 shdr_info[cnt].group_cnt = inner - 1;
626 else if (unlikely (shdr_info[cnt].shdr.sh_type == SHT_GNU_versym))
628 assert (shdr_info[shdr_info[cnt].shdr.sh_link].version_idx == 0);
629 shdr_info[shdr_info[cnt].shdr.sh_link].version_idx = cnt;
632 /* If this section is part of a group make sure it is not
633 discarded right away. */
634 if ((shdr_info[cnt].shdr.sh_flags & SHF_GROUP) != 0)
636 assert (shdr_info[cnt].group_idx != 0);
638 if (shdr_info[shdr_info[cnt].group_idx].idx == 0)
640 /* The section group section will be removed. */
641 shdr_info[cnt].group_idx = 0;
642 shdr_info[cnt].shdr.sh_flags &= ~SHF_GROUP;
646 /* Increment the counter. */
650 /* Now determine which sections can go away. The general rule is that
651 all sections which are not used at runtime are stripped out. But
652 there are a few exceptions:
654 - special sections named ".comment" and ".note" are kept
655 - OS or architecture specific sections are kept since we might not
656 know how to handle them
657 - if a section is referred to from a section which is not removed
658 in the sh_link or sh_info element it cannot be removed either
660 for (cnt = 1; cnt < shnum; ++cnt)
661 /* Check whether the section can be removed. */
662 if (ebl_section_strip_p (ebl, ehdr, &shdr_info[cnt].shdr,
663 shdr_info[cnt].name, remove_comment,
666 /* For now assume this section will be removed. */
667 shdr_info[cnt].idx = 0;
669 idx = shdr_info[cnt].group_idx;
672 /* The section group data is already loaded. */
673 assert (shdr_info[idx].data != NULL);
675 /* If the references section group is a normal section
676 group and has one element remaining, or if it is an
677 empty COMDAT section group it is removed. */
678 bool is_comdat = (((Elf32_Word *) shdr_info[idx].data->d_buf)[0]
681 --shdr_info[idx].group_cnt;
682 if ((!is_comdat && shdr_info[idx].group_cnt == 1)
683 || (is_comdat && shdr_info[idx].group_cnt == 0))
685 shdr_info[idx].idx = 0;
686 /* Continue recursively. */
687 idx = shdr_info[idx].group_idx;
694 /* Mark the SHT_NULL section as handled. */
695 shdr_info[0].idx = 2;
698 /* Handle exceptions: section groups and cross-references. We might
699 have to repeat this a few times since the resetting of the flag
705 for (cnt = 1; cnt < shnum; ++cnt)
707 if (shdr_info[cnt].idx == 0)
709 /* If a relocation section is marked as being removed make
710 sure the section it is relocating is removed, too. */
711 if ((shdr_info[cnt].shdr.sh_type == SHT_REL
712 || shdr_info[cnt].shdr.sh_type == SHT_RELA)
713 && shdr_info[shdr_info[cnt].shdr.sh_info].idx != 0)
714 shdr_info[cnt].idx = 1;
717 if (shdr_info[cnt].idx == 1)
719 /* The content of symbol tables we don't remove must not
720 reference any section which we do remove. Otherwise
721 we cannot remove the section. */
722 if (shdr_info[cnt].shdr.sh_type == SHT_DYNSYM
723 || shdr_info[cnt].shdr.sh_type == SHT_SYMTAB)
725 /* Make sure the data is loaded. */
726 if (shdr_info[cnt].data == NULL)
729 = elf_getdata (shdr_info[cnt].scn, NULL);
730 if (shdr_info[cnt].data == NULL)
731 INTERNAL_ERROR (fname);
733 Elf_Data *symdata = shdr_info[cnt].data;
735 /* If there is an extended section index table load it
737 if (shdr_info[cnt].symtab_idx != 0
738 && shdr_info[shdr_info[cnt].symtab_idx].data == NULL)
740 assert (shdr_info[cnt].shdr.sh_type == SHT_SYMTAB);
742 shdr_info[shdr_info[cnt].symtab_idx].data
743 = elf_getdata (shdr_info[shdr_info[cnt].symtab_idx].scn,
745 if (shdr_info[shdr_info[cnt].symtab_idx].data == NULL)
746 INTERNAL_ERROR (fname);
749 = shdr_info[shdr_info[cnt].symtab_idx].data;
751 /* Go through all symbols and make sure the section they
752 reference is not removed. */
753 size_t elsize = gelf_fsize (elf, ELF_T_SYM, 1,
756 for (size_t inner = 0;
757 inner < shdr_info[cnt].data->d_size / elsize;
762 GElf_Sym *sym = gelf_getsymshndx (symdata, xndxdata,
766 INTERNAL_ERROR (fname);
768 size_t scnidx = sym->st_shndx;
769 if (scnidx == SHN_UNDEF || scnidx >= shnum
770 || (scnidx >= SHN_LORESERVE
771 && scnidx <= SHN_HIRESERVE
772 && scnidx != SHN_XINDEX)
773 /* Don't count in the section symbols. */
774 || GELF_ST_TYPE (sym->st_info) == STT_SECTION)
775 /* This is no section index, leave it alone. */
777 else if (scnidx == SHN_XINDEX)
780 if (shdr_info[scnidx].idx == 0)
782 /* Mark this section as used. */
783 shdr_info[scnidx].idx = 1;
784 changes |= scnidx < cnt;
789 /* Cross referencing happens:
790 - for the cases the ELF specification says. That are
791 + SHT_DYNAMIC in sh_link to string table
792 + SHT_HASH in sh_link to symbol table
793 + SHT_REL and SHT_RELA in sh_link to symbol table
794 + SHT_SYMTAB and SHT_DYNSYM in sh_link to string table
795 + SHT_GROUP in sh_link to symbol table
796 + SHT_SYMTAB_SHNDX in sh_link to symbol table
797 Other (OS or architecture-specific) sections might as
798 well use this field so we process it unconditionally.
799 - references inside section groups
800 - specially marked references in sh_info if the SHF_INFO_LINK
804 if (shdr_info[shdr_info[cnt].shdr.sh_link].idx == 0)
806 shdr_info[shdr_info[cnt].shdr.sh_link].idx = 1;
807 changes |= shdr_info[cnt].shdr.sh_link < cnt;
810 /* Handle references through sh_info. */
811 if (SH_INFO_LINK_P (&shdr_info[cnt].shdr)
812 && shdr_info[shdr_info[cnt].shdr.sh_info].idx == 0)
814 shdr_info[shdr_info[cnt].shdr.sh_info].idx = 1;
815 changes |= shdr_info[cnt].shdr.sh_info < cnt;
818 /* Mark the section as investigated. */
819 shdr_info[cnt].idx = 2;
825 /* Copy the removed sections to the debug output file.
826 The ones that are not removed in the stripped file are SHT_NOBITS. */
827 if (debug_fname != NULL)
829 for (cnt = 1; cnt < shnum; ++cnt)
831 scn = elf_newscn (debugelf);
833 error (EXIT_FAILURE, 0,
834 gettext ("while generating output file: %s"),
837 bool discard_section = (shdr_info[cnt].idx > 0
838 && cnt != ehdr->e_shstrndx);
840 /* Set the section header in the new file. */
841 GElf_Shdr debugshdr = shdr_info[cnt].shdr;
843 debugshdr.sh_type = SHT_NOBITS;
845 if (unlikely (gelf_update_shdr (scn, &debugshdr)) == 0)
846 /* There cannot be any overflows. */
847 INTERNAL_ERROR (fname);
849 /* Get the data from the old file if necessary. */
850 if (shdr_info[cnt].data == NULL)
852 shdr_info[cnt].data = elf_getdata (shdr_info[cnt].scn, NULL);
853 if (shdr_info[cnt].data == NULL)
854 INTERNAL_ERROR (fname);
857 /* Set the data. This is done by copying from the old file. */
858 Elf_Data *debugdata = elf_newdata (scn);
859 if (debugdata == NULL)
860 INTERNAL_ERROR (fname);
862 /* Copy the structure. This data may be modified in place
863 before we write out the file. */
864 *debugdata = *shdr_info[cnt].data;
866 debugdata->d_buf = NULL;
869 /* Finish the ELF header. Fill in the fields not handled by
870 libelf from the old file. */
871 debugehdr = gelf_getehdr (debugelf, &debugehdr_mem);
872 if (debugehdr == NULL)
873 INTERNAL_ERROR (fname);
875 memcpy (debugehdr->e_ident, ehdr->e_ident, EI_NIDENT);
876 debugehdr->e_type = ehdr->e_type;
877 debugehdr->e_machine = ehdr->e_machine;
878 debugehdr->e_version = ehdr->e_version;
879 debugehdr->e_entry = ehdr->e_entry;
880 debugehdr->e_flags = ehdr->e_flags;
881 debugehdr->e_shstrndx = ehdr->e_shstrndx;
883 if (unlikely (gelf_update_ehdr (debugelf, debugehdr)) == 0)
885 error (0, 0, gettext ("%s: error while creating ELF header: %s"),
886 debug_fname, elf_errmsg (-1));
892 /* Mark the section header string table as unused, we will create
894 shdr_info[shstrndx].idx = 0;
896 /* We need a string table for the section headers. */
897 shst = ebl_strtabinit (true);
899 error (EXIT_FAILURE, errno, gettext ("while preparing output for '%s'"),
900 output_fname ?: fname);
902 /* Assign new section numbers. */
903 shdr_info[0].idx = 0;
904 for (cnt = idx = 1; cnt < shnum; ++cnt)
905 if (shdr_info[cnt].idx > 0)
907 shdr_info[cnt].idx = idx++;
909 /* Create a new section. */
910 shdr_info[cnt].newscn = elf_newscn (newelf);
911 if (shdr_info[cnt].newscn == NULL)
912 error (EXIT_FAILURE, 0, gettext ("while generating output file: %s"),
915 assert (elf_ndxscn (shdr_info[cnt].newscn) == shdr_info[cnt].idx);
917 /* Add this name to the section header string table. */
918 shdr_info[cnt].se = ebl_strtabadd (shst, shdr_info[cnt].name, 0);
921 /* Test whether we are doing anything at all. */
923 /* Nope, all removable sections are already gone. */
926 /* Create the reference to the file with the debug info. */
927 if (debug_fname != NULL)
929 /* Add the section header string table section name. */
930 shdr_info[cnt].se = ebl_strtabadd (shst, ".gnu_debuglink", 15);
931 shdr_info[cnt].idx = idx++;
933 /* Create the section header. */
934 shdr_info[cnt].shdr.sh_type = SHT_PROGBITS;
935 shdr_info[cnt].shdr.sh_flags = 0;
936 shdr_info[cnt].shdr.sh_addr = 0;
937 shdr_info[cnt].shdr.sh_link = SHN_UNDEF;
938 shdr_info[cnt].shdr.sh_info = SHN_UNDEF;
939 shdr_info[cnt].shdr.sh_entsize = 0;
940 shdr_info[cnt].shdr.sh_addralign = 4;
941 /* We set the offset to zero here. Before we write the ELF file the
942 field must have the correct value. This is done in the final
943 loop over all section. Then we have all the information needed. */
944 shdr_info[cnt].shdr.sh_offset = 0;
946 /* Create the section. */
947 shdr_info[cnt].newscn = elf_newscn (newelf);
948 if (shdr_info[cnt].newscn == NULL)
949 error (EXIT_FAILURE, 0,
950 gettext ("while create section header section: %s"),
952 assert (elf_ndxscn (shdr_info[cnt].newscn) == shdr_info[cnt].idx);
954 shdr_info[cnt].data = elf_newdata (shdr_info[cnt].newscn);
955 if (shdr_info[cnt].data == NULL)
956 error (EXIT_FAILURE, 0, gettext ("cannot allocate section data: %s"),
959 char *debug_basename = basename (debug_fname_embed ?: debug_fname);
960 off_t crc_offset = strlen (debug_basename) + 1;
961 /* Align to 4 byte boundary */
962 crc_offset = ((crc_offset - 1) & ~3) + 4;
964 shdr_info[cnt].data->d_align = 4;
965 shdr_info[cnt].shdr.sh_size = shdr_info[cnt].data->d_size
967 shdr_info[cnt].data->d_buf = xcalloc (1, shdr_info[cnt].data->d_size);
969 strcpy (shdr_info[cnt].data->d_buf, debug_basename);
971 /* Cache this Elf_Data describing the CRC32 word in the section.
972 We'll fill this in when we have written the debug file. */
973 debuglink_crc_data = *shdr_info[cnt].data;
974 debuglink_crc_data.d_buf = ((char *) debuglink_crc_data.d_buf
976 debuglink_crc_data.d_size = 4;
978 /* One more section done. */
982 /* Index of the section header table in the shdr_info array. */
983 size_t shdridx = cnt;
985 /* Add the section header string table section name. */
986 shdr_info[cnt].se = ebl_strtabadd (shst, ".shstrtab", 10);
987 shdr_info[cnt].idx = idx;
989 /* Create the section header. */
990 shdr_info[cnt].shdr.sh_type = SHT_STRTAB;
991 shdr_info[cnt].shdr.sh_flags = 0;
992 shdr_info[cnt].shdr.sh_addr = 0;
993 shdr_info[cnt].shdr.sh_link = SHN_UNDEF;
994 shdr_info[cnt].shdr.sh_info = SHN_UNDEF;
995 shdr_info[cnt].shdr.sh_entsize = 0;
996 /* We set the offset to zero here. Before we write the ELF file the
997 field must have the correct value. This is done in the final
998 loop over all section. Then we have all the information needed. */
999 shdr_info[cnt].shdr.sh_offset = 0;
1000 shdr_info[cnt].shdr.sh_addralign = 1;
1002 /* Create the section. */
1003 shdr_info[cnt].newscn = elf_newscn (newelf);
1004 if (shdr_info[cnt].newscn == NULL)
1005 error (EXIT_FAILURE, 0,
1006 gettext ("while create section header section: %s"),
1008 assert (elf_ndxscn (shdr_info[cnt].newscn) == idx);
1010 /* Finalize the string table and fill in the correct indices in the
1012 shstrtab_data = elf_newdata (shdr_info[cnt].newscn);
1013 if (shstrtab_data == NULL)
1014 error (EXIT_FAILURE, 0,
1015 gettext ("while create section header string table: %s"),
1017 ebl_strtabfinalize (shst, shstrtab_data);
1019 /* We have to set the section size. */
1020 shdr_info[cnt].shdr.sh_size = shstrtab_data->d_size;
1022 /* Update the section information. */
1023 GElf_Off lastoffset = 0;
1024 for (cnt = 1; cnt <= shdridx; ++cnt)
1025 if (shdr_info[cnt].idx > 0)
1029 scn = elf_getscn (newelf, shdr_info[cnt].idx);
1030 assert (scn != NULL);
1032 /* Update the name. */
1033 shdr_info[cnt].shdr.sh_name = ebl_strtaboffset (shdr_info[cnt].se);
1035 /* Update the section header from the input file. Some fields
1036 might be section indeces which now have to be adjusted. */
1037 if (shdr_info[cnt].shdr.sh_link != 0)
1038 shdr_info[cnt].shdr.sh_link =
1039 shdr_info[shdr_info[cnt].shdr.sh_link].idx;
1041 if (shdr_info[cnt].shdr.sh_type == SHT_GROUP)
1043 assert (shdr_info[cnt].data != NULL);
1045 Elf32_Word *grpref = (Elf32_Word *) shdr_info[cnt].data->d_buf;
1046 for (size_t inner = 0;
1047 inner < shdr_info[cnt].data->d_size / sizeof (Elf32_Word);
1049 grpref[inner] = shdr_info[grpref[inner]].idx;
1052 /* Handle the SHT_REL, SHT_RELA, and SHF_INFO_LINK flag. */
1053 if (SH_INFO_LINK_P (&shdr_info[cnt].shdr))
1054 shdr_info[cnt].shdr.sh_info =
1055 shdr_info[shdr_info[cnt].shdr.sh_info].idx;
1057 /* Get the data from the old file if necessary. We already
1058 created the data for the section header string table. */
1061 if (shdr_info[cnt].data == NULL)
1063 shdr_info[cnt].data = elf_getdata (shdr_info[cnt].scn, NULL);
1064 if (shdr_info[cnt].data == NULL)
1065 INTERNAL_ERROR (fname);
1068 /* Set the data. This is done by copying from the old file. */
1069 newdata = elf_newdata (scn);
1070 if (newdata == NULL)
1071 INTERNAL_ERROR (fname);
1073 /* Copy the structure. */
1074 *newdata = *shdr_info[cnt].data;
1076 /* We know the size. */
1077 shdr_info[cnt].shdr.sh_size = shdr_info[cnt].data->d_size;
1079 /* We have to adjust symtol tables. The st_shndx member might
1080 have to be updated. */
1081 if (shdr_info[cnt].shdr.sh_type == SHT_DYNSYM
1082 || shdr_info[cnt].shdr.sh_type == SHT_SYMTAB)
1084 Elf_Data *versiondata = NULL;
1085 Elf_Data *shndxdata = NULL;
1087 size_t elsize = gelf_fsize (elf, ELF_T_SYM, 1,
1090 if (shdr_info[cnt].symtab_idx != 0)
1092 assert (shdr_info[cnt].shdr.sh_type == SHT_SYMTAB_SHNDX);
1093 /* This section has extended section information.
1094 We have to modify that information, too. */
1095 shndxdata = elf_getdata (shdr_info[shdr_info[cnt].symtab_idx].scn,
1098 assert ((versiondata->d_size / sizeof (Elf32_Word))
1099 >= shdr_info[cnt].data->d_size / elsize);
1102 if (shdr_info[cnt].version_idx != 0)
1104 assert (shdr_info[cnt].shdr.sh_type == SHT_DYNSYM);
1105 /* This section has associated version
1106 information. We have to modify that
1107 information, too. */
1108 versiondata = elf_getdata (shdr_info[shdr_info[cnt].version_idx].scn,
1111 assert ((versiondata->d_size / sizeof (GElf_Versym))
1112 >= shdr_info[cnt].data->d_size / elsize);
1115 shdr_info[cnt].newsymidx
1116 = (Elf32_Word *) xcalloc (shdr_info[cnt].data->d_size
1117 / elsize, sizeof (Elf32_Word));
1119 bool last_was_local = true;
1122 for (destidx = inner = 1;
1123 inner < shdr_info[cnt].data->d_size / elsize;
1129 GElf_Sym *sym = gelf_getsymshndx (shdr_info[cnt].data,
1133 INTERNAL_ERROR (fname);
1135 if (sym->st_shndx == SHN_UNDEF
1136 || (sym->st_shndx >= shnum
1137 && sym->st_shndx != SHN_XINDEX))
1139 /* This is no section index, leave it alone
1140 unless it is moved. */
1141 if (destidx != inner
1142 && gelf_update_symshndx (shdr_info[cnt].data,
1146 INTERNAL_ERROR (fname);
1148 shdr_info[cnt].newsymidx[inner] = destidx++;
1151 && GELF_ST_BIND (sym->st_info) != STB_LOCAL)
1153 last_was_local = false;
1154 shdr_info[cnt].shdr.sh_info = destidx - 1;
1160 /* Get the full section index, if necessary from the
1162 if (sym->st_shndx != SHN_XINDEX)
1163 sec = shdr_info[sym->st_shndx].idx;
1166 assert (shndxdata != NULL);
1168 sec = shdr_info[xshndx].idx;
1173 GElf_Section nshndx;
1176 if (sec < SHN_LORESERVE)
1183 nshndx = SHN_XINDEX;
1187 assert (sec < SHN_LORESERVE || shndxdata != NULL);
1189 if ((inner != destidx || nshndx != sym->st_shndx
1190 || (shndxdata != NULL && nxshndx != xshndx))
1191 && (sym->st_shndx = nshndx,
1192 gelf_update_symshndx (shdr_info[cnt].data,
1196 INTERNAL_ERROR (fname);
1198 shdr_info[cnt].newsymidx[inner] = destidx++;
1201 && GELF_ST_BIND (sym->st_info) != STB_LOCAL)
1203 last_was_local = false;
1204 shdr_info[cnt].shdr.sh_info = destidx - 1;
1208 /* This is a section symbol for a section which has
1210 assert (GELF_ST_TYPE (sym->st_info) == STT_SECTION);
1213 if (destidx != inner)
1215 /* The size of the symbol table changed. */
1216 shdr_info[cnt].shdr.sh_size = newdata->d_size
1218 any_symtab_changes = true;
1222 /* The symbol table didn't really change. */
1223 free (shdr_info[cnt].newsymidx);
1224 shdr_info[cnt].newsymidx = NULL;
1229 /* If we have to, compute the offset of the section. */
1230 if (shdr_info[cnt].shdr.sh_offset == 0)
1231 shdr_info[cnt].shdr.sh_offset
1232 = ((lastoffset + shdr_info[cnt].shdr.sh_addralign - 1)
1233 & ~((GElf_Off) (shdr_info[cnt].shdr.sh_addralign - 1)));
1235 /* Set the section header in the new file. */
1236 if (unlikely (gelf_update_shdr (scn, &shdr_info[cnt].shdr) == 0))
1237 /* There cannot be any overflows. */
1238 INTERNAL_ERROR (fname);
1240 /* Remember the last section written so far. */
1241 GElf_Off filesz = (shdr_info[cnt].shdr.sh_type != SHT_NOBITS
1242 ? shdr_info[cnt].shdr.sh_size : 0);
1243 if (lastoffset < shdr_info[cnt].shdr.sh_offset + filesz)
1244 lastoffset = shdr_info[cnt].shdr.sh_offset + filesz;
1247 /* Adjust symbol references if symbol tables changed. */
1248 if (any_symtab_changes)
1250 /* Find all relocation sections which use this
1252 for (cnt = 1; cnt <= shdridx; ++cnt)
1254 if (shdr_info[cnt].idx == 0 && debug_fname == NULL)
1255 /* Ignore sections which are discarded. When we are saving a
1256 relocation section in a separate debug file, we must fix up
1257 the symbol table references. */
1260 if (shdr_info[cnt].shdr.sh_type == SHT_REL
1261 || shdr_info[cnt].shdr.sh_type == SHT_RELA)
1263 /* If the symbol table hasn't changed, do not do anything. */
1264 if (shdr_info[shdr_info[cnt].old_sh_link].newsymidx == NULL)
1267 Elf32_Word *newsymidx
1268 = shdr_info[shdr_info[cnt].old_sh_link].newsymidx;
1269 Elf_Data *d = elf_getdata (shdr_info[cnt].idx == 0
1270 ? elf_getscn (debugelf, cnt)
1271 : elf_getscn (newelf,
1272 shdr_info[cnt].idx),
1275 size_t nrels = (shdr_info[cnt].shdr.sh_size
1276 / shdr_info[cnt].shdr.sh_entsize);
1278 if (shdr_info[cnt].shdr.sh_type == SHT_REL)
1279 for (size_t relidx = 0; relidx < nrels; ++relidx)
1282 if (gelf_getrel (d, relidx, &rel_mem) == NULL)
1283 INTERNAL_ERROR (fname);
1285 size_t symidx = GELF_R_SYM (rel_mem.r_info);
1286 if (newsymidx[symidx] != symidx)
1289 = GELF_R_INFO (newsymidx[symidx],
1290 GELF_R_TYPE (rel_mem.r_info));
1292 if (gelf_update_rel (d, relidx, &rel_mem) == 0)
1293 INTERNAL_ERROR (fname);
1297 for (size_t relidx = 0; relidx < nrels; ++relidx)
1300 if (gelf_getrela (d, relidx, &rel_mem) == NULL)
1301 INTERNAL_ERROR (fname);
1303 size_t symidx = GELF_R_SYM (rel_mem.r_info);
1304 if (newsymidx[symidx] != symidx)
1307 = GELF_R_INFO (newsymidx[symidx],
1308 GELF_R_TYPE (rel_mem.r_info));
1310 if (gelf_update_rela (d, relidx, &rel_mem) == 0)
1311 INTERNAL_ERROR (fname);
1315 else if (shdr_info[cnt].shdr.sh_type == SHT_HASH)
1317 /* We have to recompute the hash table. */
1318 Elf32_Word symtabidx = shdr_info[cnt].old_sh_link;
1320 /* We do not have to do anything if the symbol table was
1322 if (shdr_info[symtabidx].newsymidx == NULL)
1325 assert (shdr_info[cnt].idx > 0);
1327 /* The hash section in the new file. */
1328 scn = elf_getscn (newelf, shdr_info[cnt].idx);
1330 /* The symbol table data. */
1331 Elf_Data *symd = elf_getdata (elf_getscn (newelf,
1332 shdr_info[symtabidx].idx),
1334 assert (symd != NULL);
1336 /* The hash table data. */
1337 Elf_Data *hashd = elf_getdata (scn, NULL);
1338 assert (hashd != NULL);
1340 if (shdr_info[cnt].shdr.sh_entsize == sizeof (Elf32_Word))
1342 /* Sane arches first. */
1343 Elf32_Word *bucket = (Elf32_Word *) hashd->d_buf;
1345 size_t strshndx = shdr_info[symtabidx].old_sh_link;
1346 size_t elsize = gelf_fsize (elf, ELF_T_SYM, 1,
1349 /* Adjust the nchain value. The symbol table size
1350 changed. We keep the same size for the bucket array. */
1351 bucket[1] = symd->d_size / elsize;
1352 Elf32_Word nbucket = bucket[0];
1354 Elf32_Word *chain = bucket + nbucket;
1356 /* New size of the section. */
1358 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1359 shdr->sh_size = hashd->d_size
1360 = (2 + symd->d_size / elsize + nbucket)
1361 * sizeof (Elf32_Word);
1362 (void) gelf_update_shdr (scn, shdr);
1364 /* Clear the arrays. */
1365 memset (bucket, '\0',
1366 (symd->d_size / elsize + nbucket)
1367 * sizeof (Elf32_Word));
1369 for (size_t inner = shdr_info[symtabidx].shdr.sh_info;
1370 inner < symd->d_size / elsize; ++inner)
1373 GElf_Sym *sym = gelf_getsym (symd, inner, &sym_mem);
1374 assert (sym != NULL);
1376 const char *name = elf_strptr (elf, strshndx,
1378 assert (name != NULL);
1379 size_t hidx = elf_hash (name) % nbucket;
1381 if (bucket[hidx] == 0)
1382 bucket[hidx] = inner;
1385 hidx = bucket[hidx];
1387 while (chain[hidx] != 0)
1390 chain[hidx] = inner;
1396 /* Alpha and S390 64-bit use 64-bit SHT_HASH entries. */
1397 assert (shdr_info[cnt].shdr.sh_entsize
1398 == sizeof (Elf64_Xword));
1400 Elf64_Xword *bucket = (Elf64_Xword *) hashd->d_buf;
1402 size_t strshndx = shdr_info[symtabidx].old_sh_link;
1403 size_t elsize = gelf_fsize (elf, ELF_T_SYM, 1,
1406 /* Adjust the nchain value. The symbol table size
1407 changed. We keep the same size for the bucket array. */
1408 bucket[1] = symd->d_size / elsize;
1409 Elf64_Xword nbucket = bucket[0];
1411 Elf64_Xword *chain = bucket + nbucket;
1413 /* New size of the section. */
1415 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1416 shdr->sh_size = hashd->d_size
1417 = (2 + symd->d_size / elsize + nbucket)
1418 * sizeof (Elf64_Xword);
1419 (void) gelf_update_shdr (scn, shdr);
1421 /* Clear the arrays. */
1422 memset (bucket, '\0',
1423 (symd->d_size / elsize + nbucket)
1424 * sizeof (Elf64_Xword));
1426 for (size_t inner = shdr_info[symtabidx].shdr.sh_info;
1427 inner < symd->d_size / elsize; ++inner)
1430 GElf_Sym *sym = gelf_getsym (symd, inner, &sym_mem);
1431 assert (sym != NULL);
1433 const char *name = elf_strptr (elf, strshndx,
1435 assert (name != NULL);
1436 size_t hidx = elf_hash (name) % nbucket;
1438 if (bucket[hidx] == 0)
1439 bucket[hidx] = inner;
1442 hidx = bucket[hidx];
1444 while (chain[hidx] != 0)
1447 chain[hidx] = inner;
1452 else if (shdr_info[cnt].shdr.sh_type == SHT_GNU_versym)
1454 /* If the symbol table changed we have to adjust the
1456 Elf32_Word symtabidx = shdr_info[cnt].old_sh_link;
1458 /* We do not have to do anything if the symbol table was
1460 if (shdr_info[symtabidx].newsymidx == NULL)
1463 assert (shdr_info[cnt].idx > 0);
1465 /* The symbol version section in the new file. */
1466 scn = elf_getscn (newelf, shdr_info[cnt].idx);
1468 /* The symbol table data. */
1469 Elf_Data *symd = elf_getdata (elf_getscn (newelf,
1470 shdr_info[symtabidx].idx),
1472 assert (symd != NULL);
1474 /* The version symbol data. */
1475 Elf_Data *verd = elf_getdata (scn, NULL);
1476 assert (verd != NULL);
1478 /* The symbol version array. */
1479 GElf_Half *verstab = (GElf_Half *) verd->d_buf;
1481 /* New indices of the symbols. */
1482 Elf32_Word *newsymidx = shdr_info[symtabidx].newsymidx;
1484 /* Walk through the list and */
1485 size_t elsize = gelf_fsize (elf, verd->d_type, 1,
1487 for (size_t inner = 1; inner < verd->d_size / elsize; ++inner)
1488 if (newsymidx[inner] != 0)
1489 /* Overwriting the same array works since the
1490 reordering can only move entries to lower indices
1492 verstab[newsymidx[inner]] = verstab[inner];
1494 /* New size of the section. */
1496 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1497 shdr->sh_size = verd->d_size
1498 = gelf_fsize (newelf, verd->d_type,
1499 symd->d_size / gelf_fsize (elf, symd->d_type, 1,
1502 (void) gelf_update_shdr (scn, shdr);
1504 else if (shdr_info[cnt].shdr.sh_type == SHT_GROUP)
1506 /* Check whether the associated symbol table changed. */
1507 if (shdr_info[shdr_info[cnt].old_sh_link].newsymidx != NULL)
1509 /* Yes the symbol table changed. Update the section
1510 header of the section group. */
1511 scn = elf_getscn (newelf, shdr_info[cnt].idx);
1513 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
1514 assert (shdr != NULL);
1516 size_t stabidx = shdr_info[cnt].old_sh_link;
1517 shdr->sh_info = shdr_info[stabidx].newsymidx[shdr->sh_info];
1519 (void) gelf_update_shdr (scn, shdr);
1525 /* Now that we have done all adjustments to the data,
1526 we can actually write out the debug file. */
1527 if (debug_fname != NULL)
1530 Elf_Data debug_crc_data =
1532 .d_type = ELF_T_WORD,
1533 .d_buf = &debug_crc,
1534 .d_size = sizeof (debug_crc),
1535 .d_version = EV_CURRENT
1538 /* Finally write the file. */
1539 if (unlikely (elf_update (debugelf, ELF_C_WRITE)) == -1)
1541 error (0, 0, gettext ("while writing '%s': %s"),
1542 debug_fname, elf_errmsg (-1));
1547 /* Create the real output file. First rename, then change the
1549 if (rename (tmp_debug_fname, debug_fname) != 0
1550 || fchmod (debug_fd, mode) != 0)
1552 error (0, errno, gettext ("while creating '%s'"), debug_fname);
1557 /* The temporary file does not exist anymore. */
1558 tmp_debug_fname = NULL;
1560 /* Compute the checksum which we will add to the executable. */
1561 if (crc32_file (debug_fd, &debug_crc) != 0)
1564 gettext ("while computing checksum for debug information"));
1565 unlink (debug_fname);
1570 /* Store it in the debuglink section data. */
1571 if (unlikely (gelf_xlatetof (newelf, &debuglink_crc_data,
1572 &debug_crc_data, ehdr->e_ident[EI_DATA])
1573 != &debuglink_crc_data))
1574 INTERNAL_ERROR (fname);
1577 /* Finally finish the ELF header. Fill in the fields not handled by
1578 libelf from the old file. */
1579 newehdr = gelf_getehdr (newelf, &newehdr_mem);
1580 if (newehdr == NULL)
1581 INTERNAL_ERROR (fname);
1583 memcpy (newehdr->e_ident, ehdr->e_ident, EI_NIDENT);
1584 newehdr->e_type = ehdr->e_type;
1585 newehdr->e_machine = ehdr->e_machine;
1586 newehdr->e_version = ehdr->e_version;
1587 newehdr->e_entry = ehdr->e_entry;
1588 newehdr->e_flags = ehdr->e_flags;
1589 newehdr->e_phoff = ehdr->e_phoff;
1590 /* We need to position the section header table. */
1591 const size_t offsize = gelf_fsize (elf, ELF_T_OFF, 1, EV_CURRENT);
1592 newehdr->e_shoff = ((shdr_info[shdridx].shdr.sh_offset
1593 + shdr_info[shdridx].shdr.sh_size + offsize - 1)
1594 & ~((GElf_Off) (offsize - 1)));
1595 newehdr->e_shentsize = gelf_fsize (elf, ELF_T_SHDR, 1, EV_CURRENT);
1597 /* The new section header string table index. */
1598 if (likely (idx < SHN_HIRESERVE) && likely (idx != SHN_XINDEX))
1599 newehdr->e_shstrndx = idx;
1602 /* The index does not fit in the ELF header field. */
1603 shdr_info[0].scn = elf_getscn (elf, 0);
1605 if (gelf_getshdr (shdr_info[0].scn, &shdr_info[0].shdr) == NULL)
1606 INTERNAL_ERROR (fname);
1608 shdr_info[0].shdr.sh_link = idx;
1609 (void) gelf_update_shdr (shdr_info[0].scn, &shdr_info[0].shdr);
1611 newehdr->e_shstrndx = SHN_XINDEX;
1614 if (gelf_update_ehdr (newelf, newehdr) == 0)
1616 error (0, 0, gettext ("%s: error while creating ELF header: %s"),
1617 fname, elf_errmsg (-1));
1621 /* We have everything from the old file. */
1622 if (elf_cntl (elf, ELF_C_FDDONE) != 0)
1624 error (0, 0, gettext ("%s: error while reading the file: %s"),
1625 fname, elf_errmsg (-1));
1629 /* The ELF library better follows our layout when this is not a
1630 relocatable object file. */
1631 elf_flagelf (newelf, ELF_C_SET,
1632 (ehdr->e_type != ET_REL ? ELF_F_LAYOUT : 0)
1633 | (permissive ? ELF_F_PERMISSIVE : 0));
1635 /* Finally write the file. */
1636 if (elf_update (newelf, ELF_C_WRITE) == -1)
1638 error (0, 0, gettext ("while writing '%s': %s"),
1639 fname, elf_errmsg (-1));
1644 if (shdr_info != NULL)
1646 /* For some sections we might have created an table to map symbol
1648 if (any_symtab_changes)
1649 for (cnt = 1; cnt <= shdridx; ++cnt)
1650 free (shdr_info[cnt].newsymidx);
1652 /* Free the memory. */
1653 if ((shnum + 2) * sizeof (struct shdr_info) > MAX_STACK_ALLOC)
1657 /* Free other resources. */
1658 if (shstrtab_data != NULL)
1659 free (shstrtab_data->d_buf);
1661 ebl_strtabfree (shst);
1663 /* That was it. Close the descriptors. */
1664 if (elf_end (newelf) != 0)
1666 error (0, 0, gettext ("error while finishing '%s': %s"), fname,
1671 if (debugelf != NULL && elf_end (debugelf) != 0)
1673 error (0, 0, gettext ("error while finishing '%s': %s"), debug_fname,
1679 /* Close the EBL backend. */
1681 ebl_closebackend (ebl);
1683 /* Close debug file descriptor, if opened */
1686 if (tmp_debug_fname != NULL)
1687 unlink (tmp_debug_fname);
1691 /* If requested, preserve the timestamp. */
1694 if (futimes (fd, tvp) != 0)
1696 error (0, errno, gettext ("\
1697 cannot set access and modification date of '%s'"),
1698 output_fname ?: fname);
1703 /* Close the file descriptor if we created a new file. */
1704 if (output_fname != NULL)
1712 handle_ar (int fd, Elf *elf, const char *prefix, const char *fname,
1713 struct timeval tvp[2])
1715 size_t prefix_len = prefix == NULL ? 0 : strlen (prefix);
1716 size_t fname_len = strlen (fname) + 1;
1717 char new_prefix[prefix_len + 1 + fname_len];
1718 char *cp = new_prefix;
1720 /* Create the full name of the file. */
1723 cp = mempcpy (cp, prefix, prefix_len);
1726 memcpy (cp, fname, fname_len);
1729 /* Process all the files contained in the archive. */
1731 Elf_Cmd cmd = ELF_C_RDWR;
1733 while ((subelf = elf_begin (fd, cmd, elf)) != NULL)
1735 /* The the header for this element. */
1736 Elf_Arhdr *arhdr = elf_getarhdr (subelf);
1738 if (elf_kind (subelf) == ELF_K_ELF)
1739 result |= handle_elf (fd, subelf, new_prefix, arhdr->ar_name, 0, NULL);
1740 else if (elf_kind (subelf) == ELF_K_AR)
1741 result |= handle_ar (fd, subelf, new_prefix, arhdr->ar_name, NULL);
1743 /* Get next archive element. */
1744 cmd = elf_next (subelf);
1745 if (unlikely (elf_end (subelf) != 0))
1746 INTERNAL_ERROR (fname);
1751 if (unlikely (futimes (fd, tvp) != 0))
1753 error (0, errno, gettext ("\
1754 cannot set access and modification date of '%s'"), fname);
1759 if (unlikely (close (fd) != 0))
1760 error (EXIT_FAILURE, errno, gettext ("while closing '%s'"), fname);