annotate src/unexsni.c @ 939:025200a2163c

[xemacs-hg @ 2002-07-31 07:23:39 by michaels] 2002-07-17 Marcus Crestani <crestani@informatik.uni-tuebingen.de> Markus Kaltenbach <makalten@informatik.uni-tuebingen.de> Mike Sperber <mike@xemacs.org> configure flag to turn these changes on: --use-kkcc First we added a dumpable flag to lrecord_implementation. It shows, if the object is dumpable and should be processed by the dumper. * lrecord.h (struct lrecord_implementation): added dumpable flag (MAKE_LRECORD_IMPLEMENTATION): fitted the different makro definitions to the new lrecord_implementation and their calls. Then we changed mark_object, that it no longer needs a mark method for those types that have pdump descritions. * alloc.c: (mark_object): If the object has a description, the new mark algorithm is called, and the object is marked according to its description. Otherwise it uses the mark method like before. These procedures mark objects according to their descriptions. They are modeled on the corresponding pdumper procedures. (mark_with_description): (get_indirect_count): (structure_size): (mark_struct_contents): These procedures still call mark_object, this is needed while there are Lisp_Objects without descriptions left. We added pdump descriptions for many Lisp_Objects: * extents.c: extent_auxiliary_description * database.c: database_description * gui.c: gui_item_description * scrollbar.c: scrollbar_instance_description * toolbar.c: toolbar_button_description * event-stream.c: command_builder_description * mule-charset.c: charset_description * device-msw.c: devmode_description * dialog-msw.c: mswindows_dialog_id_description * eldap.c: ldap_description * postgresql.c: pgconn_description pgresult_description * tooltalk.c: tooltalk_message_description tooltalk_pattern_description * ui-gtk.c: emacs_ffi_description emacs_gtk_object_description * events.c: * events.h: * event-stream.c: * event-Xt.c: * event-gtk.c: * event-tty.c: To write a pdump description for Lisp_Event, we converted every struct in the union event to a Lisp_Object. So we created nine new Lisp_Objects: Lisp_Key_Data, Lisp_Button_Data, Lisp_Motion_Data, Lisp_Process_Data, Lisp_Timeout_Data, Lisp_Eval_Data, Lisp_Misc_User_Data, Lisp_Magic_Data, Lisp_Magic_Eval_Data. We also wrote makro selectors and mutators for the fields of the new designed Lisp_Event and added everywhere these new abstractions. We implemented XD_UNION support in (mark_with_description), so we can describe exspecially console/device specific data with XD_UNION. To describe with XD_UNION, we added a field to these objects, which holds the variant type of the object. This field is initialized in the appendant constructor. The variant is an integer, it has also to be described in an description, if XD_UNION is used. XD_UNION is used in following descriptions: * console.c: console_description (get_console_variant): returns the variant (create_console): added variant initialization * console.h (console_variant): the different console types * console-impl.h (struct console): added enum console_variant contype * device.c: device_description (Fmake_device): added variant initialization * device-impl.h (struct device): added enum console_variant devtype * objects.c: image_instance_description font_instance_description (Fmake_color_instance): added variant initialization (Fmake_font_instance): added variant initialization * objects-impl.h (struct Lisp_Color_Instance): added color_instance_type * objects-impl.h (struct Lisp_Font_Instance): added font_instance_type * process.c: process_description (make_process_internal): added variant initialization * process.h (process_variant): the different process types
author michaels
date Wed, 31 Jul 2002 07:23:39 +0000
parents 943eaba38521
children 04bc9d2f42c7
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
1 /* Unexec for Siemens machines running Sinix (modified SVR4).
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
2 Copyright (C) 1985, 1986, 1987, 1988, 1990, 1992, 1993, 1994, 1995
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
3 Free Software Foundation, Inc.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
4
613
023b83f4e54b [xemacs-hg @ 2001-06-10 10:42:16 by ben]
ben
parents: 0
diff changeset
5 This file is part of XEmacs.
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
6
613
023b83f4e54b [xemacs-hg @ 2001-06-10 10:42:16 by ben]
ben
parents: 0
diff changeset
7 XEmacs is free software; you can redistribute it and/or modify
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
8 it under the terms of the GNU General Public License as published by
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
9 the Free Software Foundation; either version 2, or (at your option)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
10 any later version.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
11
613
023b83f4e54b [xemacs-hg @ 2001-06-10 10:42:16 by ben]
ben
parents: 0
diff changeset
12 XEmacs is distributed in the hope that it will be useful,
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
15 GNU General Public License for more details.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
16
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
17 You should have received a copy of the GNU General Public License
613
023b83f4e54b [xemacs-hg @ 2001-06-10 10:42:16 by ben]
ben
parents: 0
diff changeset
18 along with XEmacs; see the file COPYING. If not, write to
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
20 Boston, MA 02111-1307, USA.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
21
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
22 In other words, you are welcome to use, share and improve this program.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
23 You are forbidden to forbid anyone else to use, share and improve
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
24 what you give them. Help stamp out software-hoarding! */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
25
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
26 /* Synched up with: FSF 19.31. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
27
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
28 /*
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
29 * unexec.c - Convert a running program into an a.out file.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
30 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
31 * Author: Spencer W. Thomas
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
32 * Computer Science Dept.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
33 * University of Utah
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
34 * Date: Tue Mar 2 1982
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
35 * Modified heavily since then.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
36 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
37 * Synopsis:
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
38 * unexec (new_name, a_name, data_start, bss_start, entry_address)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
39 * char *new_name, *a_name;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
40 * unsigned data_start, bss_start, entry_address;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
41 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
42 * Takes a snapshot of the program and makes an a.out format file in the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
43 * file named by the string argument new_name.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
44 * If a_name is non-NULL, the symbol table will be taken from the given file.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
45 * On some machines, an existing a_name file is required.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
46 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
47 * The boundaries within the a.out file may be adjusted with the data_start
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
48 * and bss_start arguments. Either or both may be given as 0 for defaults.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
49 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
50 * Data_start gives the boundary between the text segment and the data
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
51 * segment of the program. The text segment can contain shared, read-only
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
52 * program code and literal data, while the data segment is always unshared
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
53 * and unprotected. Data_start gives the lowest unprotected address.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
54 * The value you specify may be rounded down to a suitable boundary
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
55 * as required by the machine you are using.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
56 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
57 * Specifying zero for data_start means the boundary between text and data
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
58 * should not be the same as when the program was loaded.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
59 * If NO_REMAP is defined, the argument data_start is ignored and the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
60 * segment boundaries are never changed.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
61 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
62 * Bss_start indicates how much of the data segment is to be saved in the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
63 * a.out file and restored when the program is executed. It gives the lowest
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
64 * unsaved address, and is rounded up to a page boundary. The default when 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
65 * is given assumes that the entire data segment is to be stored, including
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
66 * the previous data and bss as well as any additional storage allocated with
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
67 * break (2).
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
68 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
69 * The new file is set up to start at entry_address.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
70 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
71 * If you make improvements I'd like to get them too.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
72 * harpo!utah-cs!thomas, thomas@Utah-20
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
73 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
74 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
75
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
76 /* Even more heavily modified by james@bigtex.cactus.org of Dell Computer Co.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
77 * ELF support added.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
78 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
79 * Basic theory: the data space of the running process needs to be
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
80 * dumped to the output file. Normally we would just enlarge the size
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
81 * of .data, scooting everything down. But we can't do that in ELF,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
82 * because there is often something between the .data space and the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
83 * .bss space.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
84 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
85 * In the temacs dump below, notice that the Global Offset Table
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
86 * (.got) and the Dynamic link data (.dynamic) come between .data1 and
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
87 * .bss. It does not work to overlap .data with these fields.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
88 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
89 * The solution is to create a new .data segment. This segment is
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
90 * filled with data from the current process. Since the contents of
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
91 * various sections refer to sections by index, the new .data segment
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
92 * is made the last in the table to avoid changing any existing index.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
93 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
94
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
95 /* Modified by wtien@urbana.mcd.mot.com of Motorola Inc.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
96 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
97 * The above mechanism does not work if the unexeced ELF file is being
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
98 * re-layout by other applications (such as `strip'). All the applications
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
99 * that re-layout the internal of ELF will layout all sections in ascending
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
100 * order of their file offsets. After the re-layout, the data2 section will
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
101 * still be the LAST section in the section header vector, but its file offset
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
102 * is now being pushed far away down, and causes part of it not to be mapped
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
103 * in (ie. not covered by the load segment entry in PHDR vector), therefore
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
104 * causes the new binary to fail.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
105 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
106 * The solution is to modify the unexec algorithm to insert the new data2
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
107 * section header right before the new bss section header, so their file
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
108 * offsets will be in the ascending order. Since some of the section's (all
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
109 * sections AFTER the bss section) indexes are now changed, we also need to
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
110 * modify some fields to make them point to the right sections. This is done
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
111 * by macro PATCH_INDEX. All the fields that need to be patched are:
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
112 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
113 * 1. ELF header e_shstrndx field.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
114 * 2. section header sh_link and sh_info field.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
115 * 3. symbol table entry st_shndx field.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
116 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
117
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
118 /*
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
119 * New modifications for Siemens Nixdorf's MIPS-based machines.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
120 * Marco.Walther@mch.sni.de
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
121 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
122 * The problem: Before the bss segment we have a so called sbss segment
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
123 * (small bss) and maybe an sdata segment. These segments
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
124 * must also be handled correct.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
125 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
126 * /home1/marco/emacs/emacs-19.22/src
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
127 * dump -hv temacs
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
128 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
129 * temacs:
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
130 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
131 * **** SECTION HEADER TABLE ****
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
132 * [No] Type Flags Addr Offset Size Name
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
133 * Link Info Adralgn Entsize
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
134 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
135 * [1] PBIT -A-- 0x4000f4 0xf4 0x13 .interp
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
136 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
137 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
138 * [2] REGI -A-- 0x400108 0x108 0x18 .reginfo
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
139 * 0 0 0x4 0x18
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
140 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
141 * [3] DYNM -A-- 0x400120 0x120 0xb8 .dynamic
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
142 * 6 0 0x4 0x8
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
143 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
144 * [4] HASH -A-- 0x4001d8 0x1d8 0x8a0 .hash
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
145 * 5 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
146 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
147 * [5] DYNS -A-- 0x400a78 0xa78 0x11f0 .dynsym
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
148 * 6 2 0x4 0x10
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
149 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
150 * [6] STRT -A-- 0x401c68 0x1c68 0xbf9 .dynstr
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
151 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
152 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
153 * [7] REL -A-- 0x402864 0x2864 0x18 .rel.dyn
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
154 * 5 14 0x4 0x8
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
155 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
156 * [8] PBIT -AI- 0x402880 0x2880 0x60 .init
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
157 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
158 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
159 * [9] PBIT -AI- 0x4028e0 0x28e0 0x1234 .plt
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
160 * 0 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
161 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
162 * [10] PBIT -AI- 0x403b20 0x3b20 0xee400 .text
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
163 * 0 0 0x20 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
164 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
165 * [11] PBIT -AI- 0x4f1f20 0xf1f20 0x60 .fini
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
166 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
167 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
168 * [12] PBIT -A-- 0x4f1f80 0xf1f80 0xd90 .rdata
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
169 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
170 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
171 * [13] PBIT -A-- 0x4f2d10 0xf2d10 0x17e0 .rodata
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
172 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
173 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
174 * [14] PBIT WA-- 0x5344f0 0xf44f0 0x4b3e4 .data <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
175 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
176 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
177 * [15] PBIT WA-G 0x57f8d4 0x13f8d4 0x2a84 .got
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
178 * 0 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
179 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
180 * [16] PBIT WA-G 0x582360 0x142360 0x10 .sdata <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
181 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
182 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
183 * [17] NOBI WA-G 0x582370 0x142370 0xb84 .sbss <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
184 * 0 0 0x4 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
185 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
186 * [18] NOBI WA-- 0x582f00 0x142370 0x27ec0 .bss <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
187 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
188 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
189 * [19] SYMT ---- 0 0x142370 0x10e40 .symtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
190 * 20 1108 0x4 0x10
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
191 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
192 * [20] STRT ---- 0 0x1531b0 0xed9e .strtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
193 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
194 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
195 * [21] STRT ---- 0 0x161f4e 0xb5 .shstrtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
196 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
197 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
198 * [22] PBIT ---- 0 0x162003 0x28e2a .comment
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
199 * 0 0 0x1 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
200 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
201 * [23] PBIT ---- 0 0x18ae2d 0x592 .debug
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
202 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
203 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
204 * [24] PBIT ---- 0 0x18b3bf 0x80 .line
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
205 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
206 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
207 * [25] MDBG ---- 0 0x18b440 0x60 .mdebug
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
208 * 0 0 0x4 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
209 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
210 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
211 * dump -hv emacs
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
212 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
213 * emacs:
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
214 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
215 * **** SECTION HEADER TABLE ****
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
216 * [No] Type Flags Addr Offset Size Name
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
217 * Link Info Adralgn Entsize
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
218 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
219 * [1] PBIT -A-- 0x4000f4 0xf4 0x13 .interp
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
220 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
221 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
222 * [2] REGI -A-- 0x400108 0x108 0x18 .reginfo
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
223 * 0 0 0x4 0x18
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
224 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
225 * [3] DYNM -A-- 0x400120 0x120 0xb8 .dynamic
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
226 * 6 0 0x4 0x8
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
227 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
228 * [4] HASH -A-- 0x4001d8 0x1d8 0x8a0 .hash
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
229 * 5 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
230 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
231 * [5] DYNS -A-- 0x400a78 0xa78 0x11f0 .dynsym
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
232 * 6 2 0x4 0x10
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
233 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
234 * [6] STRT -A-- 0x401c68 0x1c68 0xbf9 .dynstr
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
235 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
236 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
237 * [7] REL -A-- 0x402864 0x2864 0x18 .rel.dyn
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
238 * 5 14 0x4 0x8
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
239 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
240 * [8] PBIT -AI- 0x402880 0x2880 0x60 .init
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
241 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
242 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
243 * [9] PBIT -AI- 0x4028e0 0x28e0 0x1234 .plt
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
244 * 0 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
245 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
246 * [10] PBIT -AI- 0x403b20 0x3b20 0xee400 .text
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
247 * 0 0 0x20 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
248 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
249 * [11] PBIT -AI- 0x4f1f20 0xf1f20 0x60 .fini
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
250 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
251 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
252 * [12] PBIT -A-- 0x4f1f80 0xf1f80 0xd90 .rdata
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
253 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
254 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
255 * [13] PBIT -A-- 0x4f2d10 0xf2d10 0x17e0 .rodata
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
256 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
257 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
258 * [14] PBIT WA-- 0x5344f0 0xf44f0 0x4b3e4 .data <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
259 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
260 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
261 * [15] PBIT WA-G 0x57f8d4 0x13f8d4 0x2a84 .got
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
262 * 0 0 0x4 0x4
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
263 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
264 * [16] PBIT WA-G 0x582360 0x142360 0xb94 .sdata <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
265 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
266 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
267 * [17] PBIT WA-- 0x582f00 0x142f00 0x94100 .data <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
268 * 0 0 0x10 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
269 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
270 * [18] NOBI WA-G 0x617000 0x1d7000 0 .sbss <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
271 * 0 0 0x4 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
272 *
771
943eaba38521 [xemacs-hg @ 2002-03-13 08:51:24 by ben]
ben
parents: 613
diff changeset
273 * [19] NOBI WA-- 0x617000 0x1d7000 0 .bss <----
0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
274 * 0 0 0x4 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
275 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
276 * [20] SYMT ---- 0 0x1d7000 0x10e40 .symtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
277 * 21 1109 0x4 0x10
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
278 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
279 * [21] STRT ---- 0 0x1e7e40 0xed9e .strtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
280 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
281 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
282 * [22] STRT ---- 0 0x1f6bde 0xb5 .shstrtab
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
283 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
284 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
285 * [23] PBIT ---- 0 0x1f6c93 0x28e2a .comment
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
286 * 0 0 0x1 0x1
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
287 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
288 * [24] PBIT ---- 0 0x21fabd 0x592 .debug
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
289 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
290 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
291 * [25] PBIT ---- 0 0x22004f 0x80 .line
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
292 * 0 0 0x1 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
293 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
294 * [26] MDBG ---- 0 0x2200d0 0x60 .mdebug
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
295 * 0 0 0x4 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
296 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
297 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
298
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
299 #include <sys/types.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
300 #include <stdio.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
301 #include <sys/stat.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
302 #include <memory.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
303 #include <string.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
304 #include <errno.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
305 #include <unistd.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
306 #include <fcntl.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
307 #include <elf.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
308 #include <sys/mman.h>
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
309
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
310 #ifndef emacs
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
311 #define fatal(a, b, c) fprintf(stderr, a, b, c), exit(1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
312 #else
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
313 extern void fatal(char *, ...);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
314 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
315
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
316 /* Get the address of a particular section or program header entry,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
317 * accounting for the size of the entries.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
318 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
319
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
320 #define OLD_SECTION_H(n) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
321 (*(Elf32_Shdr *) ((byte *) old_section_h + old_file_h->e_shentsize * (n)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
322 #define NEW_SECTION_H(n) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
323 (*(Elf32_Shdr *) ((byte *) new_section_h + new_file_h->e_shentsize * (n)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
324 #define OLD_PROGRAM_H(n) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
325 (*(Elf32_Phdr *) ((byte *) old_program_h + old_file_h->e_phentsize * (n)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
326 #define NEW_PROGRAM_H(n) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
327 (*(Elf32_Phdr *) ((byte *) new_program_h + new_file_h->e_phentsize * (n)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
328
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
329 #define PATCH_INDEX(n) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
330 do { \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
331 if ((n) >= old_sbss_index) \
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
332 (n) += 1 + (old_sdata_index ? 0 : 1); } while (0)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
333
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
334 typedef unsigned char byte;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
335
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
336 /* Round X up to a multiple of Y. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
337
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
338 int
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
339 round_up (x, y)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
340 int x, y;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
341 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
342 int rem = x % y;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
343 if (rem == 0)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
344 return x;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
345 return x - rem + y;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
346 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
347
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
348 /* ****************************************************************
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
349 * unexec
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
350 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
351 * driving logic.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
352 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
353 * In ELF, this works by replacing the old .bss section with a new
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
354 * .data section, and inserting an empty .bss immediately afterwards.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
355 *
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
356 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
357 void
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
358 unexec (new_name, old_name, data_start, bss_start, entry_address)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
359 char *new_name, *old_name;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
360 unsigned data_start, bss_start, entry_address;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
361 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
362 extern unsigned int bss_end;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
363 int new_file, old_file, new_file_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
364
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
365 /* Pointers to the base of the image of the two files. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
366 caddr_t old_base, new_base;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
367
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
368 /* Pointers to the file, program and section headers for the old and new
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
369 * files.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
370 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
371 Elf32_Ehdr *old_file_h, *new_file_h;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
372 Elf32_Phdr *old_program_h, *new_program_h;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
373 Elf32_Shdr *old_section_h, *new_section_h;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
374
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
375 /* Point to the section name table in the old file */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
376 char *old_section_names;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
377
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
378 Elf32_Addr old_bss_addr, new_bss_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
379 Elf32_Addr old_sbss_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
380 Elf32_Word old_bss_size, new_data2_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
381 Elf32_Word old_sbss_size, new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
382 Elf32_Off new_data2_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
383 Elf32_Off new_data3_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
384 Elf32_Addr new_data2_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
385 Elf32_Addr new_data3_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
386
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
387 Elf32_Word old_sdata_size, new_sdata_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
388 int old_sdata_index = 0;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
389
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
390 int n, nn, old_data_index, new_data2_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
391 int old_bss_index;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
392 int old_sbss_index;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
393 int old_bss_padding;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
394 struct stat stat_buf;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
395
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
396 /* Open the old file & map it into the address space. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
397
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
398 old_file = open (old_name, O_RDONLY);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
399
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
400 if (old_file < 0)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
401 fatal ("Can't open %s for reading: errno %d\n", old_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
402
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
403 if (fstat (old_file, &stat_buf) == -1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
404 fatal ("Can't fstat(%s): errno %d\n", old_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
405
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
406 old_base = mmap (0, stat_buf.st_size, PROT_READ, MAP_SHARED, old_file, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
407
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
408 if (old_base == (caddr_t) -1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
409 fatal ("Can't mmap(%s): errno %d\n", old_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
410
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
411 #ifdef DEBUG
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
412 fprintf (stderr, "mmap(%s, %x) -> %x\n", old_name, stat_buf.st_size,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
413 old_base);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
414 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
415
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
416 /* Get pointers to headers & section names */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
417
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
418 old_file_h = (Elf32_Ehdr *) old_base;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
419 old_program_h = (Elf32_Phdr *) ((byte *) old_base + old_file_h->e_phoff);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
420 old_section_h = (Elf32_Shdr *) ((byte *) old_base + old_file_h->e_shoff);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
421 old_section_names = (char *) old_base
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
422 + OLD_SECTION_H(old_file_h->e_shstrndx).sh_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
423
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
424 /* Find the old .sbss section.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
425 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
426
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
427 for (old_sbss_index = 1; old_sbss_index < old_file_h->e_shnum;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
428 old_sbss_index++)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
429 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
430 #ifdef DEBUG
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
431 fprintf (stderr, "Looking for .sbss - found %s\n",
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
432 old_section_names + OLD_SECTION_H(old_sbss_index).sh_name);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
433 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
434 if (!strcmp (old_section_names + OLD_SECTION_H(old_sbss_index).sh_name,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
435 ".sbss"))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
436 break;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
437 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
438 if (old_sbss_index == old_file_h->e_shnum)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
439 fatal ("Can't find .sbss in %s.\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
440
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
441 if (!strcmp(old_section_names + OLD_SECTION_H(old_sbss_index - 1).sh_name,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
442 ".sdata"))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
443 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
444 old_sdata_index = old_sbss_index - 1;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
445 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
446
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
447
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
448 /* Find the old .bss section.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
449 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
450
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
451 for (old_bss_index = 1; old_bss_index < old_file_h->e_shnum; old_bss_index++)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
452 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
453 #ifdef DEBUG
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
454 fprintf (stderr, "Looking for .bss - found %s\n",
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
455 old_section_names + OLD_SECTION_H(old_bss_index).sh_name);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
456 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
457 if (!strcmp (old_section_names + OLD_SECTION_H(old_bss_index).sh_name,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
458 ".bss"))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
459 break;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
460 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
461 if (old_bss_index == old_file_h->e_shnum)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
462 fatal ("Can't find .bss in %s.\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
463
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
464 if (old_sbss_index != (old_bss_index - 1))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
465 fatal (".sbss should come immediately before .bss in %s.\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
466
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
467 /* Figure out parameters of the new data3 and data2 sections.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
468 * Change the sbss and bss sections.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
469 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
470
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
471 old_bss_addr = OLD_SECTION_H(old_bss_index).sh_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
472 old_bss_size = OLD_SECTION_H(old_bss_index).sh_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
473
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
474 old_sbss_addr = OLD_SECTION_H(old_sbss_index).sh_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
475 old_sbss_size = OLD_SECTION_H(old_sbss_index).sh_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
476
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
477 if (old_sdata_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
478 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
479 old_sdata_size = OLD_SECTION_H(old_sdata_index).sh_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
480 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
481
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
482 #if defined(emacs) || !defined(DEBUG)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
483 bss_end = (unsigned int) sbrk (0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
484 new_bss_addr = (Elf32_Addr) bss_end;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
485 #else
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
486 new_bss_addr = old_bss_addr + old_bss_size + 0x1234;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
487 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
488 if (old_sdata_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
489 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
490 new_sdata_size = OLD_SECTION_H(old_sbss_index).sh_offset -
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
491 OLD_SECTION_H(old_sdata_index).sh_offset + old_sbss_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
492 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
493
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
494 new_data3_addr = old_sbss_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
495 new_data3_size = old_sbss_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
496 new_data3_offset = OLD_SECTION_H(old_sbss_index).sh_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
497
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
498 new_data2_addr = old_bss_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
499 new_data2_size = new_bss_addr - old_bss_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
500 new_data2_align = (new_data3_offset + old_sbss_size) %
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
501 OLD_SECTION_H(old_bss_index).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
502 new_data2_align = new_data2_align ?
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
503 OLD_SECTION_H(old_bss_index).sh_addralign - new_data2_align :
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
504 0;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
505 new_data2_offset = new_data3_offset + old_sbss_size + new_data2_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
506
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
507 old_bss_padding = OLD_SECTION_H(old_bss_index).sh_offset -
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
508 OLD_SECTION_H(old_sbss_index).sh_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
509 #ifdef DEBUG
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
510 fprintf (stderr, "old_bss_index %d\n", old_bss_index);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
511 fprintf (stderr, "old_bss_addr %x\n", old_bss_addr);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
512 fprintf (stderr, "old_bss_size %x\n", old_bss_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
513 fprintf (stderr, "new_bss_addr %x\n", new_bss_addr);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
514 fprintf (stderr, "new_data2_addr %x\n", new_data2_addr);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
515 fprintf (stderr, "new_data2_size %x\n", new_data2_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
516 fprintf (stderr, "new_data2_offset %x\n", new_data2_offset);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
517 fprintf (stderr, "old_sbss_index %d\n", old_sbss_index);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
518 fprintf (stderr, "old_sbss_addr %x\n", old_sbss_addr);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
519 fprintf (stderr, "old_sbss_size %x\n", old_sbss_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
520 if (old_sdata_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
521 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
522 fprintf (stderr, "old_sdata_size %x\n", old_sdata_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
523 fprintf (stderr, "new_sdata_size %x\n", new_sdata_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
524 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
525 else
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
526 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
527 fprintf (stderr, "new_data3_addr %x\n", new_data3_addr);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
528 fprintf (stderr, "new_data3_size %x\n", new_data3_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
529 fprintf (stderr, "new_data3_offset %x\n", new_data3_offset);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
530 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
531 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
532
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
533 if ((unsigned) new_bss_addr < (unsigned) old_bss_addr + old_bss_size)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
534 fatal (".bss shrank when undumping???\n", 0, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
535
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
536 /* Set the output file to the right size and mmap(2) it. Set
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
537 * pointers to various interesting objects. stat_buf still has
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
538 * old_file data.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
539 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
540
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
541 new_file = open (new_name, O_RDWR | O_CREAT, 0666);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
542 if (new_file < 0)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
543 fatal ("Can't creat(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
544
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
545 new_file_size = stat_buf.st_size +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
546 ((1 + (old_sdata_index ? 0 : 1)) * old_file_h->e_shentsize) +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
547 new_data2_size + new_data3_size + new_data2_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
548
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
549 if (ftruncate (new_file, new_file_size))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
550 fatal ("Can't ftruncate(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
551
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
552 new_base = mmap (0, new_file_size, PROT_READ | PROT_WRITE, MAP_SHARED,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
553 new_file, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
554
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
555 if (new_base == (caddr_t) -1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
556 fatal ("Can't mmap(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
557
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
558 new_file_h = (Elf32_Ehdr *) new_base;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
559 new_program_h = (Elf32_Phdr *) ((byte *) new_base + old_file_h->e_phoff);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
560 new_section_h = (Elf32_Shdr *) ((byte *) new_base +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
561 old_file_h->e_shoff +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
562 new_data2_size +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
563 new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
564 new_data3_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
565
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
566 /* Make our new file, program and section headers as copies of the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
567 * originals.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
568 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
569
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
570 memcpy (new_file_h, old_file_h, old_file_h->e_ehsize);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
571 memcpy (new_program_h, old_program_h,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
572 old_file_h->e_phnum * old_file_h->e_phentsize);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
573
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
574 /* Modify the e_shstrndx if necessary. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
575 PATCH_INDEX (new_file_h->e_shstrndx);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
576
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
577 /* Fix up file header. We'll add one section. Section header is
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
578 * further away now.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
579 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
580
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
581 new_file_h->e_shoff += new_data2_size + new_data2_align + new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
582 new_file_h->e_shnum += 1 + (old_sdata_index ? 0 : 1);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
583
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
584 #ifdef DEBUG
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
585 fprintf (stderr, "Old section offset %x\n", old_file_h->e_shoff);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
586 fprintf (stderr, "Old section count %d\n", old_file_h->e_shnum);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
587 fprintf (stderr, "New section offset %x\n", new_file_h->e_shoff);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
588 fprintf (stderr, "New section count %d\n", new_file_h->e_shnum);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
589 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
590
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
591 /* Fix up a new program header. Extend the writable data segment so
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
592 * that the bss area is covered too. Find that segment by looking
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
593 * for a segment that ends just before the .bss area. Make sure
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
594 * that no segments are above the new .data2. Put a loop at the end
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
595 * to adjust the offset and address of any segment that is above
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
596 * data2, just in case we decide to allow this later.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
597 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
598
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
599 for (n = new_file_h->e_phnum - 1; n >= 0; n--)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
600 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
601 /* Compute maximum of all requirements for alignment of section. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
602 int alignment = (NEW_PROGRAM_H (n)).p_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
603 if ((OLD_SECTION_H (old_bss_index)).sh_addralign > alignment)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
604 alignment = OLD_SECTION_H (old_bss_index).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
605
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
606 if ((OLD_SECTION_H (old_sbss_index)).sh_addralign > alignment)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
607 alignment = OLD_SECTION_H (old_sbss_index).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
608
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
609 /* Supposedly this condition is okay for the SGI. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
610 #if 0
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
611 if (NEW_PROGRAM_H(n).p_vaddr + NEW_PROGRAM_H(n).p_filesz > old_bss_addr)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
612 fatal ("Program segment above .bss in %s\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
613 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
614
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
615 if (NEW_PROGRAM_H(n).p_type == PT_LOAD
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
616 && (round_up ((NEW_PROGRAM_H (n)).p_vaddr
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
617 + (NEW_PROGRAM_H (n)).p_filesz,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
618 alignment)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
619 == round_up (old_bss_addr, alignment)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
620 break;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
621 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
622 if (n < 0)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
623 fatal ("Couldn't find segment next to .bss in %s\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
624
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
625 NEW_PROGRAM_H(n).p_filesz += new_data2_size + new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
626 new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
627 NEW_PROGRAM_H(n).p_memsz = NEW_PROGRAM_H(n).p_filesz;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
628
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
629 #if 1 /* Maybe allow section after data2 - does this ever happen? */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
630 for (n = new_file_h->e_phnum - 1; n >= 0; n--)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
631 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
632 if (NEW_PROGRAM_H(n).p_vaddr
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
633 && NEW_PROGRAM_H(n).p_vaddr >= new_data3_addr)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
634 NEW_PROGRAM_H(n).p_vaddr += new_data2_size - old_bss_size +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
635 new_data3_size - old_sbss_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
636
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
637 if (NEW_PROGRAM_H(n).p_offset >= new_data3_offset)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
638 NEW_PROGRAM_H(n).p_offset += new_data2_size + new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
639 new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
640 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
641 #endif
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
642
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
643 /* Fix up section headers based on new .data2 section. Any section
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
644 * whose offset or virtual address is after the new .data2 section
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
645 * gets its value adjusted. .bss size becomes zero and new address
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
646 * is set. data2 section header gets added by copying the existing
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
647 * .data header and modifying the offset, address and size.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
648 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
649 for (old_data_index = 1; old_data_index < old_file_h->e_shnum;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
650 old_data_index++)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
651 if (!strcmp (old_section_names + OLD_SECTION_H(old_data_index).sh_name,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
652 ".data"))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
653 break;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
654 if (old_data_index == old_file_h->e_shnum)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
655 fatal ("Can't find .data in %s.\n", old_name, 0);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
656
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
657 /* Walk through all section headers, insert the new data2 section right
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
658 before the new bss section. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
659 for (n = 1, nn = 1; n < old_file_h->e_shnum; n++, nn++)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
660 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
661 caddr_t src;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
662
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
663 if (n == old_sbss_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
664
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
665 /* If it is sbss section, insert the new data3 section before it. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
666 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
667 /* Steal the data section header for this data3 section. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
668 if (!old_sdata_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
669 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
670 memcpy (&NEW_SECTION_H(nn), &OLD_SECTION_H(old_data_index),
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
671 new_file_h->e_shentsize);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
672
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
673 NEW_SECTION_H(nn).sh_addr = new_data3_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
674 NEW_SECTION_H(nn).sh_offset = new_data3_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
675 NEW_SECTION_H(nn).sh_size = new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
676 NEW_SECTION_H(nn).sh_flags = OLD_SECTION_H(n).sh_flags;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
677 /* Use the sbss section's alignment. This will assure that the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
678 new data3 section always be placed in the same spot as the old
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
679 sbss section by any other application. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
680 NEW_SECTION_H(nn).sh_addralign = OLD_SECTION_H(n).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
681
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
682 /* Now copy over what we have in the memory now. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
683 memcpy (NEW_SECTION_H(nn).sh_offset + new_base,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
684 (caddr_t) OLD_SECTION_H(n).sh_addr,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
685 new_data3_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
686 /* the new .data2 section should also come before the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
687 * new .sbss section */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
688 nn += 2;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
689 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
690 else
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
691 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
692 /* We always have a .sdata section: append the contents of the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
693 * old .sbss section.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
694 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
695 memcpy (new_data3_offset + new_base,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
696 (caddr_t) OLD_SECTION_H(n).sh_addr,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
697 new_data3_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
698 nn ++;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
699 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
700 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
701 else if (n == old_bss_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
702
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
703 /* If it is bss section, insert the new data2 section before it. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
704 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
705 Elf32_Word tmp_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
706 Elf32_Addr tmp_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
707
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
708 tmp_align = OLD_SECTION_H(n).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
709 tmp_addr = OLD_SECTION_H(n).sh_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
710
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
711 nn -= 2;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
712 /* Steal the data section header for this data2 section. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
713 memcpy (&NEW_SECTION_H(nn), &OLD_SECTION_H(old_data_index),
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
714 new_file_h->e_shentsize);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
715
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
716 NEW_SECTION_H(nn).sh_addr = new_data2_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
717 NEW_SECTION_H(nn).sh_offset = new_data2_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
718 NEW_SECTION_H(nn).sh_size = new_data2_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
719 /* Use the bss section's alignment. This will assure that the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
720 new data2 section always be placed in the same spot as the old
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
721 bss section by any other application. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
722 NEW_SECTION_H(nn).sh_addralign = tmp_align;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
723
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
724 /* Now copy over what we have in the memory now. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
725 memcpy (NEW_SECTION_H(nn).sh_offset + new_base,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
726 (caddr_t) tmp_addr, new_data2_size);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
727 nn += 2;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
728 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
729
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
730 memcpy (&NEW_SECTION_H(nn), &OLD_SECTION_H(n),
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
731 old_file_h->e_shentsize);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
732
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
733 if (old_sdata_index && n == old_sdata_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
734 /* The old .sdata section has now a new size */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
735 NEW_SECTION_H(nn).sh_size = new_sdata_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
736
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
737 /* The new bss section's size is zero, and its file offset and virtual
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
738 address should be off by NEW_DATA2_SIZE. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
739 if (n == old_sbss_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
740 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
741 /* NN should be `old_sbss_index + 2' at this point. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
742 NEW_SECTION_H(nn).sh_offset += new_data2_size + new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
743 new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
744 NEW_SECTION_H(nn).sh_addr += new_data2_size + new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
745 new_data3_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
746 /* Let the new bss section address alignment be the same as the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
747 section address alignment followed the old bss section, so
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
748 this section will be placed in exactly the same place. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
749 NEW_SECTION_H(nn).sh_addralign =
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
750 OLD_SECTION_H(nn + (old_sdata_index ? 1 : 0)).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
751 NEW_SECTION_H(nn).sh_size = 0;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
752 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
753 else if (n == old_bss_index)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
754 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
755 /* NN should be `old_bss_index + 2' at this point. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
756 NEW_SECTION_H(nn).sh_offset += new_data2_size + new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
757 new_data3_size - old_bss_padding;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
758 NEW_SECTION_H(nn).sh_addr += new_data2_size;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
759 /* Let the new bss section address alignment be the same as the
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
760 section address alignment followed the old bss section, so
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
761 this section will be placed in exactly the same place. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
762 NEW_SECTION_H(nn).sh_addralign =
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
763 OLD_SECTION_H((nn - (old_sdata_index ? 0 : 1))).sh_addralign;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
764 NEW_SECTION_H(nn).sh_size = 0;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
765 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
766 /* Any section that was original placed AFTER the bss section should now
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
767 be off by NEW_DATA2_SIZE. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
768 else if (NEW_SECTION_H(nn).sh_offset >= new_data3_offset)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
769 NEW_SECTION_H(nn).sh_offset += new_data2_size +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
770 new_data2_align +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
771 new_data3_size -
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
772 old_bss_padding;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
773
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
774 /* If any section hdr refers to the section after the new .data
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
775 section, make it refer to next one because we have inserted
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
776 a new section in between. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
777
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
778 PATCH_INDEX(NEW_SECTION_H(nn).sh_link);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
779 PATCH_INDEX(NEW_SECTION_H(nn).sh_info);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
780
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
781 /* Now, start to copy the content of sections. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
782 if (NEW_SECTION_H(nn).sh_type == SHT_NULL
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
783 || NEW_SECTION_H(nn).sh_type == SHT_NOBITS)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
784 continue;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
785
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
786 /* Write out the sections. .data, .data1 and .sdata get copied from
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
787 * the current process instead of the old file.
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
788 */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
789 if (!strcmp (old_section_names + OLD_SECTION_H(n).sh_name, ".data") ||
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
790 !strcmp (old_section_names + OLD_SECTION_H(n).sh_name, ".data1") ||
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
791 (old_sdata_index && (n == old_sdata_index)))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
792 src = (caddr_t) OLD_SECTION_H(n).sh_addr;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
793 else
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
794 src = old_base + OLD_SECTION_H(n).sh_offset;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
795
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
796 memcpy (NEW_SECTION_H(nn).sh_offset + new_base, src,
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
797 ((n == old_sdata_index) ?
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
798 old_sdata_size :
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
799 NEW_SECTION_H(nn).sh_size));
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
800
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
801 /* If it is the symbol table, its st_shndx field needs to be patched. */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
802 if (NEW_SECTION_H(nn).sh_type == SHT_SYMTAB
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
803 || NEW_SECTION_H(nn).sh_type == SHT_DYNSYM)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
804 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
805 Elf32_Shdr *spt = &NEW_SECTION_H(nn);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
806 unsigned int num = spt->sh_size / spt->sh_entsize;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
807 Elf32_Sym * sym = (Elf32_Sym *) (NEW_SECTION_H(nn).sh_offset +
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
808 new_base);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
809 for (; num--; sym++)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
810 {
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
811 if ((sym->st_shndx == SHN_UNDEF)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
812 || (sym->st_shndx == SHN_ABS)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
813 || (sym->st_shndx == SHN_COMMON))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
814 continue;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
815
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
816 PATCH_INDEX(sym->st_shndx);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
817 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
818 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
819 }
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
820
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
821 /* Close the files and make the new file executable */
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
822
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
823 if (close (old_file))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
824 fatal ("Can't close(%s): errno %d\n", old_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
825
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
826 if (close (new_file))
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
827 fatal ("Can't close(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
828
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
829 if (stat (new_name, &stat_buf) == -1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
830 fatal ("Can't stat(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
831
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
832 n = umask (777);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
833 umask (n);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
834 stat_buf.st_mode |= 0111 & ~n;
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
835 if (chmod (new_name, stat_buf.st_mode) == -1)
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
836 fatal ("Can't chmod(%s): errno %d\n", new_name, errno);
376386a54a3c Import from CVS: tag r19-14
cvs
parents:
diff changeset
837 }