]> git.ipfire.org Git - thirdparty/gcc.git/blob - libphobos/libdruntime/core/sys/darwin/mach/nlist.d
d: Merge upstream dmd 3982604c5, druntime bc58b1e9, phobos 12329adb6.
[thirdparty/gcc.git] / libphobos / libdruntime / core / sys / darwin / mach / nlist.d
1 /**
2 * Bindings for symbols and defines in `mach-o/nlist.h`
3 *
4 * This file was created based on the MacOSX 10.15 SDK.
5 *
6 * Copyright:
7 * D Language Foundation 2020
8 * Some documentation was extracted from the C headers
9 * and is the property of Apple Inc.
10 *
11 * License: $(HTTP www.boost.org/LICENSE_1_0.txt, Boost License 1.0).
12 * Authors: Mathias 'Geod24' Lang
13 * Source: $(DRUNTIMESRC core/sys/darwin/mach/_nlist.d)
14 */
15 module core.sys.darwin.mach.nlist;
16
17 import core.stdc.config;
18
19 extern(C):
20 nothrow:
21 @nogc:
22 pure:
23
24 /**
25 * An entry in a list of symbols for 64-bits architectures
26 *
27 * Said symbols can be used to describe many different type of data,
28 * including STABS debug infos. Introduced in MacOSX 10.8 SDK.
29 *
30 * See_Also:
31 * https://developer.apple.com/documentation/kernel/nlist_64
32 */
33 struct nlist_64
34 {
35 /// Compatibility alias, as `n_strx` is in an union in C code
36 alias n_un = n_strx;
37
38 /**
39 * Index of this symbol's name into the string table
40 *
41 * All names are stored as NUL-terminated strings into the string table.
42 * For historical reason, the very first entry into the string table is `0`,
43 * hence all non-NULL names have an index > 0.
44 */
45 uint n_strx;
46
47 /**
48 * A bitfield that describes the type of this symbol
49 *
50 * In reality, this describes 4 fields:
51 * - N_STAB (top 3 bits)
52 * - N_PEXT (next 1 bit)
53 * - N_TYPE (next 3 bits)
54 * - N_EXT (last 1 bit)
55 *
56 * The enum values `N_STAB`, `N_PEXT`, `N_TYPE`, and `N_EXT` should be used
57 * as masks to check which type this `nlist_64` actually is.
58 */
59 ubyte n_type;
60 /// Section number (note that `0` means `NO_SECT`)
61 ubyte n_sect;
62 /* see <mach-o/stab.h> */
63 ushort n_desc;
64 /* value of this symbol (or stab offset) */
65 ulong n_value;
66 // Note: `n_value` *is* `uint64_t`, not `c_ulong` !
67 }
68
69 /// Mask to use with `nlist_64.n_type` to check what the entry describes
70 enum
71 {
72 /**
73 * If any of these bits set, a symbolic debugging entry
74 *
75 * Only symbolic debugging entries have some of the N_STAB bits set and if any
76 * of these bits are set then it is a symbolic debugging entry (a stab). In
77 * which case then the values of the n_type field (the entire field) are given
78 * in <mach-o/stab.h>
79 */
80 N_STAB = 0xe0,
81 /// Private external symbol bit
82 N_PEXT = 0x10,
83 /// Mask for the type bits
84 N_TYPE = 0x0e, /* mask for the type bits */
85 /// External symbol bit, set for external symbols
86 N_EXT = 0x01,
87 }
88
89 /// Values for `NTypeMask.N_TYPE` bits of the `nlist_64.n_type` field.
90 enum
91 {
92 /// Undefined (`n_sect == NO_SECT`)
93 N_UNDF = 0x0,
94 /// Absolute (`n_sect == NO_SECT`)
95 N_ABS = 0x2,
96 /// Defined in section number `nlist_64.n_sect`
97 N_SECT = 0xe,
98 /// Prebound undefined (defined in a dylib)
99 N_PBUD = 0xc,
100 /**
101 * Indirect symbol
102 *
103 * If the type is `N_INDR` then the symbol is defined to be the same as
104 * another symbol. In this case the `n_value` field is an index into
105 * the string table of the other symbol's name. When the other symbol
106 * is defined then they both take on the defined type and value.
107 */
108 N_INDR = 0xa,
109 }
110
111 /**
112 * Symbol is not in any section
113 *
114 * If the type is N_SECT then the n_sect field contains an ordinal of the
115 * section the symbol is defined in. The sections are numbered from 1 and
116 * refer to sections in order they appear in the load commands for the file
117 * they are in. This means the same ordinal may very well refer to different
118 * sections in different files.
119 *
120 * The n_value field for all symbol table entries (including N_STAB's) gets
121 * updated by the link editor based on the value of it's n_sect field and where
122 * the section n_sect references gets relocated. If the value of the n_sect
123 * field is NO_SECT then it's n_value field is not changed by the link editor.
124 */
125 enum NO_SECT = 0;
126
127 /// Maximum number of sections: 1 thru 255 inclusive
128 enum MAX_SECT = 255;
129
130 /**
131 * Common symbols are represented by undefined (N_UNDF) external (N_EXT) types
132 * who's values (n_value) are non-zero. In which case the value of the n_value
133 * field is the size (in bytes) of the common symbol. The n_sect field is set
134 * to NO_SECT. The alignment of a common symbol may be set as a power of 2
135 * between 2^1 and 2^15 as part of the n_desc field using the macros below. If
136 * the alignment is not set (a value of zero) then natural alignment based on
137 * the size is used.
138 */
139 extern(D) ubyte GET_COMM_ALIGN(uint n_desc) @safe
140 {
141 return (((n_desc) >> 8) & 0x0f);
142 }
143
144 /// Ditto
145 extern(D) ref ushort SET_COMM_ALIGN(return ref ushort n_desc, size_t wanted_align) @safe
146 {
147 return n_desc = (((n_desc) & 0xf0ff) | (((wanted_align) & 0x0f) << 8));
148 }
149
150 /**
151 * To support the lazy binding of undefined symbols in the dynamic link-editor,
152 * the undefined symbols in the symbol table (the nlist structures) are marked
153 * with the indication if the undefined reference is a lazy reference or
154 * non-lazy reference. If both a non-lazy reference and a lazy reference is
155 * made to the same symbol the non-lazy reference takes precedence. A reference
156 * is lazy only when all references to that symbol are made through a symbol
157 * pointer in a lazy symbol pointer section.
158 *
159 * The implementation of marking nlist structures in the symbol table for
160 * undefined symbols will be to use some of the bits of the n_desc field as a
161 * reference type. The mask REFERENCE_TYPE will be applied to the n_desc field
162 * of an nlist structure for an undefined symbol to determine the type of
163 * undefined reference (lazy or non-lazy).
164 *
165 * The constants for the REFERENCE FLAGS are propagated to the reference table
166 * in a shared library file. In that case the constant for a defined symbol,
167 * REFERENCE_FLAG_DEFINED, is also used.
168 */
169 enum
170 {
171 /// Reference type bits of the n_desc field of undefined symbols
172 REFERENCE_TYPE = 0x7,
173
174 /// types of references
175 REFERENCE_FLAG_UNDEFINED_NON_LAZY = 0,
176 /// Ditto
177 REFERENCE_FLAG_UNDEFINED_LAZY = 1,
178 /// Ditto
179 REFERENCE_FLAG_DEFINED = 2,
180 /// Ditto
181 REFERENCE_FLAG_PRIVATE_DEFINED = 3,
182 /// Ditto
183 REFERENCE_FLAG_PRIVATE_UNDEFINED_NON_LAZY = 4,
184 /// Ditto
185 REFERENCE_FLAG_PRIVATE_UNDEFINED_LAZY = 5,
186
187 /**
188 * To simplify stripping of objects that use are used with the dynamic link
189 * editor, the static link editor marks the symbols defined an object that are
190 * referenced by a dynamicly bound object (dynamic shared libraries, bundles).
191 * With this marking strip knows not to strip these symbols.
192 */
193 REFERENCED_DYNAMICALLY = 0x0010,
194 }
195
196 /**
197 * For images created by the static link editor with the -twolevel_namespace
198 * option in effect the flags field of the mach header is marked with
199 * MH_TWOLEVEL. And the binding of the undefined references of the image are
200 * determined by the static link editor. Which library an undefined symbol is
201 * bound to is recorded by the static linker in the high 8 bits of the n_desc
202 * field using the SET_LIBRARY_ORDINAL macro below. The ordinal recorded
203 * references the libraries listed in the Mach-O's LC_LOAD_DYLIB,
204 * LC_LOAD_WEAK_DYLIB, LC_REEXPORT_DYLIB, LC_LOAD_UPWARD_DYLIB, and
205 * LC_LAZY_LOAD_DYLIB, etc. load commands in the order they appear in the
206 * headers. The library ordinals start from 1.
207 * For a dynamic library that is built as a two-level namespace image the
208 * undefined references from module defined in another use the same nlist struct
209 * an in that case SELF_LIBRARY_ORDINAL is used as the library ordinal. For
210 * defined symbols in all images they also must have the library ordinal set to
211 * SELF_LIBRARY_ORDINAL. The EXECUTABLE_ORDINAL refers to the executable
212 * image for references from plugins that refer to the executable that loads
213 * them.
214 *
215 * The DYNAMIC_LOOKUP_ORDINAL is for undefined symbols in a two-level namespace
216 * image that are looked up by the dynamic linker with flat namespace semantics.
217 * This ordinal was added as a feature in Mac OS X 10.3 by reducing the
218 * value of MAX_LIBRARY_ORDINAL by one. So it is legal for existing binaries
219 * or binaries built with older tools to have 0xfe (254) dynamic libraries. In
220 * this case the ordinal value 0xfe (254) must be treated as a library ordinal
221 * for compatibility.
222 */
223 ubyte GET_LIBRARY_ORDINAL(uint n_desc) @safe { return ((n_desc) >> 8) & 0xff; }
224 /// Ditto
225 ref ushort SET_LIBRARY_ORDINAL(return ref ushort n_desc, uint ordinal) @safe
226 {
227 return n_desc = (((n_desc) & 0x00ff) | (((ordinal) & 0xff) << 8));
228 }
229
230 /// Ditto
231 enum
232 {
233 SELF_LIBRARY_ORDINAL = 0x00,
234 MAX_LIBRARY_ORDINAL = 0xfd,
235 DYNAMIC_LOOKUP_ORDINAL = 0xfe,
236 EXECUTABLE_ORDINAL = 0xff,
237 }
238
239 /**
240 * The bit 0x0020 of the n_desc field is used for two non-overlapping purposes
241 * and has two different symbolic names, N_NO_DEAD_STRIP and N_DESC_DISCARDED.
242 */
243 enum
244 {
245 /**
246 * Symbol is not to be dead stripped
247 *
248 * The N_NO_DEAD_STRIP bit of the n_desc field only ever appears in a
249 * relocatable .o file (MH_OBJECT filetype). And is used to indicate to the
250 * static link editor it is never to dead strip the symbol.
251 */
252 N_NO_DEAD_STRIP = 0x0020,
253
254 /**
255 * Symbol is discarded
256 *
257 * The N_DESC_DISCARDED bit of the n_desc field never appears in linked image.
258 * But is used in very rare cases by the dynamic link editor to mark an in
259 * memory symbol as discared and longer used for linking.
260 */
261 N_DESC_DISCARDED =0x0020,
262
263 /**
264 * Symbol is weak referenced
265 *
266 * The N_WEAK_REF bit of the n_desc field indicates to the dynamic linker that
267 * the undefined symbol is allowed to be missing and is to have the address of
268 * zero when missing.
269 */
270 N_WEAK_REF = 0x0040,
271
272 /**
273 * Coalesed symbol is a weak definition
274 *
275 * The N_WEAK_DEF bit of the n_desc field indicates to the static and dynamic
276 * linkers that the symbol definition is weak, allowing a non-weak symbol to
277 * also be used which causes the weak definition to be discared. Currently this
278 * is only supported for symbols in coalesed sections.
279 */
280 N_WEAK_DEF = 0x0080,
281
282 /**
283 * Reference to a weak symbol
284 *
285 * The N_REF_TO_WEAK bit of the n_desc field indicates to the dynamic linker
286 * that the undefined symbol should be resolved using flat namespace searching.
287 */
288 N_REF_TO_WEAK = 0x0080,
289
290 /**
291 * Symbol is a Thumb function (ARM)
292 *
293 * The N_ARM_THUMB_DEF bit of the n_desc field indicates that the symbol is
294 * a defintion of a Thumb function.
295 */
296 N_ARM_THUMB_DEF = 0x0008,
297
298 /**
299 * The N_SYMBOL_RESOLVER bit of the n_desc field indicates that the
300 * that the function is actually a resolver function and should
301 * be called to get the address of the real function to use.
302 * This bit is only available in .o files (MH_OBJECT filetype)
303 */
304 N_SYMBOL_RESOLVER = 0x0100,
305
306 /**
307 * The N_ALT_ENTRY bit of the n_desc field indicates that the
308 * symbol is pinned to the previous content.
309 */
310 N_ALT_ENTRY = 0x0200,
311
312 /**
313 * The N_COLD_FUNC bit of the n_desc field indicates that the symbol is used
314 * infrequently and the linker should order it towards the end of the section.
315 */
316 N_COLD_FUNC = 0x0400,
317 }