annotate src/unexec.c @ 510:5bdbc721d46a

[xemacs-hg @ 2001-05-06 08:33:35 by ben] implement printing the selection when it's selected. force redisplay when set-charset-ccl-program called. if bytecomp or byte-optimize need recompiling, then load the .el version of them first, recompile them, and reload the .elc versions to recompile everything else (so we won't be waiting until the cows come home).
author ben
date Sun, 06 May 2001 08:33:41 +0000
parents abe6d1db359e
children 183866b06e0b
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1 /* Copyright (C) 1985, 1986, 1987, 1988, 1992, 1993, 1994
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
2 Free Software Foundation, Inc.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
3
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
4 This file is part of XEmacs.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
5
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
6 XEmacs is free software; you can redistribute it and/or modify it
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
7 under the terms of the GNU General Public License as published by the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
8 Free Software Foundation; either version 2, or (at your option) any
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
9 later version.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
10
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
11 XEmacs is distributed in the hope that it will be useful, but WITHOUT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
12 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
14 for more details.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
15
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
16 You should have received a copy of the GNU General Public License
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
17 along with XEmacs; see the file COPYING. If not, write to
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
18 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
19 Boston, MA 02111-1307, USA. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
20
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
21 /* Synched up with: FSF 19.31. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
22
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
23 /*
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
24 * unexec.c - Convert a running program into an a.out file.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
25 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
26 * Author: Spencer W. Thomas
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
27 * Computer Science Dept.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
28 * University of Utah
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
29 * Date: Tue Mar 2 1982
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
30 * Modified heavily since then.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
31 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
32 * Synopsis:
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
33 * unexec (new_name, a_name, data_start, bss_start, entry_address)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
34 * char *new_name, *a_name;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
35 * unsigned data_start, bss_start, entry_address;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
36 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
37 * Takes a snapshot of the program and makes an a.out format file in the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
38 * file named by the string argument new_name.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
39 * If a_name is non-NULL, the symbol table will be taken from the given file.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
40 * On some machines, an existing a_name file is required.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
41 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
42 * The boundaries within the a.out file may be adjusted with the data_start
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
43 * and bss_start arguments. Either or both may be given as 0 for defaults.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
44 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
45 * Data_start gives the boundary between the text segment and the data
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
46 * segment of the program. The text segment can contain shared, read-only
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
47 * program code and literal data, while the data segment is always unshared
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
48 * and unprotected. Data_start gives the lowest unprotected address.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
49 * The value you specify may be rounded down to a suitable boundary
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
50 * as required by the machine you are using.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
51 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
52 * Specifying zero for data_start means the boundary between text and data
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
53 * should not be the same as when the program was loaded.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
54 * If NO_REMAP is defined, the argument data_start is ignored and the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
55 * segment boundaries are never changed.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
56 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
57 * Bss_start indicates how much of the data segment is to be saved in the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
58 * a.out file and restored when the program is executed. It gives the lowest
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
59 * unsaved address, and is rounded up to a page boundary. The default when 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
60 * is given assumes that the entire data segment is to be stored, including
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
61 * the previous data and bss as well as any additional storage allocated with
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
62 * break (2).
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
63 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
64 * The new file is set up to start at entry_address.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
65 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
66 * If you make improvements I'd like to get them too.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
67 * harpo!utah-cs!thomas, thomas@Utah-20
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
68 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
69 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
70
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
71 /* Modified to support SysVr3 shared libraries by James Van Artsdalen
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
72 * of Dell Computer Corporation. james@bigtex.cactus.org.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
73 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
74
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
75 /* There are several compilation parameters affecting unexec:
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
76
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
77 * COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
78
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
79 Define this if your system uses COFF for executables.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
80
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
81 * COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
82
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
83 Define this if you are using the GNU coff encapsulated a.out format.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
84 This is closer to a.out than COFF. You should *not* define COFF if
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
85 you define COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
86
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
87 Otherwise we assume you use Berkeley format.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
88
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
89 * NO_REMAP
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
90
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
91 Define this if you do not want to try to save Emacs's pure data areas
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
92 as part of the text segment.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
93
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
94 Saving them as text is good because it allows users to share more.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
95
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
96 However, on machines that locate the text area far from the data area,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
97 the boundary cannot feasibly be moved. Such machines require
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
98 NO_REMAP.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
99
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
100 Also, remapping can cause trouble with the built-in startup routine
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
101 /lib/crt0.o, which defines `environ' as an initialized variable.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
102 Dumping `environ' as pure does not work! So, to use remapping,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
103 you must write a startup routine for your machine in Emacs's crt0.c.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
104 If NO_REMAP is defined, Emacs uses the system's crt0.o.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
105
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
106 * SECTION_ALIGNMENT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
107
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
108 Some machines that use COFF executables require that each section
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
109 start on a certain boundary *in the COFF file*. Such machines should
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
110 define SECTION_ALIGNMENT to a mask of the low-order bits that must be
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
111 zero on such a boundary. This mask is used to control padding between
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
112 segments in the COFF file.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
113
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
114 If SECTION_ALIGNMENT is not defined, the segments are written
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
115 consecutively with no attempt at alignment. This is right for
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
116 unmodified system V.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
117
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
118 * SEGMENT_MASK
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
119
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
120 Some machines require that the beginnings and ends of segments
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
121 *in core* be on certain boundaries. For most machines, a page
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
122 boundary is sufficient. That is the default. When a larger
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
123 boundary is needed, define SEGMENT_MASK to a mask of
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
124 the bits that must be zero on such a boundary.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
125
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
126 * A_TEXT_OFFSET(HDR)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
127
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
128 Some machines count the a.out header as part of the size of the text
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
129 segment (a_text); they may actually load the header into core as the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
130 first data in the text segment. Some have additional padding between
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
131 the header and the real text of the program that is counted in a_text.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
132
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
133 For these machines, define A_TEXT_OFFSET(HDR) to examine the header
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
134 structure HDR and return the number of bytes to add to `a_text'
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
135 before writing it (above and beyond the number of bytes of actual
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
136 program text). HDR's standard fields are already correct, except that
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
137 this adjustment to the `a_text' field has not yet been made;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
138 thus, the amount of offset can depend on the data in the file.
438
84b14dcb0985 Import from CVS: tag r21-2-27
cvs
parents: 428
diff changeset
139
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
140 * A_TEXT_SEEK(HDR)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
141
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
142 If defined, this macro specifies the number of bytes to seek into the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
143 a.out file before starting to write the text segment.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
144
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
145 * EXEC_MAGIC
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
146
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
147 For machines using COFF, this macro, if defined, is a value stored
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
148 into the magic number field of the output file.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
149
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
150 * ADJUST_EXEC_HEADER
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
151
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
152 This macro can be used to generate statements to adjust or
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
153 initialize nonstandard fields in the file header
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
154
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
155 * ADDR_CORRECT(ADDR)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
156
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
157 Macro to correct an int which is the bit pattern of a pointer to a byte
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
158 into an int which is the number of a byte.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
159
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
160 This macro has a default definition which is usually right.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
161 This default definition is a no-op on most machines (where a
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
162 pointer looks like an int) but not on all machines.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
163
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
164 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
165
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
166 #ifndef emacs
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
167 #define PERROR(arg) perror (arg); return -1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
168 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
169 #define IN_UNEXEC
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
170 #define DONT_ENCAPSULATE /* we include lisp.h so we want to make sure we
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
171 don't get filename conversion. The caller
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
172 of unexec() is assumed to have done this
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
173 already (it's easier to do it this way than
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
174 to modify all the unexec modules to ensure
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
175 that all weirdo functions, such as
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
176 elf_write_modified_data(), have proper
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
177 filename conversion applied). */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
178 #include <config.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
179 #define PERROR(file) report_error (file, new)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
180 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
181
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
182 #if __STDC__ || defined(STDC_HEADERS)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
183
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
184 /* I don't know how correct this attempt to get more prototypes is... */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
185 # if defined(sun) && defined(_POSIX_SOURCE)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
186 # undef _POSIX_SOURCE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
187 # endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
188
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
189 # include <stddef.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
190 # include <stdlib.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
191 # include <unistd.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
192 # include <string.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
193 # include <stddef.h>
438
84b14dcb0985 Import from CVS: tag r21-2-27
cvs
parents: 428
diff changeset
194 # include <errno.h>
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
195
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
196 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
197
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
198 /* I don't understand this, but it's necessary to get some slots in struct exec
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
199 from /usr/include/sys/exec.h when running LCC in strict ANSI mode. We don't
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
200 need this in K&R mode...
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
201 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
202 #if defined(__lucid) && defined(__sparc) && !defined(sun)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
203 # define sun 1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
204 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
205
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
206 #ifndef CANNOT_DUMP /* all rest of file! */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
207
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
208 #ifdef COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
209 int need_coff_header = 1;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
210 #include <coff-encap/a.out.encap.h> /* The location might be a poor assumption */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
211 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
212 #include <a.out.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
213 #endif /* not COFF_ENCAPSULATE */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
214
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
215 /* Define getpagesize if the system does not.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
216 Note that this may depend on symbols defined in a.out.h. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
217 #include "getpagesize.h"
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
218
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
219 #ifndef makedev /* Try to detect types.h already loaded */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
220 #include <sys/types.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
221 #endif /* makedev */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
222 #include <stdio.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
223 #include <sys/stat.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
224 #include <errno.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
225
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
226 #include <sys/file.h> /* Must be after sys/types.h for USG and BSD4_1*/
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
227
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
228 #ifdef USG5
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
229 #include <fcntl.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
230 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
231
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
232 #ifndef O_RDONLY
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
233 #define O_RDONLY 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
234 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
235 #ifndef O_RDWR
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
236 #define O_RDWR 2
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
237 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
238
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
239
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
240 extern char *start_of_text (); /* Start of text */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
241
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
242 extern void *start_of_data (); /* Start of initialized data */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
243
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
244 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
245 static long block_copy_start; /* Old executable start point */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
246 static struct filehdr f_hdr; /* File header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
247 static struct aouthdr f_ohdr; /* Optional file header (a.out) */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
248 long bias; /* Bias to add for growth */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
249 long lnnoptr; /* Pointer to line-number info within file */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
250 #define SYMS_START block_copy_start
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
251
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
252 static long text_scnptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
253 static long data_scnptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
254
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
255 #else /* not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
256
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
257 #ifdef __STDC__
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
258 #ifndef __sys_stdtypes_h
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
259 #if !defined(_PTRDIFF_T) && !defined(_BSD_PTRDIFF_T_)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
260 typedef long ptrdiff_t;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
261 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
262 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
263 #ifndef HPUX
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
264 /* not sure where this for NetBSD should really go
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
265 and it probably applies to other systems */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
266 #if !defined(__NetBSD__) && !defined(__bsdi__) && !defined(__OpenBSD__)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
267 extern void *sbrk (ptrdiff_t);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
268 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
269 extern char *sbrk ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
270 #endif /* __NetBSD__ or __OpenBSD__ */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
271 #endif /* HPUX */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
272 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
273 extern void *sbrk ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
274 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
275
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
276 #define SYMS_START ((long) N_SYMOFF (ohdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
277
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
278 /* Some machines override the structure name for an a.out header. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
279 #ifndef EXEC_HDR_TYPE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
280 #define EXEC_HDR_TYPE struct exec
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
281 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
282
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
283 #ifdef HPUX
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
284 #ifdef HP9000S200_ID
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
285 #define MY_ID HP9000S200_ID
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
286 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
287 #include <model.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
288 #define MY_ID MYSYS
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
289 #endif /* no HP9000S200_ID */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
290 static MAGIC OLDMAGIC = {MY_ID, SHARE_MAGIC};
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
291 static MAGIC NEWMAGIC = {MY_ID, DEMAND_MAGIC};
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
292 #define N_TXTOFF(x) TEXT_OFFSET(x)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
293 #define N_SYMOFF(x) LESYM_OFFSET(x)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
294 static EXEC_HDR_TYPE hdr, ohdr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
295
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
296 #else /* not HPUX */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
297
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
298 #if defined (USG) && !defined (IBMAIX) && !defined (IRIS) && !defined (COFF_ENCAPSULATE) && !defined (LINUX)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
299 static struct bhdr hdr, ohdr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
300 #define a_magic fmagic
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
301 #define a_text tsize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
302 #define a_data dsize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
303 #define a_bss bsize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
304 #define a_syms ssize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
305 #define a_trsize rtsize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
306 #define a_drsize rdsize
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
307 #define a_entry entry
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
308 #define N_BADMAG(x) \
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
309 (((x).fmagic)!=OMAGIC && ((x).fmagic)!=NMAGIC &&\
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
310 ((x).fmagic)!=FMAGIC && ((x).fmagic)!=IMAGIC)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
311 #define NEWMAGIC FMAGIC
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
312 #else /* IRIS or IBMAIX or not USG */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
313 static EXEC_HDR_TYPE hdr, ohdr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
314 #define NEWMAGIC ZMAGIC
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
315 #endif /* IRIS or IBMAIX not USG */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
316 #endif /* not HPUX */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
317
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
318 static int unexec_text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
319 static int unexec_data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
320
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
321 #ifdef COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
322 /* coffheader is defined in the GNU a.out.encap.h file. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
323 struct coffheader coffheader;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
324 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
325
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
326 #endif /* not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
327
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
328 static int pagemask;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
329
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
330 /* Correct an int which is the bit pattern of a pointer to a byte
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
331 into an int which is the number of a byte.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
332 This is a no-op on ordinary machines, but not on all. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
333
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
334 #ifndef ADDR_CORRECT /* Let m-*.h files override this definition */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
335 #define ADDR_CORRECT(x) ((char *)(x) - (char*)0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
336 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
337
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
338 #ifdef emacs
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
339
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
340 #include "lisp.h"
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
341
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
342 static void
440
8de8e3f6228a Import from CVS: tag r21-2-28
cvs
parents: 438
diff changeset
343 report_error (const char *file, int fd)
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
344 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
345 if (fd)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
346 close (fd);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
347 report_file_error ("Cannot unexec",
440
8de8e3f6228a Import from CVS: tag r21-2-28
cvs
parents: 438
diff changeset
348 Fcons (build_ext_string (file, Qfile_name), Qnil));
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
349 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
350 #endif /* emacs */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
351
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
352 #define ERROR0(msg) report_error_1 (new, msg, 0, 0); return -1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
353 #define ERROR1(msg,x) report_error_1 (new, msg, x, 0); return -1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
354 #define ERROR2(msg,x,y) report_error_1 (new, msg, x, y); return -1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
355
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
356 static void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
357 report_error_1 (fd, msg, a1, a2)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
358 int fd;
442
abe6d1db359e Import from CVS: tag r21-2-36
cvs
parents: 440
diff changeset
359 const char *msg;
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
360 int a1, a2;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
361 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
362 close (fd);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
363 #ifdef emacs
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
364 error (msg, a1, a2);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
365 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
366 fprintf (stderr, msg, a1, a2);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
367 fprintf (stderr, "\n");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
368 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
369 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
370
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
371 static int make_hdr (int new, int a_out, unsigned data_start,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
372 unsigned bss_start, unsigned entry_address,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
373 char *a_name, char *new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
374 static int copy_text_and_data (int new, int a_out);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
375 static int copy_sym (int new, int a_out, char *a_name, char *new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
376 static void mark_x (char *name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
377
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
378 /* ****************************************************************
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
379 * unexec
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
380 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
381 * driving logic.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
382 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
383 int
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
384 unexec (new_name, a_name, data_start, bss_start, entry_address)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
385 char *new_name, *a_name;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
386 unsigned data_start, bss_start, entry_address;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
387 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
388 int new, a_out = -1;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
389
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
390 if (a_name && (a_out = open (a_name, O_RDONLY)) < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
391 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
392 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
393 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
394 if ((new = creat (new_name, 0666)) < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
395 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
396 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
397 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
398
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
399 if (make_hdr (new, a_out, data_start, bss_start, entry_address, a_name, new_name) < 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
400 || copy_text_and_data (new, a_out) < 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
401 || copy_sym (new, a_out, a_name, new_name) < 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
402 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
403 #ifndef COFF_BSD_SYMBOLS
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
404 || adjust_lnnoptrs (new, a_out, new_name) < 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
405 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
406 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
407 )
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
408 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
409 close (new);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
410 /* unlink (new_name); / * Failed, unlink new a.out */
438
84b14dcb0985 Import from CVS: tag r21-2-27
cvs
parents: 428
diff changeset
411 return -1;
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
412 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
413
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
414 close (new);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
415 if (a_out >= 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
416 close (a_out);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
417 mark_x (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
418 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
419 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
420
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
421 /* ****************************************************************
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
422 * make_hdr
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
423 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
424 * Make the header in the new a.out from the header in core.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
425 * Modify the text and data sizes.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
426 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
427 static int
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
428 make_hdr (int new, int a_out, unsigned data_start, unsigned bss_start,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
429 unsigned entry_address, char *a_name, char *new_name)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
430 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
431 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
432 auto struct scnhdr f_thdr; /* Text section header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
433 auto struct scnhdr f_dhdr; /* Data section header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
434 auto struct scnhdr f_bhdr; /* Bss section header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
435 auto struct scnhdr scntemp; /* Temporary section header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
436 int scns;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
437 #endif /* COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
438 #ifdef USG_SHARED_LIBRARIES
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
439 extern unsigned int bss_end;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
440 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
441 unsigned int bss_end;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
442 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
443
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
444 pagemask = getpagesize () - 1;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
445
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
446 /* Adjust text/data boundary. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
447 #ifdef NO_REMAP
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
448 data_start = (int) start_of_data ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
449 #else /* not NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
450 if (!data_start)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
451 data_start = (int) start_of_data ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
452 #endif /* not NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
453 data_start = ADDR_CORRECT (data_start);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
454
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
455 #ifdef SEGMENT_MASK
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
456 data_start = data_start & ~SEGMENT_MASK; /* (Down) to segment boundary. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
457 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
458 data_start = data_start & ~pagemask; /* (Down) to page boundary. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
459 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
460
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
461 bss_end = ADDR_CORRECT (sbrk (0)) + pagemask;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
462 bss_end &= ~ pagemask;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
463
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
464 /* Adjust data/bss boundary. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
465 if (bss_start != 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
466 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
467 bss_start = (ADDR_CORRECT (bss_start) + pagemask);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
468 /* (Up) to page bdry. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
469 bss_start &= ~ pagemask;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
470 if (bss_start > bss_end)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
471 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
472 ERROR1 ("unexec: Specified bss_start (%u) is past end of program",
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
473 bss_start);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
474 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
475 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
476 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
477 bss_start = bss_end;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
478
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
479 if (data_start > bss_start) /* Can't have negative data size. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
480 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
481 ERROR2 ("unexec: data_start (%u) can't be greater than bss_start (%u)",
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
482 data_start, bss_start);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
483 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
484
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
485 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
486 /* Salvage as much info from the existing file as possible */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
487 if (a_out >= 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
488 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
489 if (read (a_out, &f_hdr, sizeof (f_hdr)) != sizeof (f_hdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
490 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
491 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
492 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
493 block_copy_start += sizeof (f_hdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
494 if (f_hdr.f_opthdr > 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
495 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
496 if (read (a_out, &f_ohdr, sizeof (f_ohdr)) != sizeof (f_ohdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
497 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
498 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
499 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
500 block_copy_start += sizeof (f_ohdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
501 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
502 /* Loop through section headers, copying them in */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
503 lseek (a_out, sizeof (f_hdr) + f_hdr.f_opthdr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
504 for (scns = f_hdr.f_nscns; scns > 0; scns--) {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
505 if (read (a_out, &scntemp, sizeof (scntemp)) != sizeof (scntemp))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
506 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
507 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
508 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
509 if (scntemp.s_scnptr > 0L)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
510 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
511 if (block_copy_start < scntemp.s_scnptr + scntemp.s_size)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
512 block_copy_start = scntemp.s_scnptr + scntemp.s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
513 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
514 if (strcmp (scntemp.s_name, ".text") == 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
515 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
516 f_thdr = scntemp;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
517 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
518 else if (strcmp (scntemp.s_name, ".data") == 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
519 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
520 f_dhdr = scntemp;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
521 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
522 else if (strcmp (scntemp.s_name, ".bss") == 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
523 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
524 f_bhdr = scntemp;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
525 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
526 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
527 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
528 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
529 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
530 ERROR0 ("can't build a COFF file from scratch yet");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
531 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
532
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
533 /* Now we alter the contents of all the f_*hdr variables
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
534 to correspond to what we want to dump. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
535
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
536 #ifdef USG_SHARED_LIBRARIES
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
537
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
538 /* The amount of data we're adding to the file is distance from the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
539 * end of the original .data space to the current end of the .data
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
540 * space.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
541 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
542
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
543 bias = bss_start - (f_ohdr.data_start + f_dhdr.s_size);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
544
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
545 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
546
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
547 f_hdr.f_flags |= (F_RELFLG | F_EXEC);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
548 #ifdef TPIX
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
549 f_hdr.f_nscns = 3;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
550 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
551 #ifdef EXEC_MAGIC
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
552 f_ohdr.magic = EXEC_MAGIC;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
553 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
554 #ifndef NO_REMAP
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
555 f_ohdr.text_start = (long) start_of_text ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
556 f_ohdr.tsize = data_start - f_ohdr.text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
557 f_ohdr.data_start = data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
558 #endif /* NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
559 f_ohdr.dsize = bss_start - f_ohdr.data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
560 f_ohdr.bsize = bss_end - bss_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
561 #ifndef KEEP_OLD_TEXT_SCNPTR
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
562 /* On some machines, the old values are right.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
563 ??? Maybe on all machines with NO_REMAP. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
564 f_thdr.s_size = f_ohdr.tsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
565 f_thdr.s_scnptr = sizeof (f_hdr) + sizeof (f_ohdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
566 f_thdr.s_scnptr += (f_hdr.f_nscns) * (sizeof (f_thdr));
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
567 #endif /* KEEP_OLD_TEXT_SCNPTR */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
568 #ifdef ADJUST_TEXT_SCNHDR_SIZE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
569 /* On some machines, `text size' includes all headers. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
570 f_thdr.s_size -= f_thdr.s_scnptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
571 #endif /* ADJUST_TEST_SCNHDR_SIZE */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
572 lnnoptr = f_thdr.s_lnnoptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
573 #ifdef SECTION_ALIGNMENT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
574 /* Some systems require special alignment
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
575 of the sections in the file itself. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
576 f_thdr.s_scnptr
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
577 = (f_thdr.s_scnptr + SECTION_ALIGNMENT) & ~SECTION_ALIGNMENT;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
578 #endif /* SECTION_ALIGNMENT */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
579 #ifdef TPIX
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
580 f_thdr.s_scnptr = 0xd0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
581 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
582 text_scnptr = f_thdr.s_scnptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
583 #ifdef ADJUST_TEXTBASE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
584 text_scnptr = sizeof (f_hdr) + sizeof (f_ohdr) + (f_hdr.f_nscns) * (sizeof (f_thdr));
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
585 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
586 #ifndef KEEP_OLD_PADDR
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
587 f_dhdr.s_paddr = f_ohdr.data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
588 #endif /* KEEP_OLD_PADDR */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
589 f_dhdr.s_vaddr = f_ohdr.data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
590 f_dhdr.s_size = f_ohdr.dsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
591 f_dhdr.s_scnptr = f_thdr.s_scnptr + f_thdr.s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
592 #ifdef SECTION_ALIGNMENT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
593 /* Some systems require special alignment
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
594 of the sections in the file itself. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
595 f_dhdr.s_scnptr
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
596 = (f_dhdr.s_scnptr + SECTION_ALIGNMENT) & ~SECTION_ALIGNMENT;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
597 #endif /* SECTION_ALIGNMENT */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
598 #ifdef DATA_SECTION_ALIGNMENT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
599 /* Some systems require special alignment
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
600 of the data section only. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
601 f_dhdr.s_scnptr
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
602 = (f_dhdr.s_scnptr + DATA_SECTION_ALIGNMENT) & ~DATA_SECTION_ALIGNMENT;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
603 #endif /* DATA_SECTION_ALIGNMENT */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
604 data_scnptr = f_dhdr.s_scnptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
605 #ifndef KEEP_OLD_PADDR
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
606 f_bhdr.s_paddr = f_ohdr.data_start + f_ohdr.dsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
607 #endif /* KEEP_OLD_PADDR */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
608 f_bhdr.s_vaddr = f_ohdr.data_start + f_ohdr.dsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
609 f_bhdr.s_size = f_ohdr.bsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
610 f_bhdr.s_scnptr = 0L;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
611 #ifndef USG_SHARED_LIBRARIES
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
612 bias = f_dhdr.s_scnptr + f_dhdr.s_size - block_copy_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
613 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
614
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
615 if (f_hdr.f_symptr > 0L)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
616 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
617 f_hdr.f_symptr += bias;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
618 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
619
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
620 if (f_thdr.s_lnnoptr > 0L)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
621 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
622 f_thdr.s_lnnoptr += bias;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
623 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
624
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
625 #ifdef ADJUST_EXEC_HEADER
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
626 ADJUST_EXEC_HEADER;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
627 #endif /* ADJUST_EXEC_HEADER */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
628
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
629 if (write (new, &f_hdr, sizeof (f_hdr)) != sizeof (f_hdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
630 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
631 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
632 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
633
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
634 if (write (new, &f_ohdr, sizeof (f_ohdr)) != sizeof (f_ohdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
635 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
636 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
637 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
638
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
639 #ifndef USG_SHARED_LIBRARIES
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
640
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
641 if (write (new, &f_thdr, sizeof (f_thdr)) != sizeof (f_thdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
642 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
643 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
644 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
645
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
646 if (write (new, &f_dhdr, sizeof (f_dhdr)) != sizeof (f_dhdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
647 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
648 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
649 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
650
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
651 if (write (new, &f_bhdr, sizeof (f_bhdr)) != sizeof (f_bhdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
652 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
653 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
654 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
655
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
656 #else /* USG_SHARED_LIBRARIES */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
657
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
658 /* The purpose of this code is to write out the new file's section
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
659 * header table.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
660 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
661 * Scan through the original file's sections. If the encountered
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
662 * section is one we know (.text, .data or .bss), write out the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
663 * correct header. If it is a section we do not know (such as
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
664 * .lib), adjust the address of where the section data is in the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
665 * file, and write out the header.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
666 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
667 * If any section precedes .text or .data in the file, this code
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
668 * will not adjust the file pointer for that section correctly.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
669 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
670
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
671 /* This used to use sizeof (f_ohdr) instead of .f_opthdr.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
672 .f_opthdr is said to be right when there is no optional header. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
673 lseek (a_out, sizeof (f_hdr) + f_hdr.f_opthdr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
674
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
675 for (scns = f_hdr.f_nscns; scns > 0; scns--)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
676 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
677 if (read (a_out, &scntemp, sizeof (scntemp)) != sizeof (scntemp))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
678 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
679
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
680 if (!strcmp (scntemp.s_name, f_thdr.s_name)) /* .text */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
681 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
682 if (write (new, &f_thdr, sizeof (f_thdr)) != sizeof (f_thdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
683 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
684 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
685 else if (!strcmp (scntemp.s_name, f_dhdr.s_name)) /* .data */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
686 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
687 if (write (new, &f_dhdr, sizeof (f_dhdr)) != sizeof (f_dhdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
688 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
689 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
690 else if (!strcmp (scntemp.s_name, f_bhdr.s_name)) /* .bss */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
691 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
692 if (write (new, &f_bhdr, sizeof (f_bhdr)) != sizeof (f_bhdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
693 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
694 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
695 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
696 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
697 if (scntemp.s_scnptr)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
698 scntemp.s_scnptr += bias;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
699 if (write (new, &scntemp, sizeof (scntemp)) != sizeof (scntemp))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
700 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
701 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
702 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
703 #endif /* USG_SHARED_LIBRARIES */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
704
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
705 return (0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
706
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
707 #else /* if not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
708
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
709 /* Get symbol table info from header of a.out file if given one. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
710 if (a_out >= 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
711 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
712 #ifdef COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
713 if (read (a_out, &coffheader, sizeof coffheader) != sizeof coffheader)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
714 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
715 PERROR(a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
716 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
717 if (coffheader.f_magic != COFF_MAGIC)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
718 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
719 ERROR1("%s doesn't have legal coff magic number\n", a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
720 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
721 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
722 if (read (a_out, (char *) &ohdr, sizeof hdr) != sizeof hdr)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
723 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
724 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
725 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
726
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
727 if (N_BADMAG (ohdr))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
728 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
729 ERROR1 ("invalid magic number in %s", a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
730 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
731 hdr = ohdr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
732 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
733 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
734 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
735 #ifdef COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
736 /* We probably could without too much trouble. The code is in gld
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
737 * but I don't have that much time or incentive.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
738 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
739 ERROR0 ("can't build a COFF file from scratch yet");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
740 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
741 memset ((void *)&hdr, 0, sizeof hdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
742 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
743 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
744
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
745 unexec_text_start = (long) start_of_text ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
746 unexec_data_start = data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
747
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
748 /* Machine-dependent fixup for header, or maybe for unexec_text_start */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
749 #ifdef ADJUST_EXEC_HEADER
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
750 ADJUST_EXEC_HEADER;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
751 #endif /* ADJUST_EXEC_HEADER */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
752
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
753 hdr.a_trsize = 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
754 hdr.a_drsize = 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
755 if (entry_address != 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
756 hdr.a_entry = entry_address;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
757
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
758 hdr.a_bss = bss_end - bss_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
759 hdr.a_data = bss_start - data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
760 #ifdef NO_REMAP
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
761 hdr.a_text = ohdr.a_text;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
762 #else /* not NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
763 hdr.a_text = data_start - unexec_text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
764
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
765 #ifdef A_TEXT_OFFSET
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
766 hdr.a_text += A_TEXT_OFFSET (ohdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
767 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
768
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
769 #endif /* not NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
770
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
771 #ifdef COFF_ENCAPSULATE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
772 /* We are encapsulating BSD format within COFF format. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
773 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
774 struct coffscn *tp, *dp, *bp;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
775 tp = &coffheader.scns[0];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
776 dp = &coffheader.scns[1];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
777 bp = &coffheader.scns[2];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
778 tp->s_size = hdr.a_text + sizeof(struct exec);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
779 dp->s_paddr = data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
780 dp->s_vaddr = data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
781 dp->s_size = hdr.a_data;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
782 bp->s_paddr = dp->s_vaddr + dp->s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
783 bp->s_vaddr = bp->s_paddr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
784 bp->s_size = hdr.a_bss;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
785 coffheader.tsize = tp->s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
786 coffheader.dsize = dp->s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
787 coffheader.bsize = bp->s_size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
788 coffheader.text_start = tp->s_vaddr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
789 coffheader.data_start = dp->s_vaddr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
790 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
791 if (write (new, &coffheader, sizeof coffheader) != sizeof coffheader)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
792 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
793 PERROR(new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
794 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
795 #endif /* COFF_ENCAPSULATE */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
796
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
797 if (write (new, (char *) &hdr, sizeof hdr) != sizeof hdr)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
798 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
799 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
800 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
801
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
802 #if 0 /* This #ifndef caused a bug on Linux when using QMAGIC. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
803 /* This adjustment was done above only #ifndef NO_REMAP,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
804 so only undo it now #ifndef NO_REMAP. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
805 /* #ifndef NO_REMAP */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
806 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
807 #ifdef A_TEXT_OFFSET
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
808 hdr.a_text -= A_TEXT_OFFSET (ohdr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
809 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
810
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
811 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
812
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
813 #endif /* not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
814 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
815
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
816 static void write_segment (int, char *, char *);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
817
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
818 /* ****************************************************************
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
819 * copy_text_and_data
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
820 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
821 * Copy the text and data segments from memory to the new a.out
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
822 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
823 static int
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
824 copy_text_and_data (int new, int a_out)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
825 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
826 char *end;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
827 char *ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
828
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
829 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
830
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
831 #ifdef USG_SHARED_LIBRARIES
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
832
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
833 int scns;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
834 struct scnhdr scntemp; /* Temporary section header */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
835
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
836 /* The purpose of this code is to write out the new file's section
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
837 * contents.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
838 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
839 * Step through the section table. If we know the section (.text,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
840 * .data) do the appropriate thing. Otherwise, if the section has
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
841 * no allocated space in the file (.bss), do nothing. Otherwise,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
842 * the section has space allocated in the file, and is not a section
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
843 * we know. So just copy it.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
844 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
845
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
846 lseek (a_out, sizeof (struct filehdr) + sizeof (struct aouthdr), 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
847
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
848 for (scns = f_hdr.f_nscns; scns > 0; scns--)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
849 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
850 if (read (a_out, &scntemp, sizeof (scntemp)) != sizeof (scntemp))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
851 PERROR ("temacs");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
852
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
853 if (!strcmp (scntemp.s_name, ".text"))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
854 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
855 lseek (new, (long) text_scnptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
856 ptr = (char *) f_ohdr.text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
857 end = ptr + f_ohdr.tsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
858 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
859 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
860 else if (!strcmp (scntemp.s_name, ".data"))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
861 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
862 lseek (new, (long) data_scnptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
863 ptr = (char *) f_ohdr.data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
864 end = ptr + f_ohdr.dsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
865 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
866 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
867 else if (!scntemp.s_scnptr)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
868 ; /* do nothing - no data for this section */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
869 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
870 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
871 char page[BUFSIZ];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
872 int size, n;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
873 long old_a_out_ptr = lseek (a_out, 0, 1);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
874
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
875 lseek (a_out, scntemp.s_scnptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
876 for (size = scntemp.s_size; size > 0; size -= sizeof (page))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
877 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
878 n = size > sizeof (page) ? sizeof (page) : size;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
879 if (read (a_out, page, n) != n || write (new, page, n) != n)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
880 PERROR ("emacs");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
881 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
882 lseek (a_out, old_a_out_ptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
883 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
884 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
885
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
886 #else /* COFF, but not USG_SHARED_LIBRARIES */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
887
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
888 lseek (new, (long) text_scnptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
889 ptr = (char *) f_ohdr.text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
890 #ifdef HEADER_INCL_IN_TEXT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
891 /* For Gould UTX/32, text starts after headers */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
892 ptr = (char *) (ptr + text_scnptr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
893 #endif /* HEADER_INCL_IN_TEXT */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
894 end = ptr + f_ohdr.tsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
895 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
896
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
897 lseek (new, (long) data_scnptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
898 ptr = (char *) f_ohdr.data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
899 end = ptr + f_ohdr.dsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
900 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
901
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
902 #endif /* USG_SHARED_LIBRARIES */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
903
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
904 #else /* if not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
905
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
906 /* Some machines count the header as part of the text segment.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
907 That is to say, the header appears in core
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
908 just before the address that start_of_text returns.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
909 For them, N_TXTOFF is the place where the header goes.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
910 We must adjust the seek to the place after the header.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
911 Note that at this point hdr.a_text does *not* count
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
912 the extra A_TEXT_OFFSET bytes, only the actual bytes of code. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
913
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
914 #ifdef A_TEXT_SEEK
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
915 lseek (new, (long) A_TEXT_SEEK (hdr), 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
916 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
917 lseek (new, (long) N_TXTOFF (hdr), 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
918 #endif /* no A_TEXT_SEEK */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
919
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
920 #ifdef RISCiX
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
921
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
922 /* Acorn's RISC-iX has a wacky way of initializing the position of the heap.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
923 * There is a little table in crt0.o that is filled at link time with
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
924 * the min and current brk positions, among other things. When start
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
925 * runs, it copies the table to where these parameters live during
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
926 * execution. This data is in text space, so it cannot be modified here
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
927 * before saving the executable, so the data is written manually. In
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
928 * addition, the table does not have a label, and the nearest accessible
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
929 * label (mcount) is not prefixed with a '_', thus making it inaccessible
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
930 * from within C programs. To overcome this, emacs's executable is passed
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
931 * through the command 'nm %s | fgrep mcount' into a pipe, and the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
932 * resultant output is then used to find the address of 'mcount'. As far as
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
933 * is possible to determine, in RISC-iX releases prior to 1.2, the negative
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
934 * offset of the table from mcount is 0x2c, whereas from 1.2 onwards it is
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
935 * 0x30. bss_end has been rounded up to page boundary. This solution is
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
936 * based on suggestions made by Kevin Welton and Steve Hunt of Acorn, and
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
937 * avoids the need for a custom version of crt0.o for emacs which has its
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
938 * table in data space.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
939 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
940
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
941 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
942 char command[1024];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
943 char errbuf[1024];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
944 char address_text[32];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
945 int proforma[4];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
946 FILE *pfile;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
947 char *temp_ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
948 char c;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
949 int mcount_address, mcount_offset, count;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
950 extern char *_execname;
438
84b14dcb0985 Import from CVS: tag r21-2-27
cvs
parents: 428
diff changeset
951
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
952
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
953 /* The use of _execname is incompatible with RISCiX 1.1 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
954 sprintf (command, "nm %s | fgrep mcount", _execname);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
955
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
956 if ( (pfile = popen(command, "r")) == NULL)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
957 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
958 sprintf (errbuf, "Could not open pipe");
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
959 PERROR (errbuf);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
960 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
961
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
962 count=0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
963 while ( ((c=getc(pfile)) != EOF) && (c != ' ') && (count < 31))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
964 address_text[count++]=c;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
965 address_text[count]=0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
966
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
967 if ((count == 0) || pclose(pfile) != NULL)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
968 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
969 sprintf (errbuf, "Failed to execute the command '%s'\n", command);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
970 PERROR (errbuf);
438
84b14dcb0985 Import from CVS: tag r21-2-27
cvs
parents: 428
diff changeset
971 }
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
972
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
973 sscanf(address_text, "%x", &mcount_address);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
974 ptr = (char *) unexec_text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
975 mcount_offset = (char *)mcount_address - ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
976
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
977 #ifdef RISCiX_1_1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
978 #define EDATA_OFFSET 0x2c
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
979 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
980 #define EDATA_OFFSET 0x30
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
981 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
982
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
983 end = ptr + mcount_offset - EDATA_OFFSET;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
984
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
985 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
986
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
987 proforma[0] = bss_end; /* becomes _edata */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
988 proforma[1] = bss_end; /* becomes _end */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
989 proforma[2] = bss_end; /* becomes _minbrk */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
990 proforma[3] = bss_end; /* becomes _curbrk */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
991
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
992 write (new, proforma, 16);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
993
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
994 temp_ptr = ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
995 ptr = end + 16;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
996 end = temp_ptr + hdr.a_text;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
997
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
998 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
999 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1000
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1001 #else /* !RISCiX */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1002 ptr = (char *) unexec_text_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1003 end = ptr + hdr.a_text;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1004 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1005 #endif /* RISCiX */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1006
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1007 ptr = (char *) unexec_data_start;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1008 end = ptr + hdr.a_data;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1009 /* This lseek is certainly incorrect when A_TEXT_OFFSET
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1010 and I believe it is a no-op otherwise.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1011 Let's see if its absence ever fails. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1012 /* lseek (new, (long) N_TXTOFF (hdr) + hdr.a_text, 0); */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1013 write_segment (new, ptr, end);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1014
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1015 #endif /* not COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1016
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1017 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1018 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1019
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1020 static void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1021 write_segment (new, ptr, end)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1022 int new;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1023 char *ptr, *end;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1024 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1025 int i, nwrite, ret;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1026 #if 0
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1027 char buf[80];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1028 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1029 /* This is the normal amount to write at once.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1030 It is the size of block that NFS uses. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1031 int writesize = 1 << 13;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1032 int pagesize = getpagesize ();
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1033 char zeros[1 << 13];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1034
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1035 memset (zeros, 0, sizeof (zeros));
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1036
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1037 for (i = 0; ptr < end;)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1038 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1039 /* Distance to next multiple of writesize. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1040 nwrite = (((int) ptr + writesize) & -writesize) - (int) ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1041 /* But not beyond specified end. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1042 if (nwrite > end - ptr) nwrite = end - ptr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1043 ret = write (new, ptr, nwrite);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1044 /* If write gets a page fault, it means we reached
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1045 a gap between the old text segment and the old data segment.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1046 This gap has probably been remapped into part of the text segment.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1047 So write zeros for it. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1048 if (ret == -1
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1049 #ifdef EFAULT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1050 && errno == EFAULT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1051 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1052 )
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1053 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1054 /* Write only a page of zeros at once,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1055 so that we don't overshoot the start
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1056 of the valid memory in the old data segment. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1057 if (nwrite > pagesize)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1058 nwrite = pagesize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1059 write (new, zeros, nwrite);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1060 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1061 #if 0 /* Now that we have can ask `write' to write more than a page,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1062 it is legit for write do less than the whole amount specified. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1063 else if (nwrite != ret)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1064 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1065 sprintf (buf,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1066 "unexec write failure: addr 0x%lx, fileno %d, size 0x%x, wrote 0x%x, errno %d",
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1067 (unsigned long) ptr, new, nwrite, ret, errno);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1068 PERROR (buf);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1069 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1070 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1071 i += nwrite;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1072 ptr += nwrite;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1073 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1074 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1075
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1076 /* ****************************************************************
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1077 * copy_sym
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1078 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1079 * Copy the relocation information and symbol table from the a.out to the new
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1080 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1081 static int
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1082 copy_sym (int new, int a_out, char *a_name, char *new_name)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1083 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1084 char page[1024];
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1085 int n;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1086
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1087 if (a_out < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1088 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1089
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1090 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1091 if (SYMS_START == 0L)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1092 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1093 #endif /* COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1094
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1095 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1096 if (lnnoptr) /* if there is line number info */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1097 lseek (a_out, lnnoptr, 0); /* start copying from there */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1098 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1099 #endif /* COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1100 lseek (a_out, SYMS_START, 0); /* Position a.out to symtab. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1101
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1102 while ((n = read (a_out, page, sizeof page)) > 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1103 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1104 if (write (new, page, n) != n)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1105 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1106 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1107 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1108 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1109 if (n < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1110 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1111 PERROR (a_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1112 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1113 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1114 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1115
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1116 /* ****************************************************************
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1117 * mark_x
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1118 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1119 * After successfully building the new a.out, mark it executable
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1120 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1121 static void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1122 mark_x (char *name)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1123 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1124 struct stat sbuf;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1125 int um;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1126 int new = 0; /* for PERROR */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1127
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1128 um = umask (777);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1129 umask (um);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1130 if (stat (name, &sbuf) == -1)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1131 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1132 PERROR (name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1133 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1134 sbuf.st_mode |= 0111 & ~um;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1135 if (chmod (name, sbuf.st_mode) == -1)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1136 PERROR (name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1137 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1138
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1139 #ifdef COFF
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1140 #ifndef COFF_BSD_SYMBOLS
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1141
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1142 /*
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1143 * If the COFF file contains a symbol table and a line number section,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1144 * then any auxiliary entries that have values for x_lnnoptr must
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1145 * be adjusted by the amount that the line number section has moved
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1146 * in the file (bias computed in make_hdr). The #@$%&* designers of
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1147 * the auxiliary entry structures used the absolute file offsets for
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1148 * the line number entry rather than an offset from the start of the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1149 * line number section!
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1150 *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1151 * When I figure out how to scan through the symbol table and pick out
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1152 * the auxiliary entries that need adjustment, this routine will
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1153 * be fixed. As it is now, all such entries are wrong and sdb
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1154 * will complain. Fred Fish, UniSoft Systems Inc.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1155 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1156
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1157 /* This function is probably very slow. Instead of reopening the new
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1158 file for input and output it should copy from the old to the new
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1159 using the two descriptors already open (WRITEDESC and READDESC).
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1160 Instead of reading one small structure at a time it should use
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1161 a reasonable size buffer. But I don't have time to work on such
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1162 things, so I am installing it as submitted to me. -- RMS. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1163
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1164 int
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1165 adjust_lnnoptrs (writedesc, readdesc, new_name)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1166 int writedesc;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1167 int readdesc;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1168 char *new_name;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1169 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1170 int nsyms;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1171 int new;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1172 #if defined (amdahl_uts) || defined (pfa)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1173 SYMENT symentry;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1174 AUXENT auxentry;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1175 #else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1176 struct syment symentry;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1177 union auxent auxentry;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1178 #endif
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1179
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1180 if (!lnnoptr || !f_hdr.f_symptr)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1181 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1182
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1183 if ((new = open (new_name, O_RDWR)) < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1184 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1185 PERROR (new_name);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1186 return -1;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1187 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1188
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1189 lseek (new, f_hdr.f_symptr, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1190 for (nsyms = 0; nsyms < f_hdr.f_nsyms; nsyms++)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1191 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1192 read (new, &symentry, SYMESZ);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1193 if (symentry.n_numaux)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1194 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1195 read (new, &auxentry, AUXESZ);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1196 nsyms++;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1197 if (ISFCN (symentry.n_type) || symentry.n_type == 0x2400)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1198 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1199 auxentry.x_sym.x_fcnary.x_fcn.x_lnnoptr += bias;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1200 lseek (new, -AUXESZ, 1);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1201 write (new, &auxentry, AUXESZ);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1202 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1203 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1204 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1205 close (new);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1206 return 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1207 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1208
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1209 #endif /* COFF_BSD_SYMBOLS */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1210
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1211 #endif /* COFF */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1212
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1213 #endif /* not CANNOT_DUMP */