]> git.saurik.com Git - apple/xnu.git/blob - libkern/kxld/kxld_object.c
xnu-3789.51.2.tar.gz
[apple/xnu.git] / libkern / kxld / kxld_object.c
1 /*
2 * Copyright (c) 2009-2014 Apple Inc. All rights reserved.
3 *
4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. The rights granted to you under the License
10 * may not be used to create, or enable the creation or redistribution of,
11 * unlawful or unlicensed copies of an Apple operating system, or to
12 * circumvent, violate, or enable the circumvention or violation of, any
13 * terms of an Apple operating system software license agreement.
14 *
15 * Please obtain a copy of the License at
16 * http://www.opensource.apple.com/apsl/ and read it before using this file.
17 *
18 * The Original Code and all software distributed under the License are
19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23 * Please see the License for the specific language governing rights and
24 * limitations under the License.
25 *
26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
27 */
28 #include <string.h>
29 #include <sys/types.h>
30
31 #if KERNEL
32 #include <libkern/kernel_mach_header.h>
33 #include <mach/machine.h>
34 #include <mach/vm_param.h>
35 #include <mach-o/fat.h>
36 #else /* !KERNEL */
37 /* Get machine.h from the kernel source so we can support all platforms
38 * that the kernel supports. Otherwise we're at the mercy of the host.
39 */
40 #include "../../osfmk/mach/machine.h"
41
42 #include <architecture/byte_order.h>
43 #include <mach/mach_init.h>
44 #include <mach-o/arch.h>
45 #include <mach-o/swap.h>
46 #endif /* KERNEL */
47
48 #include <mach-o/loader.h>
49 #include <mach-o/nlist.h>
50 #include <mach-o/reloc.h>
51
52 #define DEBUG_ASSERT_COMPONENT_NAME_STRING "kxld"
53 #include <AssertMacros.h>
54
55 #include "kxld_demangle.h"
56 #include "kxld_dict.h"
57 #include "kxld_reloc.h"
58 #include "kxld_sect.h"
59 #include "kxld_seg.h"
60 #include "kxld_srcversion.h"
61 #include "kxld_symtab.h"
62 #include "kxld_util.h"
63 #include "kxld_uuid.h"
64 #include "kxld_versionmin.h"
65 #include "kxld_vtable.h"
66 #include "kxld_splitinfolc.h"
67
68 #include "kxld_object.h"
69
70 extern boolean_t isSplitKext;
71 extern boolean_t isOldInterface;
72
73 /*******************************************************************************
74 * Data structures
75 *******************************************************************************/
76
77 struct kxld_object {
78 u_char *file; // used by old interface
79 u_long size; // used by old interface
80 const char *name;
81 uint32_t filetype;
82 cpu_type_t cputype;
83 cpu_subtype_t cpusubtype;
84 KXLDArray segs;
85 KXLDArray sects;
86 KXLDArray extrelocs;
87 KXLDArray locrelocs;
88 KXLDRelocator relocator;
89 KXLDuuid uuid;
90 KXLDversionmin versionmin;
91 KXLDsrcversion srcversion;
92 KXLDSymtab *symtab;
93 struct dysymtab_command *dysymtab_hdr;
94 KXLDsplitinfolc splitinfolc;
95 splitKextLinkInfo split_info;
96 kxld_addr_t link_addr;
97 u_long output_buffer_size;
98 boolean_t is_kernel;
99 boolean_t is_final_image;
100 boolean_t is_linked;
101 boolean_t got_is_created;
102 #if KXLD_USER_OR_OBJECT
103 KXLDArray *section_order;
104 #endif
105 #if KXLD_PIC_KEXTS
106 boolean_t include_kaslr_relocs;
107 #endif
108 #if !KERNEL
109 enum NXByteOrder host_order;
110 enum NXByteOrder target_order;
111 #endif
112 };
113
114 /*******************************************************************************
115 * Prototypes
116 *******************************************************************************/
117
118 static kern_return_t get_target_machine_info(KXLDObject *object,
119 cpu_type_t cputype, cpu_subtype_t cpusubtype);
120 static kern_return_t get_macho_slice_for_arch(KXLDObject *object,
121 u_char *file, u_long size);
122
123 static u_long get_macho_header_size(const KXLDObject *object);
124 static u_long get_macho_data_size(const KXLDObject *object) __unused;
125
126 static kern_return_t init_from_execute(KXLDObject *object);
127 static kern_return_t init_from_final_linked_image(KXLDObject *object,
128 u_int *filetype_out, struct symtab_command **symtab_hdr_out);
129
130 static boolean_t target_supports_protected_segments(const KXLDObject *object)
131 __attribute__((pure));
132 static void set_is_object_linked(KXLDObject *object);
133
134 #if KXLD_USER_OR_BUNDLE
135 static boolean_t target_supports_bundle(const KXLDObject *object)
136 __attribute((pure));
137 static kern_return_t init_from_bundle(KXLDObject *object);
138 static kern_return_t process_relocs_from_tables(KXLDObject *object);
139 static KXLDSeg *get_seg_by_base_addr(KXLDObject *object,
140 kxld_addr_t base_addr);
141 static kern_return_t process_symbol_pointers(KXLDObject *object);
142 static void add_to_ptr(u_char *symptr, kxld_addr_t val, boolean_t is_32_bit);
143 #endif /* KXLD_USER_OR_BUNDLE */
144
145 #if KXLD_USER_OR_OBJECT
146 static boolean_t target_supports_object(const KXLDObject *object)
147 __attribute((pure));
148 static kern_return_t init_from_object(KXLDObject *object);
149 static kern_return_t process_relocs_from_sections(KXLDObject *object);
150 #endif /* KXLD_USER_OR_OBJECT */
151
152 #if KXLD_PIC_KEXTS
153 static boolean_t target_supports_slideable_kexts(const KXLDObject *object);
154 #endif /* KXLD_PIC_KEXTS */
155
156
157 static kern_return_t export_macho_header(const KXLDObject *object, u_char *buf,
158 u_int ncmds, u_long *header_offset, u_long header_size);
159 #if KXLD_USER_OR_ILP32
160 static u_long get_macho_cmd_data_32(u_char *file, u_long offset,
161 u_int *filetype, u_int *ncmds);
162 static kern_return_t export_macho_header_32(const KXLDObject *object,
163 u_char *buf, u_int ncmds, u_long *header_offset, u_long header_size);
164 #endif /* KXLD_USER_OR_ILP32 */
165 #if KXLD_USER_OR_LP64
166 static u_long get_macho_cmd_data_64(u_char *file, u_long offset,
167 u_int *filetype, u_int *ncmds);
168 static kern_return_t export_macho_header_64(const KXLDObject *object,
169 u_char *buf, u_int ncmds, u_long *header_offset, u_long header_size);
170 #endif /* KXLD_USER_OR_LP64 */
171
172 #if KXLD_USER_OR_GOT || KXLD_USER_OR_COMMON
173 static kern_return_t add_section(KXLDObject *object, KXLDSect **sect);
174 #endif /* KXLD_USER_OR_GOT || KXLD_USER_OR_COMMON */
175
176 #if KXLD_USER_OR_COMMON
177 static kern_return_t resolve_common_symbols(KXLDObject *object);
178 #endif /* KXLD_USER_OR_COMMON */
179
180 #if KXLD_USER_OR_GOT
181 static boolean_t target_has_got(const KXLDObject *object) __attribute__((pure));
182 static kern_return_t create_got(KXLDObject *object);
183 static kern_return_t populate_got(KXLDObject *object);
184 #endif /* KXLD_USER_OR_GOT */
185
186 static KXLDSym *get_mutable_sym(const KXLDObject *object, const KXLDSym *sym);
187
188 static kern_return_t populate_kmod_info(KXLDObject *object);
189
190 /*******************************************************************************
191 * Prototypes that may need to be exported
192 *******************************************************************************/
193 static boolean_t kxld_object_target_needs_swap(const KXLDObject *object __unused);
194 static KXLDSeg * kxld_object_get_seg_by_name(const KXLDObject *object, const char *segname);
195 static KXLDSect * kxld_object_get_sect_by_name(const KXLDObject *object, const char *segname,
196 const char *sectname);
197
198 /*******************************************************************************
199 *******************************************************************************/
200 size_t
201 kxld_object_sizeof(void)
202 {
203 return sizeof(KXLDObject);
204 }
205
206 /*******************************************************************************
207 *******************************************************************************/
208 kern_return_t
209 kxld_object_init_from_macho(KXLDObject *object, u_char *file, u_long size,
210 const char *name, KXLDArray *section_order __unused,
211 cpu_type_t cputype, cpu_subtype_t cpusubtype, KXLDFlags flags __unused)
212 {
213 kern_return_t rval = KERN_FAILURE;
214 KXLDSeg * seg = NULL;
215 u_int i = 0;
216 u_char * my_file;
217
218 check(object);
219 check(file);
220 check(name);
221
222 object->name = name;
223
224 #if KXLD_USER_OR_OBJECT
225 object->section_order = section_order;
226 #endif
227 #if KXLD_PIC_KEXTS
228 object->include_kaslr_relocs = ((flags & kKXLDFlagIncludeRelocs) == kKXLDFlagIncludeRelocs);
229 #endif
230
231 /* Find the local architecture */
232
233 rval = get_target_machine_info(object, cputype, cpusubtype);
234 require_noerr(rval, finish);
235
236 /* Find the Mach-O slice for the target architecture */
237
238 rval = get_macho_slice_for_arch(object, file, size);
239 require_noerr(rval, finish);
240
241 if (isOldInterface) {
242 my_file = object->file;
243 }
244 else {
245 my_file = object->split_info.kextExecutable;
246 }
247
248 /* Allocate the symbol table */
249
250 if (!object->symtab) {
251 object->symtab = kxld_alloc(kxld_symtab_sizeof());
252 require_action(object->symtab, finish, rval=KERN_RESOURCE_SHORTAGE);
253 bzero(object->symtab, kxld_symtab_sizeof());
254 }
255
256 /* Build the relocator */
257
258 rval = kxld_relocator_init(&object->relocator,
259 my_file,
260 object->symtab, &object->sects,
261 object->cputype,
262 object->cpusubtype,
263 kxld_object_target_needs_swap(object));
264 require_noerr(rval, finish);
265
266 /* There are four types of Mach-O files that we can support:
267 * 1) 32-bit MH_OBJECT - Snow Leopard and earlier
268 * 2) 32-bit MH_KEXT_BUNDLE - Lion and Later
269 * 3) 64-bit MH_OBJECT - Unsupported
270 * 4) 64-bit MH_KEXT_BUNDLE - Snow Leopard and Later
271 */
272
273 if (kxld_object_is_32_bit(object)) {
274 struct mach_header *mach_hdr = (struct mach_header *) ((void *) my_file);
275 object->filetype = mach_hdr->filetype;
276 } else {
277 struct mach_header_64 *mach_hdr = (struct mach_header_64 *) ((void *) my_file);
278 object->filetype = mach_hdr->filetype;
279 }
280
281 switch (object->filetype) {
282 #if KXLD_USER_OR_BUNDLE
283 case MH_KEXT_BUNDLE:
284 rval = init_from_bundle(object);
285 require_noerr(rval, finish);
286 break;
287 #endif /* KXLD_USER_OR_BUNDLE */
288 #if KXLD_USER_OR_OBJECT
289 case MH_OBJECT:
290 rval = init_from_object(object);
291 require_noerr(rval, finish);
292 break;
293 #endif /* KXLD_USER_OR_OBJECT */
294 case MH_EXECUTE:
295 object->is_kernel = TRUE;
296 rval = init_from_execute(object);
297 require_noerr(rval, finish);
298 break;
299 default:
300 rval = KERN_FAILURE;
301 kxld_log(kKxldLogLinking, kKxldLogErr,
302 kKxldLogFiletypeNotSupported, object->filetype);
303 goto finish;
304 }
305
306 if (!kxld_object_is_kernel(object)) {
307 for (i = 0; i < object->segs.nitems; ++i) {
308 seg = kxld_array_get_item(&object->segs, i);
309 kxld_seg_set_vm_protections(seg,
310 target_supports_protected_segments(object));
311 }
312
313 seg = kxld_object_get_seg_by_name(object, SEG_LINKEDIT);
314 if (seg) {
315 (void) kxld_seg_populate_linkedit(seg, object->symtab,
316 kxld_object_is_32_bit(object)
317 #if KXLD_PIC_KEXTS
318 , &object->locrelocs, &object->extrelocs,
319 target_supports_slideable_kexts(object)
320 #endif
321 , isOldInterface ? 0 : object->splitinfolc.datasize
322 );
323 }
324 }
325
326 (void) set_is_object_linked(object);
327
328 rval = KERN_SUCCESS;
329 finish:
330 return rval;
331 }
332
333 /*******************************************************************************
334 *******************************************************************************/
335 splitKextLinkInfo *
336 kxld_object_get_link_info(KXLDObject *object)
337 {
338 check(object);
339
340 return &object->split_info;
341 }
342
343
344 /*******************************************************************************
345 *******************************************************************************/
346 void
347 kxld_object_set_link_info(KXLDObject *object, splitKextLinkInfo *link_info)
348 {
349 check(object);
350 check(link_info);
351
352 object->split_info.vmaddr_TEXT = link_info->vmaddr_TEXT;
353 object->split_info.vmaddr_TEXT_EXEC = link_info->vmaddr_TEXT_EXEC;
354 object->split_info.vmaddr_DATA = link_info->vmaddr_DATA;
355 object->split_info.vmaddr_DATA_CONST = link_info->vmaddr_DATA_CONST;
356 object->split_info.vmaddr_LLVM_COV = link_info->vmaddr_LLVM_COV;
357 object->split_info.vmaddr_LINKEDIT = link_info->vmaddr_LINKEDIT;
358
359 return;
360 }
361
362 /*******************************************************************************
363 *******************************************************************************/
364 kern_return_t
365 get_target_machine_info(KXLDObject *object, cpu_type_t cputype __unused,
366 cpu_subtype_t cpusubtype __unused)
367 {
368 #if KERNEL
369
370 /* Because the kernel can only link for its own architecture, we know what
371 * the host and target architectures are at compile time, so we can use
372 * a vastly simplified version of this function.
373 */
374
375 check(object);
376
377 #if defined(__x86_64__)
378 object->cputype = CPU_TYPE_X86_64;
379 /* FIXME: we need clang to provide a __x86_64h__ macro for the sub-type. Using
380 * __AVX2__ is a temporary solution until this is available. */
381 #if defined(__AVX2__)
382 object->cpusubtype = CPU_SUBTYPE_X86_64_H;
383 #else
384 object->cpusubtype = CPU_SUBTYPE_X86_64_ALL;
385 #endif
386 return KERN_SUCCESS;
387 #else
388 kxld_log(kKxldLogLinking, kKxldLogErr,
389 kKxldLogArchNotSupported, _mh_execute_header->cputype);
390 return KERN_NOT_SUPPORTED;
391 #endif /* Supported architecture defines */
392
393
394 #else /* !KERNEL */
395
396 /* User-space must look up the architecture it's running on and the target
397 * architecture at run-time.
398 */
399
400 kern_return_t rval = KERN_FAILURE;
401 const NXArchInfo *host_arch = NULL;
402
403 check(object);
404
405 host_arch = NXGetLocalArchInfo();
406 require_action(host_arch, finish, rval=KERN_FAILURE);
407
408 object->host_order = host_arch->byteorder;
409
410 /* If the user did not specify a cputype, use the local architecture.
411 */
412
413 if (cputype) {
414 object->cputype = cputype;
415 object->cpusubtype = cpusubtype;
416 } else {
417 object->cputype = host_arch->cputype;
418 object->target_order = object->host_order;
419
420 switch (object->cputype) {
421 case CPU_TYPE_I386:
422 object->cpusubtype = CPU_SUBTYPE_I386_ALL;
423 break;
424 case CPU_TYPE_X86_64:
425 object->cpusubtype = CPU_SUBTYPE_X86_64_ALL;
426 break;
427 case CPU_TYPE_ARM:
428 object->cpusubtype = CPU_SUBTYPE_ARM_ALL;
429 break;
430 case CPU_TYPE_ARM64:
431 object->cpusubtype = CPU_SUBTYPE_ARM64_ALL;
432 break;
433 default:
434 object->cpusubtype = 0;
435 break;
436 }
437 }
438
439 /* Validate that we support the target architecture and record its
440 * endianness.
441 */
442
443 switch(object->cputype) {
444 case CPU_TYPE_ARM:
445 case CPU_TYPE_ARM64:
446 case CPU_TYPE_I386:
447 case CPU_TYPE_X86_64:
448 object->target_order = NX_LittleEndian;
449 break;
450 default:
451 rval = KERN_NOT_SUPPORTED;
452 kxld_log(kKxldLogLinking, kKxldLogErr,
453 kKxldLogArchNotSupported, object->cputype);
454 goto finish;
455 }
456
457 rval = KERN_SUCCESS;
458
459 finish:
460 return rval;
461 #endif /* KERNEL */
462 }
463
464 /*******************************************************************************
465 *******************************************************************************/
466 static kern_return_t
467 get_macho_slice_for_arch(KXLDObject *object, u_char *file, u_long size)
468 {
469 kern_return_t rval = KERN_FAILURE;
470 struct mach_header *mach_hdr = NULL;
471 #if !KERNEL
472 struct fat_header *fat = (struct fat_header *) ((void *) file);
473 struct fat_arch *archs = (struct fat_arch *) &fat[1];
474 boolean_t swap = FALSE;
475 #endif /* KERNEL */
476 u_char *my_file = file;
477 u_long my_file_size = size;
478
479 check(object);
480 check(file);
481 check(size);
482
483 /* We are assuming that we will never receive a fat file in the kernel */
484
485 #if !KERNEL
486 require_action(size >= sizeof(*fat), finish,
487 rval=KERN_FAILURE;
488 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogTruncatedMachO));
489
490 /* The fat header is always big endian, so swap if necessary */
491 if (fat->magic == FAT_CIGAM) {
492 (void) swap_fat_header(fat, object->host_order);
493 swap = TRUE;
494 }
495
496 if (fat->magic == FAT_MAGIC) {
497 struct fat_arch *arch = NULL;
498
499 require_action(size >= (sizeof(*fat) + (fat->nfat_arch * sizeof(*archs))),
500 finish,
501 rval=KERN_FAILURE;
502 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogTruncatedMachO));
503
504 /* Swap the fat_arch structures if necessary */
505 if (swap) {
506 (void) swap_fat_arch(archs, fat->nfat_arch, object->host_order);
507 }
508
509 /* Locate the Mach-O for the requested architecture */
510
511 arch = NXFindBestFatArch(object->cputype, object->cpusubtype, archs, fat->nfat_arch);
512 require_action(arch, finish, rval=KERN_FAILURE;
513 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogArchNotFound));
514 require_action(size >= arch->offset + arch->size, finish,
515 rval=KERN_FAILURE;
516 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogTruncatedMachO));
517
518 my_file = my_file + arch->offset;
519 my_file_size = arch->size;
520 }
521 #endif /* !KERNEL */
522
523 /* Swap the Mach-O's headers to this architecture if necessary */
524 if (kxld_object_is_32_bit(object)) {
525 rval = validate_and_swap_macho_32(my_file, my_file_size
526 #if !KERNEL
527 , object->host_order
528 #endif /* !KERNEL */
529 );
530 } else {
531 rval = validate_and_swap_macho_64(my_file, my_file_size
532 #if !KERNEL
533 , object->host_order
534 #endif /* !KERNEL */
535 );
536 }
537 require_noerr(rval, finish);
538
539 mach_hdr = (struct mach_header *) ((void *) my_file);
540 require_action(object->cputype == mach_hdr->cputype, finish,
541 rval=KERN_FAILURE;
542 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogTruncatedMachO));
543 object->cpusubtype = mach_hdr->cpusubtype; /* <rdar://problem/16008438> */
544
545 if (isOldInterface) {
546 object->file = my_file;
547 object->size = my_file_size;
548 }
549 else {
550 object->split_info.kextExecutable = my_file;
551 object->split_info.kextSize = my_file_size;
552 }
553
554 rval = KERN_SUCCESS;
555 finish:
556 return rval;
557 }
558
559 /*******************************************************************************
560 *******************************************************************************/
561 static kern_return_t
562 init_from_final_linked_image(KXLDObject *object, u_int *filetype_out,
563 struct symtab_command **symtab_hdr_out)
564 {
565 kern_return_t rval = KERN_FAILURE;
566 KXLDSeg *seg = NULL;
567 KXLDSect *sect = NULL;
568 struct load_command *cmd_hdr = NULL;
569 struct symtab_command *symtab_hdr = NULL;
570 struct uuid_command *uuid_hdr = NULL;
571 struct version_min_command *versionmin_hdr = NULL;
572 struct source_version_command *source_version_hdr = NULL;
573 u_long base_offset = 0;
574 u_long offset = 0;
575 u_long sect_offset = 0;
576 u_int filetype = 0;
577 u_int i = 0;
578 u_int j = 0;
579 u_int segi = 0;
580 u_int secti = 0;
581 u_int nsegs = 0;
582 u_int nsects = 0;
583 u_int ncmds = 0;
584 u_char *my_file;
585
586 if (isOldInterface) {
587 my_file = object->file;
588 }
589 else {
590 my_file = object->split_info.kextExecutable;
591 }
592
593 KXLD_3264_FUNC(kxld_object_is_32_bit(object), base_offset,
594 get_macho_cmd_data_32, get_macho_cmd_data_64,
595 my_file, offset, &filetype, &ncmds);
596
597 /* First pass to count segments and sections */
598
599 offset = base_offset;
600 for (i = 0; i < ncmds; ++i, offset += cmd_hdr->cmdsize) {
601 cmd_hdr = (struct load_command *) ((void *) (my_file + offset));
602
603 switch(cmd_hdr->cmd) {
604 #if KXLD_USER_OR_ILP32
605 case LC_SEGMENT:
606 {
607 struct segment_command *seg_hdr =
608 (struct segment_command *) cmd_hdr;
609
610 /* Ignore segments with no vm size */
611 if (!seg_hdr->vmsize) continue;
612
613 ++nsegs;
614 nsects += seg_hdr->nsects;
615 }
616 break;
617 #endif /* KXLD_USER_OR_ILP32 */
618 #if KXLD_USER_OR_LP64
619 case LC_SEGMENT_64:
620 {
621 struct segment_command_64 *seg_hdr =
622 (struct segment_command_64 *) ((void *) cmd_hdr);
623
624 /* Ignore segments with no vm size */
625 if (!seg_hdr->vmsize) continue;
626
627 ++nsegs;
628 nsects += seg_hdr->nsects;
629 }
630 break;
631 #endif /* KXLD_USER_OR_LP64 */
632 default:
633 continue;
634 }
635 }
636
637 /* Allocate the segments and sections */
638
639 if (nsegs) {
640 rval = kxld_array_init(&object->segs, sizeof(KXLDSeg), nsegs);
641 require_noerr(rval, finish);
642
643 rval = kxld_array_init(&object->sects, sizeof(KXLDSect), nsects);
644 require_noerr(rval, finish);
645 }
646
647 /* Initialize the segments and sections */
648
649 offset = base_offset;
650 for (i = 0; i < ncmds; ++i, offset += cmd_hdr->cmdsize) {
651 cmd_hdr = (struct load_command *) ((void *) (my_file + offset));
652 seg = NULL;
653
654 switch(cmd_hdr->cmd) {
655 #if KXLD_USER_OR_ILP32
656 case LC_SEGMENT:
657 {
658 struct segment_command *seg_hdr =
659 (struct segment_command *) cmd_hdr;
660
661 /* Ignore segments with no vm size */
662 if (!seg_hdr->vmsize) continue;
663
664 seg = kxld_array_get_item(&object->segs, segi++);
665
666 rval = kxld_seg_init_from_macho_32(seg, seg_hdr);
667 require_noerr(rval, finish);
668
669 sect_offset = offset + sizeof(*seg_hdr);
670 }
671 break;
672 #endif /* KXLD_USER_OR_ILP32 */
673 #if KXLD_USER_OR_LP64
674 case LC_SEGMENT_64:
675 {
676 struct segment_command_64 *seg_hdr =
677 (struct segment_command_64 *) ((void *) cmd_hdr);
678
679 /* Ignore segments with no vm size */
680 if (!seg_hdr->vmsize) continue;
681
682 seg = kxld_array_get_item(&object->segs, segi++);
683
684 rval = kxld_seg_init_from_macho_64(seg, seg_hdr);
685 require_noerr(rval, finish);
686
687 sect_offset = offset + sizeof(*seg_hdr);
688 }
689 break;
690 #endif /* KXLD_USER_OR_LP64 */
691 case LC_SYMTAB:
692 symtab_hdr = (struct symtab_command *) cmd_hdr;
693 break;
694 case LC_UUID:
695 uuid_hdr = (struct uuid_command *) cmd_hdr;
696 kxld_uuid_init_from_macho(&object->uuid, uuid_hdr);
697 break;
698 case LC_VERSION_MIN_MACOSX:
699 case LC_VERSION_MIN_IPHONEOS:
700 case LC_VERSION_MIN_TVOS:
701 case LC_VERSION_MIN_WATCHOS:
702 versionmin_hdr = (struct version_min_command *) cmd_hdr;
703 kxld_versionmin_init_from_macho(&object->versionmin, versionmin_hdr);
704 break;
705 case LC_SOURCE_VERSION:
706 source_version_hdr = (struct source_version_command *) (void *) cmd_hdr;
707 kxld_srcversion_init_from_macho(&object->srcversion, source_version_hdr);
708 break;
709 case LC_DYSYMTAB:
710 object->dysymtab_hdr = (struct dysymtab_command *) cmd_hdr;
711 rval = kxld_reloc_create_macho(&object->extrelocs, &object->relocator,
712 (struct relocation_info *) ((void *) (my_file + object->dysymtab_hdr->extreloff)),
713 object->dysymtab_hdr->nextrel);
714 require_noerr(rval, finish);
715
716 rval = kxld_reloc_create_macho(&object->locrelocs, &object->relocator,
717 (struct relocation_info *) ((void *) (my_file + object->dysymtab_hdr->locreloff)),
718 object->dysymtab_hdr->nlocrel);
719 require_noerr(rval, finish);
720
721 break;
722 case LC_UNIXTHREAD:
723 case LC_MAIN:
724 /* Don't need to do anything with UNIXTHREAD or MAIN for the kernel */
725 require_action(kxld_object_is_kernel(object),
726 finish, rval=KERN_FAILURE;
727 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
728 "LC_UNIXTHREAD/LC_MAIN segment is not valid in a kext."));
729 break;
730 case LC_SEGMENT_SPLIT_INFO:
731 if (isSplitKext) {
732 struct linkedit_data_command *split_info_hdr = NULL;
733 split_info_hdr = (struct linkedit_data_command *) (void *) cmd_hdr;
734 kxld_splitinfolc_init_from_macho(&object->splitinfolc, split_info_hdr);
735 }
736 break;
737 case LC_CODE_SIGNATURE:
738 case LC_DYLD_INFO:
739 case LC_DYLD_INFO_ONLY:
740 case LC_FUNCTION_STARTS:
741 case LC_DATA_IN_CODE:
742 case LC_DYLIB_CODE_SIGN_DRS:
743 /* Various metadata that might be stored in the linkedit segment */
744 break;
745 default:
746 rval=KERN_FAILURE;
747 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
748 "Invalid load command type in MH_KEXT_BUNDLE kext: %u.", cmd_hdr->cmd);
749 goto finish;
750 }
751
752 if (seg) {
753
754 /* Initialize the sections */
755 for (j = 0; j < seg->sects.nitems; ++j, ++secti) {
756 sect = kxld_array_get_item(&object->sects, secti);
757
758 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
759 kxld_sect_init_from_macho_32, kxld_sect_init_from_macho_64,
760 sect, my_file, &sect_offset, secti, &object->relocator);
761 require_noerr(rval, finish);
762
763 /* Add the section to the segment. This will also make sure
764 * that the sections and segments have the same segname.
765 */
766 rval = kxld_seg_add_section(seg, sect);
767 require_noerr(rval, finish);
768 }
769 rval = kxld_seg_finish_init(seg);
770 require_noerr(rval, finish);
771 }
772 }
773
774 if (filetype_out) *filetype_out = filetype;
775 if (symtab_hdr_out) *symtab_hdr_out = symtab_hdr;
776 object->is_final_image = TRUE;
777 rval = KERN_SUCCESS;
778 finish:
779 return rval;
780 }
781
782 /*******************************************************************************
783 *******************************************************************************/
784 static kern_return_t
785 init_from_execute(KXLDObject *object)
786 {
787 kern_return_t rval = KERN_FAILURE;
788 struct symtab_command *symtab_hdr = NULL;
789 u_int filetype = 0;
790 KXLDSeg * kernel_linkedit_seg = NULL; // used if running kernel
791 #if KXLD_USER_OR_OBJECT
792 KXLDSeg *seg = NULL;
793 KXLDSect *sect = NULL;
794 KXLDSectionName *sname = NULL;
795 u_int i = 0, j = 0, k = 0;
796 #endif /* KXLD_USER_OR_OBJECT */
797 u_char *my_file;
798
799 check(object);
800
801 if (isOldInterface) {
802 my_file = object->file;
803 }
804 else {
805 my_file = object->split_info.kextExecutable;
806 }
807
808 require_action(kxld_object_is_kernel(object), finish, rval=KERN_FAILURE);
809
810 rval = init_from_final_linked_image(object, &filetype, &symtab_hdr);
811 require_noerr(rval, finish);
812
813 require_action(filetype == MH_EXECUTE, finish, rval=KERN_FAILURE;
814 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
815 "The kernel file is not of type MH_EXECUTE."));
816
817 /* Initialize the symbol table. If this is the running kernel
818 * we will work from the in-memory linkedit segment;
819 * otherwise we work from the whole mach-o image.
820 */
821 #if KERNEL
822 kernel_linkedit_seg = kxld_object_get_seg_by_name(object, SEG_LINKEDIT);
823 require_action(kernel_linkedit_seg, finish, rval=KERN_FAILURE;
824 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO));
825 #endif
826
827 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
828 kxld_symtab_init_from_macho_32, kxld_symtab_init_from_macho_64,
829 object->symtab, symtab_hdr, my_file, kernel_linkedit_seg);
830 require_noerr(rval, finish);
831
832 #if KXLD_USER_OR_OBJECT
833 /* Save off the order of section names so that we can lay out kext
834 * sections for MH_OBJECT-based systems.
835 */
836 if (target_supports_object(object)) {
837
838 rval = kxld_array_init(object->section_order, sizeof(KXLDSectionName),
839 object->sects.nitems);
840 require_noerr(rval, finish);
841
842 /* Copy the section names into the section_order array for future kext
843 * section ordering.
844 */
845 for (i = 0, k = 0; i < object->segs.nitems; ++i) {
846 seg = kxld_array_get_item(&object->segs, i);
847
848 for (j = 0; j < seg->sects.nitems; ++j, ++k) {
849 sect = *(KXLDSect **) kxld_array_get_item(&seg->sects, j);
850 sname = kxld_array_get_item(object->section_order, k);
851
852 strlcpy(sname->segname, sect->segname, sizeof(sname->segname));
853 strlcpy(sname->sectname, sect->sectname, sizeof(sname->sectname));
854 }
855 }
856 }
857 #endif /* KXLD_USER_OR_OBJECT */
858
859 rval = KERN_SUCCESS;
860 finish:
861 return rval;
862 }
863
864 #if KXLD_USER_OR_BUNDLE
865 /*******************************************************************************
866 *******************************************************************************/
867 static boolean_t
868 target_supports_bundle(const KXLDObject *object __unused)
869 {
870 return TRUE;
871 }
872
873 /*******************************************************************************
874 *******************************************************************************/
875 static kern_return_t
876 init_from_bundle(KXLDObject *object)
877 {
878 kern_return_t rval = KERN_FAILURE;
879 struct symtab_command *symtab_hdr = NULL;
880 u_int filetype = 0;
881 u_char *my_file;
882
883 check(object);
884
885 if (isOldInterface) {
886 my_file = object->file;
887 }
888 else {
889 my_file = object->split_info.kextExecutable;
890 }
891
892 require_action(target_supports_bundle(object), finish,
893 rval=KERN_FAILURE;
894 kxld_log(kKxldLogLinking, kKxldLogErr,
895 kKxldLogFiletypeNotSupported, MH_KEXT_BUNDLE));
896
897 rval = init_from_final_linked_image(object, &filetype, &symtab_hdr);
898 require_noerr(rval, finish);
899
900 require_action(filetype == MH_KEXT_BUNDLE, finish,
901 rval=KERN_FAILURE);
902
903 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
904 kxld_symtab_init_from_macho_32, kxld_symtab_init_from_macho_64,
905 object->symtab, symtab_hdr, my_file,
906 /* kernel_linkedit_seg */ NULL);
907 require_noerr(rval, finish);
908
909 rval = KERN_SUCCESS;
910 finish:
911 return rval;
912 }
913 #endif /* KXLD_USER_OR_BUNDLE */
914
915 #if KXLD_USER_OR_OBJECT
916 /*******************************************************************************
917 *******************************************************************************/
918 static boolean_t target_supports_object(const KXLDObject *object)
919 {
920 return (object->cputype == CPU_TYPE_I386);
921 }
922
923 /*******************************************************************************
924 *******************************************************************************/
925 static kern_return_t
926 init_from_object(KXLDObject *object)
927 {
928 kern_return_t rval = KERN_FAILURE;
929 struct load_command *cmd_hdr = NULL;
930 struct symtab_command *symtab_hdr = NULL;
931 struct uuid_command *uuid_hdr = NULL;
932 KXLDSect *sect = NULL;
933 u_long offset = 0;
934 u_long sect_offset = 0;
935 u_int filetype = 0;
936 u_int ncmds = 0;
937 u_int nsects = 0;
938 u_int i = 0;
939 boolean_t has_segment = FALSE;
940 u_char *my_file;
941
942 check(object);
943
944 if (isOldInterface) {
945 my_file = object->file;
946 }
947 else {
948 my_file = object->split_info.kextExecutable;
949 }
950
951 require_action(target_supports_object(object),
952 finish, rval=KERN_FAILURE;
953 kxld_log(kKxldLogLinking, kKxldLogErr,
954 kKxldLogFiletypeNotSupported, MH_OBJECT));
955
956 KXLD_3264_FUNC(kxld_object_is_32_bit(object), offset,
957 get_macho_cmd_data_32, get_macho_cmd_data_64,
958 my_file, offset, &filetype, &ncmds);
959
960 require_action(filetype == MH_OBJECT, finish, rval=KERN_FAILURE);
961
962 /* MH_OBJECTs use one unnamed segment to contain all of the sections. We
963 * loop over all of the load commands to initialize the structures we
964 * expect. Then, we'll use the unnamed segment to get to all of the
965 * sections, and then use those sections to create the actual segments.
966 */
967
968 for (; i < ncmds; ++i, offset += cmd_hdr->cmdsize) {
969 cmd_hdr = (struct load_command *) ((void *) (my_file + offset));
970
971 switch(cmd_hdr->cmd) {
972 #if KXLD_USER_OR_ILP32
973 case LC_SEGMENT:
974 {
975 struct segment_command *seg_hdr =
976 (struct segment_command *) cmd_hdr;
977
978 /* Ignore segments with no vm size */
979 if (!seg_hdr->vmsize) continue;
980
981 /* Ignore LINKEDIT segments */
982 if (streq_safe(seg_hdr->segname, SEG_LINKEDIT,
983 const_strlen(SEG_LINKEDIT)))
984 {
985 continue;
986 }
987
988 require_action(kxld_object_is_32_bit(object), finish, rval=KERN_FAILURE;
989 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
990 "LC_SEGMENT in 64-bit kext."));
991 require_action(!has_segment, finish, rval=KERN_FAILURE;
992 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
993 "Multiple segments in an MH_OBJECT kext."));
994
995 nsects = seg_hdr->nsects;
996 sect_offset = offset + sizeof(*seg_hdr);
997 has_segment = TRUE;
998 }
999 break;
1000 #endif /* KXLD_USER_OR_ILP32 */
1001 #if KXLD_USER_OR_LP64
1002 case LC_SEGMENT_64:
1003 {
1004 struct segment_command_64 *seg_hdr =
1005 (struct segment_command_64 *) ((void *) cmd_hdr);
1006
1007 /* Ignore segments with no vm size */
1008 if (!seg_hdr->vmsize) continue;
1009
1010 /* Ignore LINKEDIT segments */
1011 if (streq_safe(seg_hdr->segname, SEG_LINKEDIT,
1012 const_strlen(SEG_LINKEDIT)))
1013 {
1014 continue;
1015 }
1016
1017 require_action(!kxld_object_is_32_bit(object), finish, rval=KERN_FAILURE;
1018 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
1019 "LC_SEGMENT_64 in a 32-bit kext."));
1020 require_action(!has_segment, finish, rval=KERN_FAILURE;
1021 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
1022 "Multiple segments in an MH_OBJECT kext."));
1023
1024 nsects = seg_hdr->nsects;
1025 sect_offset = offset + sizeof(*seg_hdr);
1026 has_segment = TRUE;
1027 }
1028 break;
1029 #endif /* KXLD_USER_OR_LP64 */
1030 case LC_SYMTAB:
1031 symtab_hdr = (struct symtab_command *) cmd_hdr;
1032
1033 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
1034 kxld_symtab_init_from_macho_32, kxld_symtab_init_from_macho_64,
1035 object->symtab, symtab_hdr, my_file,
1036 /* kernel_linkedit_seg */ NULL);
1037 require_noerr(rval, finish);
1038 break;
1039 case LC_UUID:
1040 uuid_hdr = (struct uuid_command *) cmd_hdr;
1041 kxld_uuid_init_from_macho(&object->uuid, uuid_hdr);
1042 break;
1043 case LC_UNIXTHREAD:
1044 case LC_MAIN:
1045 /* Don't need to do anything with UNIXTHREAD or MAIN */
1046 break;
1047 case LC_CODE_SIGNATURE:
1048 case LC_DYLD_INFO:
1049 case LC_DYLD_INFO_ONLY:
1050 case LC_FUNCTION_STARTS:
1051 case LC_DATA_IN_CODE:
1052 case LC_DYLIB_CODE_SIGN_DRS:
1053 /* Various metadata that might be stored in the linkedit segment */
1054 break;
1055 case LC_VERSION_MIN_MACOSX:
1056 case LC_VERSION_MIN_IPHONEOS:
1057 case LC_VERSION_MIN_TVOS:
1058 case LC_VERSION_MIN_WATCHOS:
1059 case LC_SOURCE_VERSION:
1060 /* Not supported for object files, fall through */
1061 default:
1062 rval = KERN_FAILURE;
1063 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
1064 "Invalid load command type in MH_OBJECT kext: %u.", cmd_hdr->cmd);
1065 goto finish;
1066 }
1067 }
1068
1069 if (has_segment) {
1070
1071 /* Get the number of sections from the segment and build the section index */
1072
1073 rval = kxld_array_init(&object->sects, sizeof(KXLDSect), nsects);
1074 require_noerr(rval, finish);
1075
1076 /* Loop over all of the sections to initialize the section index */
1077
1078 for (i = 0; i < nsects; ++i) {
1079 sect = kxld_array_get_item(&object->sects, i);
1080
1081 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
1082 kxld_sect_init_from_macho_32, kxld_sect_init_from_macho_64,
1083 sect, my_file, &sect_offset, i, &object->relocator);
1084 require_noerr(rval, finish);
1085 }
1086
1087 /* Create special sections */
1088
1089 #if KXLD_USER_OR_GOT
1090 rval = create_got(object);
1091 require_noerr(rval, finish);
1092 #endif /* KXLD_USER_OR_GOT */
1093
1094 #if KXLD_USER_OR_COMMON
1095 rval = resolve_common_symbols(object);
1096 require_noerr(rval, finish);
1097 #endif /* KXLD_USER_OR_COMMON */
1098
1099 /* Create the segments from the section index */
1100
1101 rval = kxld_seg_create_seg_from_sections(&object->segs, &object->sects);
1102 require_noerr(rval, finish);
1103
1104 rval = kxld_seg_finalize_object_segment(&object->segs,
1105 object->section_order, get_macho_header_size(object));
1106 require_noerr(rval, finish);
1107
1108 rval = kxld_seg_init_linkedit(&object->segs);
1109 require_noerr(rval, finish);
1110 }
1111
1112 rval = KERN_SUCCESS;
1113 finish:
1114 return rval;
1115 }
1116 #endif /* KXLD_USER_OR_OBJECT */
1117
1118 #if KXLD_USER_OR_ILP32
1119 /*******************************************************************************
1120 *******************************************************************************/
1121 static u_long
1122 get_macho_cmd_data_32(u_char *file, u_long offset, u_int *filetype, u_int *ncmds)
1123 {
1124 struct mach_header *mach_hdr = (struct mach_header *) ((void *) (file + offset));
1125
1126 if (filetype) *filetype = mach_hdr->filetype;
1127 if (ncmds) *ncmds = mach_hdr->ncmds;
1128
1129 return sizeof(*mach_hdr);
1130 }
1131
1132 #endif /* KXLD_USER_OR_ILP32 */
1133
1134 #if KXLD_USER_OR_LP64
1135 /*******************************************************************************
1136 *******************************************************************************/
1137 static u_long
1138 get_macho_cmd_data_64(u_char *file, u_long offset, u_int *filetype, u_int *ncmds)
1139 {
1140 struct mach_header_64 *mach_hdr = (struct mach_header_64 *) ((void *) (file + offset));
1141
1142 if (filetype) *filetype = mach_hdr->filetype;
1143 if (ncmds) *ncmds = mach_hdr->ncmds;
1144
1145 return sizeof(*mach_hdr);
1146 }
1147 #endif /* KXLD_USER_OR_LP64 */
1148
1149 /*******************************************************************************
1150 *******************************************************************************/
1151 static u_long
1152 get_macho_header_size(const KXLDObject *object)
1153 {
1154 KXLDSeg *seg = NULL;
1155 u_long header_size = 0;
1156 u_int i = 0;
1157 boolean_t object_is_32_bit = kxld_object_is_32_bit(object);
1158
1159 check(object);
1160
1161 /* Mach, segment, symtab, and UUID headers */
1162
1163 header_size += object_is_32_bit ? sizeof(struct mach_header) : sizeof(struct mach_header_64);
1164
1165 for (i = 0; i < object->segs.nitems; ++i) {
1166 seg = kxld_array_get_item(&object->segs, i);
1167 header_size += kxld_seg_get_macho_header_size(seg, object_is_32_bit);
1168 }
1169
1170 header_size += kxld_symtab_get_macho_header_size();
1171
1172 #if KXLD_PIC_KEXTS
1173 if (target_supports_slideable_kexts(object)) {
1174 header_size += kxld_reloc_get_macho_header_size();
1175 }
1176 #endif /* KXLD_PIC_KEXTS */
1177
1178 if (object->uuid.has_uuid) {
1179 header_size += kxld_uuid_get_macho_header_size();
1180 }
1181
1182 if (object->versionmin.has_versionmin) {
1183 header_size += kxld_versionmin_get_macho_header_size();
1184 }
1185
1186 if (object->srcversion.has_srcversion) {
1187 header_size += kxld_srcversion_get_macho_header_size();
1188 }
1189
1190 if (isSplitKext && object->splitinfolc.has_splitinfolc) {
1191 header_size += kxld_splitinfolc_get_macho_header_size();
1192 }
1193
1194 return header_size;
1195 }
1196
1197 /*******************************************************************************
1198 *******************************************************************************/
1199 static u_long
1200 get_macho_data_size(const KXLDObject *object)
1201 {
1202 KXLDSeg *seg = NULL;
1203 u_long data_size = 0;
1204 u_int i = 0;
1205
1206 check(object);
1207
1208 /* total all segment vmsize values */
1209 for (i = 0; i < object->segs.nitems; ++i) {
1210 seg = kxld_array_get_item(&object->segs, i);
1211 data_size += (u_long) kxld_seg_get_vmsize(seg);
1212 }
1213
1214 #if KXLD_PIC_KEXTS
1215 {
1216 /* ensure that when we eventually emit the final linked object,
1217 * appending the __DYSYMTAB data after the __LINKEDIT data will
1218 * not overflow the space allocated for the __LINKEDIT segment
1219 */
1220
1221 u_long seg_vmsize = 0;
1222 u_long symtab_size = 0;
1223 u_long reloc_size = 0;
1224
1225 /* get current __LINKEDIT sizes */
1226 seg = kxld_object_get_seg_by_name(object, SEG_LINKEDIT);
1227
1228 seg_vmsize = (u_long) kxld_seg_get_vmsize(seg);
1229
1230 /* get size of symbol table data that will eventually be dumped
1231 * into the __LINKEDIT segment
1232 */
1233 symtab_size = kxld_symtab_get_macho_data_size(object->symtab, kxld_object_is_32_bit(object));
1234
1235 if (target_supports_slideable_kexts(object)) {
1236 /* get size of __DYSYMTAB relocation entries */
1237 reloc_size = kxld_reloc_get_macho_data_size(&object->locrelocs, &object->extrelocs);
1238 }
1239
1240 /* combine, and ensure they'll both fit within the page(s)
1241 * allocated for the __LINKEDIT segment. If they'd overflow,
1242 * increase the vmsize appropriately so no overflow will occur
1243 */
1244 if ((symtab_size + reloc_size) > seg_vmsize) {
1245 u_long overflow = (symtab_size + reloc_size) - seg_vmsize;
1246 data_size += kxld_round_page_cross_safe(overflow);
1247 }
1248 }
1249 #endif // KXLD_PIC_KEXTS
1250
1251 return data_size;
1252 }
1253
1254 /*******************************************************************************
1255 *******************************************************************************/
1256 boolean_t
1257 kxld_object_target_needs_swap(const KXLDObject *object __unused)
1258 {
1259 #if KERNEL
1260 return FALSE;
1261 #else
1262 return (object->target_order != object->host_order);
1263 #endif /* KERNEL */
1264 }
1265
1266 /*******************************************************************************
1267 *******************************************************************************/
1268 KXLDSeg *
1269 kxld_object_get_seg_by_name(const KXLDObject *object, const char *segname)
1270 {
1271 KXLDSeg *seg = NULL;
1272 u_int i = 0;
1273
1274 for (i = 0; i < object->segs.nitems; ++i) {
1275 seg = kxld_array_get_item(&object->segs, i);
1276
1277 if (streq_safe(segname, seg->segname, sizeof(seg->segname))) break;
1278
1279 seg = NULL;
1280 }
1281
1282 return seg;
1283 }
1284
1285 /*******************************************************************************
1286 *******************************************************************************/
1287 const KXLDRelocator *
1288 kxld_object_get_relocator(const KXLDObject * object)
1289 {
1290 check(object);
1291
1292 return &object->relocator;
1293 }
1294
1295 /*******************************************************************************
1296 *******************************************************************************/
1297 KXLDSect *
1298 kxld_object_get_sect_by_name(const KXLDObject *object, const char *segname,
1299 const char *sectname)
1300 {
1301 KXLDSect *sect = NULL;
1302 u_int i = 0;
1303
1304 for (i = 0; i < object->sects.nitems; ++i) {
1305 sect = kxld_array_get_item(&object->sects, i);
1306
1307 if (streq_safe(segname, sect->segname, sizeof(sect->segname)) &&
1308 streq_safe(sectname, sect->sectname, sizeof(sect->sectname)))
1309 {
1310 break;
1311 }
1312
1313 sect = NULL;
1314 }
1315
1316 return sect;
1317 }
1318
1319 /*******************************************************************************
1320 *******************************************************************************/
1321 const KXLDReloc *
1322 kxld_object_get_reloc_at_symbol(const KXLDObject *object, const KXLDSym *sym)
1323 {
1324 const KXLDReloc *reloc = NULL;
1325 const KXLDSect *sect = NULL;
1326 uint32_t offset = 0;
1327
1328 check(object);
1329 check(sym);
1330
1331 sect = kxld_object_get_section_by_index(object, sym->sectnum);
1332 require(sect, finish);
1333
1334 if (kxld_object_is_final_image(object)) {
1335 reloc = kxld_reloc_get_reloc_by_offset(&object->extrelocs,
1336 sym->base_addr);
1337 if (!reloc) {
1338 reloc = kxld_reloc_get_reloc_by_offset(&object->locrelocs,
1339 sym->base_addr);
1340 }
1341 } else {
1342 offset = kxld_sym_get_section_offset(sym, sect);
1343 reloc = kxld_reloc_get_reloc_by_offset(&sect->relocs, offset);
1344 }
1345
1346 finish:
1347 return reloc;
1348 }
1349
1350 /*******************************************************************************
1351 *******************************************************************************/
1352 const KXLDSym *
1353 kxld_object_get_symbol_of_reloc(const KXLDObject *object,
1354 const KXLDReloc *reloc, const KXLDSect *sect)
1355 {
1356 const KXLDSym *sym = NULL;
1357 u_char *my_file;
1358
1359 if (isOldInterface) {
1360 my_file = object->file;
1361 }
1362 else {
1363 my_file = object->split_info.kextExecutable;
1364 }
1365
1366 if (kxld_object_is_final_image(object)) {
1367 sym = kxld_reloc_get_symbol(&object->relocator, reloc, my_file);
1368 } else {
1369 sym = kxld_reloc_get_symbol(&object->relocator, reloc, sect->data);
1370 }
1371 return sym;
1372 }
1373
1374 /*******************************************************************************
1375 *******************************************************************************/
1376 const KXLDSect *
1377 kxld_object_get_section_by_index(const KXLDObject *object, u_int sectnum)
1378 {
1379 KXLDSect *sect = NULL;
1380
1381 check(object);
1382
1383 if (sectnum < object->sects.nitems) {
1384 sect = kxld_array_get_item(&object->sects, sectnum);
1385 }
1386
1387 return sect;
1388 }
1389
1390 /*******************************************************************************
1391 *******************************************************************************/
1392 const KXLDArray *
1393 kxld_object_get_extrelocs(const KXLDObject *object)
1394 {
1395 const KXLDArray *rval = NULL;
1396
1397 check(object);
1398
1399 if (kxld_object_is_final_image(object)) {
1400 rval = &object->extrelocs;
1401 }
1402
1403 return rval;
1404 }
1405
1406 /*******************************************************************************
1407 *******************************************************************************/
1408 const KXLDSymtab *
1409 kxld_object_get_symtab(const KXLDObject *object)
1410 {
1411 check(object);
1412
1413 return object->symtab;
1414 }
1415
1416 #if KXLD_USER_OR_GOT || KXLD_USER_OR_COMMON
1417 /*******************************************************************************
1418 *******************************************************************************/
1419 static kern_return_t
1420 add_section(KXLDObject *object, KXLDSect **sect)
1421 {
1422 kern_return_t rval = KERN_FAILURE;
1423 u_int nsects = object->sects.nitems;
1424
1425 rval = kxld_array_resize(&object->sects, nsects + 1);
1426 require_noerr(rval, finish);
1427
1428 *sect = kxld_array_get_item(&object->sects, nsects);
1429
1430 rval = KERN_SUCCESS;
1431
1432 finish:
1433 return rval;
1434 }
1435 #endif /* KXLD_USER_OR_GOT || KXLD_USER_OR_COMMON */
1436
1437 #if KXLD_USER_OR_COMMON
1438 /*******************************************************************************
1439 * If there are common symbols, calculate how much space they'll need
1440 * and create/grow the __DATA __common section to accommodate them.
1441 * Then, resolve them against that section.
1442 *******************************************************************************/
1443 static kern_return_t
1444 resolve_common_symbols(KXLDObject *object)
1445 {
1446 kern_return_t rval = KERN_FAILURE;
1447 KXLDSymtabIterator iter;
1448 KXLDSym *sym = NULL;
1449 KXLDSect *sect = NULL;
1450 kxld_addr_t base_addr = 0;
1451 kxld_size_t size = 0;
1452 kxld_size_t total_size = 0;
1453 u_int align = 0;
1454 u_int max_align = 0;
1455 u_int sectnum = 0;
1456
1457 if (!kxld_object_target_supports_common_symbols(object)) {
1458 rval = KERN_SUCCESS;
1459 goto finish;
1460 }
1461
1462 /* Iterate over the common symbols to calculate their total aligned size */
1463 kxld_symtab_iterator_init(&iter, object->symtab, kxld_sym_is_common, FALSE);
1464 while ((sym = kxld_symtab_iterator_get_next(&iter))) {
1465 align = kxld_sym_get_common_align(sym);
1466 size = kxld_sym_get_common_size(sym);
1467
1468 if (align > max_align) max_align = align;
1469
1470 total_size = kxld_align_address(total_size, align) + size;
1471 }
1472
1473 /* If there are common symbols, grow or create the __DATA __common section
1474 * to hold them.
1475 */
1476 if (total_size) {
1477 sect = kxld_object_get_sect_by_name(object, SEG_DATA, SECT_COMMON);
1478 if (sect) {
1479 base_addr = sect->base_addr + sect->size;
1480
1481 kxld_sect_grow(sect, total_size, max_align);
1482 } else {
1483 base_addr = 0;
1484
1485 rval = add_section(object, &sect);
1486 require_noerr(rval, finish);
1487
1488 kxld_sect_init_zerofill(sect, SEG_DATA, SECT_COMMON,
1489 total_size, max_align);
1490 }
1491
1492 /* Resolve the common symbols against the new section */
1493 rval = kxld_array_get_index(&object->sects, sect, &sectnum);
1494 require_noerr(rval, finish);
1495
1496 kxld_symtab_iterator_reset(&iter);
1497 while ((sym = kxld_symtab_iterator_get_next(&iter))) {
1498 align = kxld_sym_get_common_align(sym);
1499 size = kxld_sym_get_common_size(sym);
1500
1501 base_addr = kxld_align_address(base_addr, align);
1502 kxld_sym_resolve_common(sym, sectnum, base_addr);
1503
1504 base_addr += size;
1505 }
1506 }
1507
1508 rval = KERN_SUCCESS;
1509
1510 finish:
1511 return rval;
1512 }
1513 #endif /* KXLD_USER_OR_COMMON */
1514
1515 #if KXLD_USER_OR_GOT
1516 /*******************************************************************************
1517 *******************************************************************************/
1518 static boolean_t
1519 target_has_got(const KXLDObject *object)
1520 {
1521 return FALSE:
1522 }
1523
1524 /*******************************************************************************
1525 * Create and initialize the Global Offset Table
1526 *******************************************************************************/
1527 static kern_return_t
1528 create_got(KXLDObject *object)
1529 {
1530 kern_return_t rval = KERN_FAILURE;
1531 KXLDSect *sect = NULL;
1532 u_int ngots = 0;
1533 u_int i = 0;
1534
1535 if (!target_has_got(object)) {
1536 rval = KERN_SUCCESS;
1537 goto finish;
1538 }
1539
1540 for (i = 0; i < object->sects.nitems; ++i) {
1541 sect = kxld_array_get_item(&object->sects, i);
1542 ngots += kxld_sect_get_ngots(sect, &object->relocator,
1543 object->symtab);
1544 }
1545
1546 rval = add_section(object, &sect);
1547 require_noerr(rval, finish);
1548
1549 rval = kxld_sect_init_got(sect, ngots);
1550 require_noerr(rval, finish);
1551
1552 object->got_is_created = TRUE;
1553 rval = KERN_SUCCESS;
1554
1555 finish:
1556 return rval;
1557 }
1558
1559 /*******************************************************************************
1560 *******************************************************************************/
1561 static kern_return_t
1562 populate_got(KXLDObject *object)
1563 {
1564 kern_return_t rval = KERN_FAILURE;
1565 KXLDSect *sect = NULL;
1566 u_int i = 0;
1567
1568 if (!target_has_got(object) || !object->got_is_created) {
1569 rval = KERN_SUCCESS;
1570 goto finish;
1571 }
1572
1573 for (i = 0; i < object->sects.nitems; ++i) {
1574 sect = kxld_array_get_item(&object->sects, i);
1575 if (streq_safe(sect->segname, KXLD_SEG_GOT, sizeof(KXLD_SEG_GOT)) &&
1576 streq_safe(sect->sectname, KXLD_SECT_GOT, sizeof(KXLD_SECT_GOT)))
1577 {
1578 kxld_sect_populate_got(sect, object->symtab,
1579 kxld_object_target_needs_swap(object));
1580 break;
1581 }
1582 }
1583
1584 require_action(i < object->sects.nitems, finish, rval=KXLD_MISSING_GOT);
1585
1586 rval = KERN_SUCCESS;
1587
1588 finish:
1589 return rval;
1590 }
1591 #endif /* KXLD_USER_OR_GOT */
1592
1593 /*******************************************************************************
1594 *******************************************************************************/
1595 static boolean_t
1596 target_supports_protected_segments(const KXLDObject *object)
1597 {
1598 return (object->is_final_image &&
1599 (object->cputype == CPU_TYPE_X86_64 ||
1600 object->cputype == CPU_TYPE_ARM ||
1601 object->cputype == CPU_TYPE_ARM64));
1602 }
1603
1604 /*******************************************************************************
1605 *******************************************************************************/
1606 static void
1607 set_is_object_linked(KXLDObject *object)
1608 {
1609 u_int i = 0;
1610
1611 if (kxld_object_is_kernel(object)) {
1612 object->is_linked = TRUE;
1613 return;
1614 }
1615
1616 if (object->is_final_image) {
1617 object->is_linked = !object->extrelocs.nitems;
1618 return;
1619 }
1620
1621 object->is_linked = TRUE;
1622 for (i = 0; i < object->sects.nitems; ++i) {
1623 KXLDSect *sect = kxld_array_get_item(&object->sects, i);
1624 if (sect->relocs.nitems) {
1625 object->is_linked = FALSE;
1626 break;
1627 }
1628 }
1629 }
1630
1631
1632 /*******************************************************************************
1633 *******************************************************************************/
1634 void kxld_object_clear(KXLDObject *object)
1635 {
1636 KXLDSeg *seg = NULL;
1637 KXLDSect *sect = NULL;
1638 u_int i;
1639 u_char *my_file;
1640
1641 check(object);
1642
1643 if (isOldInterface) {
1644 my_file = object->file;
1645 }
1646 else {
1647 my_file = object->split_info.kextExecutable;
1648 }
1649
1650 #if !KERNEL
1651 if (kxld_object_is_kernel(object)) {
1652 unswap_macho(my_file, object->host_order, object->target_order);
1653 }
1654 #endif /* !KERNEL */
1655
1656 for (i = 0; i < object->segs.nitems; ++i) {
1657 seg = kxld_array_get_item(&object->segs, i);
1658 kxld_seg_clear(seg);
1659 }
1660 kxld_array_reset(&object->segs);
1661
1662 for (i = 0; i < object->sects.nitems; ++i) {
1663 sect = kxld_array_get_item(&object->sects, i);
1664 kxld_sect_clear(sect);
1665 }
1666 kxld_array_reset(&object->sects);
1667
1668 kxld_array_reset(&object->extrelocs);
1669 kxld_array_reset(&object->locrelocs);
1670 kxld_relocator_clear(&object->relocator);
1671 kxld_uuid_clear(&object->uuid);
1672 kxld_versionmin_clear(&object->versionmin);
1673 kxld_srcversion_clear(&object->srcversion);
1674
1675 if (object->symtab) kxld_symtab_clear(object->symtab);
1676
1677 if (isOldInterface) {
1678 object->file = NULL;
1679 object->size = 0;
1680 }
1681 else {
1682 kxld_splitinfolc_clear(&object->splitinfolc);
1683 object->split_info.kextExecutable = NULL;
1684 object->split_info.kextSize = 0;
1685 }
1686 object->filetype = 0;
1687 object->cputype = 0;
1688 object->cpusubtype = 0;
1689 object->is_kernel = FALSE;
1690 object->is_final_image = FALSE;
1691 object->is_linked = FALSE;
1692 object->got_is_created = FALSE;
1693
1694 #if KXLD_USER_OR_OBJECT
1695 object->section_order = NULL;
1696 #endif
1697 #if !KERNEL
1698 object->host_order = 0;
1699 object->target_order = 0;
1700 #endif
1701 }
1702
1703 /*******************************************************************************
1704 *******************************************************************************/
1705 void kxld_object_deinit(KXLDObject *object __unused)
1706 {
1707 KXLDSeg *seg = NULL;
1708 KXLDSect *sect = NULL;
1709 u_int i;
1710 u_char *my_file;
1711
1712 check(object);
1713
1714 if (isOldInterface) {
1715 my_file = object->file;
1716 }
1717 else {
1718 my_file = object->split_info.kextExecutable;
1719 }
1720
1721 #if !KERNEL
1722 if (my_file && kxld_object_is_kernel(object)) {
1723 unswap_macho(my_file, object->host_order, object->target_order);
1724 }
1725 #endif /* !KERNEL */
1726
1727 for (i = 0; i < object->segs.maxitems; ++i) {
1728 seg = kxld_array_get_slot(&object->segs, i);
1729 kxld_seg_deinit(seg);
1730 }
1731 kxld_array_deinit(&object->segs);
1732
1733 for (i = 0; i < object->sects.maxitems; ++i) {
1734 sect = kxld_array_get_slot(&object->sects, i);
1735 kxld_sect_deinit(sect);
1736 }
1737 kxld_array_deinit(&object->sects);
1738
1739 kxld_array_deinit(&object->extrelocs);
1740 kxld_array_deinit(&object->locrelocs);
1741
1742 if (object->symtab) {
1743 kxld_symtab_deinit(object->symtab);
1744 kxld_free(object->symtab, kxld_symtab_sizeof());
1745 }
1746
1747 bzero(object, sizeof(*object));
1748 }
1749
1750 /*******************************************************************************
1751 *******************************************************************************/
1752 const u_char *
1753 kxld_object_get_file(const KXLDObject *object)
1754 {
1755 const u_char *my_file;
1756
1757 check(object);
1758
1759 if (isOldInterface) {
1760 my_file = object->file;
1761 }
1762 else {
1763 my_file = object->split_info.kextExecutable;
1764 }
1765
1766 return my_file;
1767 }
1768
1769 /*******************************************************************************
1770 *******************************************************************************/
1771 const char *
1772 kxld_object_get_name(const KXLDObject *object)
1773 {
1774 check(object);
1775
1776 return object->name;
1777 }
1778
1779 /*******************************************************************************
1780 *******************************************************************************/
1781 boolean_t
1782 kxld_object_is_32_bit(const KXLDObject *object)
1783 {
1784 check(object);
1785
1786 return kxld_is_32_bit(object->cputype);
1787 }
1788
1789 /*******************************************************************************
1790 *******************************************************************************/
1791 boolean_t
1792 kxld_object_is_final_image(const KXLDObject *object)
1793 {
1794 check(object);
1795
1796 return object->is_final_image;
1797 }
1798
1799 /*******************************************************************************
1800 *******************************************************************************/
1801 boolean_t
1802 kxld_object_is_kernel(const KXLDObject *object)
1803 {
1804 check(object);
1805
1806 return object->is_kernel;
1807 }
1808
1809 /*******************************************************************************
1810 *******************************************************************************/
1811 boolean_t
1812 kxld_object_is_linked(const KXLDObject *object)
1813 {
1814 check(object);
1815
1816 return object->is_linked;
1817 }
1818
1819 /*******************************************************************************
1820 *******************************************************************************/
1821 boolean_t
1822 kxld_object_target_supports_strict_patching(const KXLDObject *object)
1823 {
1824 check(object);
1825
1826 return (object->cputype != CPU_TYPE_I386);
1827 }
1828
1829 /*******************************************************************************
1830 *******************************************************************************/
1831 boolean_t
1832 kxld_object_target_supports_common_symbols(const KXLDObject *object)
1833 {
1834 check(object);
1835
1836 return (object->cputype == CPU_TYPE_I386);
1837 }
1838
1839
1840 /*******************************************************************************
1841 *******************************************************************************/
1842 void
1843 kxld_object_get_vmsize_for_seg_by_name(const KXLDObject *object,
1844 const char *segname,
1845 u_long *vmsize)
1846 {
1847 check(object);
1848 check(segname);
1849 check(vmsize);
1850
1851 KXLDSeg *seg = NULL;
1852 u_long my_size = 0;
1853
1854 /* segment vmsize */
1855 seg = kxld_object_get_seg_by_name(object, segname);
1856
1857 my_size = (u_long) kxld_seg_get_vmsize(seg);
1858
1859 #if KXLD_PIC_KEXTS
1860 if (kxld_seg_is_linkedit_seg(seg))
1861 {
1862 u_long reloc_size = 0;
1863
1864 if (target_supports_slideable_kexts(object)) {
1865 /* get size of __DYSYMTAB relocation entries */
1866 reloc_size = kxld_reloc_get_macho_data_size(&object->locrelocs, &object->extrelocs);
1867 my_size += reloc_size;
1868 }
1869 }
1870 #endif
1871
1872 *vmsize = my_size;
1873 }
1874
1875 /*******************************************************************************
1876 *******************************************************************************/
1877 void
1878 kxld_object_get_vmsize(const KXLDObject *object, u_long *header_size,
1879 u_long *vmsize)
1880 {
1881 check(object);
1882 check(header_size);
1883 check(vmsize);
1884 *header_size = 0;
1885 *vmsize = 0;
1886
1887 /* vmsize is the padded header page(s) + segment vmsizes */
1888
1889 *header_size = (object->is_final_image) ?
1890 0 : (u_long)kxld_round_page_cross_safe(get_macho_header_size(object));
1891
1892 *vmsize = *header_size + get_macho_data_size(object);
1893
1894 }
1895
1896 /*******************************************************************************
1897 *******************************************************************************/
1898 void
1899 kxld_object_set_linked_object_size(KXLDObject *object, u_long vmsize)
1900 {
1901 check(object);
1902
1903 if (isOldInterface) {
1904 object->output_buffer_size = vmsize; /* cache this for use later */
1905 }
1906 else {
1907 object->split_info.linkedKextSize = vmsize;
1908 }
1909 return;
1910 }
1911
1912 /*******************************************************************************
1913 *******************************************************************************/
1914 kern_return_t
1915 kxld_object_export_linked_object(const KXLDObject *object,
1916 void *linked_object
1917 )
1918 {
1919 kern_return_t rval = KERN_FAILURE;
1920 KXLDSeg *seg = NULL;
1921 u_long size = 0;
1922 u_long header_size = 0;
1923 u_long header_offset = 0;
1924 u_long data_offset = 0;
1925 u_int ncmds = 0;
1926 u_int i = 0;
1927 boolean_t is_32bit_object = kxld_object_is_32_bit(object);
1928 kxld_addr_t link_addr;
1929 u_char *my_linked_object;
1930
1931 check(object);
1932 check(linked_object);
1933
1934 if (isOldInterface) {
1935 size = object->output_buffer_size;
1936 link_addr = object->link_addr;
1937 my_linked_object = (u_char *) linked_object;
1938 }
1939 else {
1940 size = ((splitKextLinkInfo *)linked_object)->linkedKextSize;
1941 link_addr = ((splitKextLinkInfo *)linked_object)->vmaddr_TEXT;
1942 my_linked_object = ((splitKextLinkInfo *)linked_object)->linkedKext;
1943 }
1944
1945 /* Calculate the size of the headers and data */
1946
1947 header_size = get_macho_header_size(object);
1948
1949 /* Copy data to the file */
1950
1951 ncmds = object->segs.nitems + 1 /* LC_SYMTAB */;
1952
1953 #if KXLD_PIC_KEXTS
1954 /* don't write out a DYSYMTAB segment for targets that can't digest it
1955 */
1956 if (target_supports_slideable_kexts(object)) {
1957 ncmds++; /* dysymtab */
1958 }
1959 #endif /* KXLD_PIC_KEXTS */
1960
1961 if (object->uuid.has_uuid == TRUE) {
1962 ncmds++;
1963 }
1964
1965 if (object->versionmin.has_versionmin == TRUE) {
1966 ncmds++;
1967 }
1968
1969 if (object->srcversion.has_srcversion == TRUE) {
1970 ncmds++;
1971 }
1972
1973 if (isSplitKext && object->splitinfolc.has_splitinfolc) {
1974 ncmds++;
1975 }
1976
1977 rval = export_macho_header(object, my_linked_object, ncmds, &header_offset, header_size);
1978 require_noerr(rval, finish);
1979
1980 for (i = 0; i < object->segs.nitems; ++i) {
1981 seg = kxld_array_get_item(&object->segs, i);
1982
1983 rval = kxld_seg_export_macho_to_vm(seg, my_linked_object, &header_offset,
1984 header_size, size, link_addr, is_32bit_object);
1985 require_noerr(rval, finish);
1986 }
1987
1988 seg = kxld_object_get_seg_by_name(object, SEG_LINKEDIT);
1989 data_offset = (u_long) (seg->link_addr - link_addr);
1990
1991 // data_offset is used to set the fileoff in the macho header load commands
1992 rval = kxld_symtab_export_macho(object->symtab,
1993 my_linked_object,
1994 &header_offset,
1995 header_size,
1996 &data_offset, size, is_32bit_object);
1997 require_noerr(rval, finish);
1998
1999 // data_offset now points past the symbol tab and strings data in the linkedit
2000 // segment - (it was used to set new values for symoff and stroff)
2001
2002 #if KXLD_PIC_KEXTS
2003 if (target_supports_slideable_kexts(object)) {
2004 rval = kxld_reloc_export_macho(&object->relocator,
2005 &object->locrelocs,
2006 &object->extrelocs,
2007 my_linked_object,
2008 &header_offset,
2009 header_size,
2010 &data_offset, size);
2011 require_noerr(rval, finish);
2012 }
2013 #endif /* KXLD_PIC_KEXTS */
2014
2015 if (object->uuid.has_uuid) {
2016 rval = kxld_uuid_export_macho(&object->uuid, my_linked_object, &header_offset, header_size);
2017 require_noerr(rval, finish);
2018 }
2019
2020 if (object->versionmin.has_versionmin) {
2021 rval = kxld_versionmin_export_macho(&object->versionmin, my_linked_object, &header_offset, header_size);
2022 require_noerr(rval, finish);
2023 }
2024
2025 if (object->srcversion.has_srcversion) {
2026 rval = kxld_srcversion_export_macho(&object->srcversion, my_linked_object, &header_offset, header_size);
2027 require_noerr(rval, finish);
2028 }
2029
2030 if (isSplitKext && object->splitinfolc.has_splitinfolc) {
2031 rval = kxld_splitinfolc_export_macho(&object->splitinfolc,
2032 linked_object,
2033 &header_offset,
2034 header_size,
2035 &data_offset,
2036 size);
2037 require_noerr(rval, finish);
2038 }
2039
2040 #if !KERNEL
2041 unswap_macho(my_linked_object, object->host_order, object->target_order);
2042 #endif /* KERNEL */
2043
2044 rval = KERN_SUCCESS;
2045
2046 finish:
2047 return rval;
2048 }
2049
2050 /*******************************************************************************
2051 *******************************************************************************/
2052 static kern_return_t
2053 export_macho_header(const KXLDObject *object, u_char *buf, u_int ncmds,
2054 u_long *header_offset, u_long header_size)
2055 {
2056 kern_return_t rval = KERN_FAILURE;
2057
2058 check(object);
2059 check(buf);
2060 check(header_offset);
2061
2062 KXLD_3264_FUNC(kxld_object_is_32_bit(object), rval,
2063 export_macho_header_32, export_macho_header_64,
2064 object, buf, ncmds, header_offset, header_size);
2065 require_noerr(rval, finish);
2066
2067 rval = KERN_SUCCESS;
2068
2069 finish:
2070 return rval;
2071 }
2072
2073 #if KXLD_USER_OR_ILP32
2074 /*******************************************************************************
2075 *******************************************************************************/
2076 static kern_return_t
2077 export_macho_header_32(const KXLDObject *object, u_char *buf, u_int ncmds,
2078 u_long *header_offset, u_long header_size)
2079 {
2080 kern_return_t rval = KERN_FAILURE;
2081 struct mach_header *mach = NULL;
2082
2083 check(object);
2084 check(buf);
2085 check(header_offset);
2086
2087 require_action(sizeof(*mach) <= header_size - *header_offset, finish,
2088 rval=KERN_FAILURE);
2089 mach = (struct mach_header *) ((void *) (buf + *header_offset));
2090
2091 mach->magic = MH_MAGIC;
2092 mach->cputype = object->cputype;
2093 mach->cpusubtype = object->cpusubtype;
2094 mach->filetype = object->filetype;
2095 mach->ncmds = ncmds;
2096 mach->sizeofcmds = (uint32_t) (header_size - sizeof(*mach));
2097 mach->flags = MH_NOUNDEFS;
2098
2099 *header_offset += sizeof(*mach);
2100
2101 rval = KERN_SUCCESS;
2102
2103 finish:
2104 return rval;
2105 }
2106 #endif /* KXLD_USER_OR_ILP32 */
2107
2108 #if KXLD_USER_OR_LP64
2109 /*******************************************************************************
2110 *******************************************************************************/
2111 static kern_return_t
2112 export_macho_header_64(const KXLDObject *object, u_char *buf, u_int ncmds,
2113 u_long *header_offset, u_long header_size)
2114 {
2115 kern_return_t rval = KERN_FAILURE;
2116 struct mach_header_64 *mach = NULL;
2117
2118 check(object);
2119 check(buf);
2120 check(header_offset);
2121
2122 require_action(sizeof(*mach) <= header_size - *header_offset, finish,
2123 rval=KERN_FAILURE);
2124 mach = (struct mach_header_64 *) ((void *) (buf + *header_offset));
2125
2126 mach->magic = MH_MAGIC_64;
2127 mach->cputype = object->cputype;
2128 mach->cpusubtype = object->cpusubtype;
2129 mach->filetype = object->filetype;
2130 mach->ncmds = ncmds;
2131 mach->sizeofcmds = (uint32_t) (header_size - sizeof(*mach));
2132 mach->flags = MH_NOUNDEFS;
2133
2134 *header_offset += sizeof(*mach);
2135
2136 #if SPLIT_KEXTS_DEBUG
2137 {
2138 kxld_log(kKxldLogLinking, kKxldLogErr,
2139 " %p >>> Start of macho header (size %lu) <%s>",
2140 (void *) mach,
2141 sizeof(*mach),
2142 __func__);
2143 kxld_log(kKxldLogLinking, kKxldLogErr,
2144 " %p <<< End of macho header <%s>",
2145 (void *) ((u_char *)mach + sizeof(*mach)),
2146 __func__);
2147 }
2148 #endif
2149
2150 rval = KERN_SUCCESS;
2151
2152 finish:
2153 return rval;
2154 }
2155 #endif /* KXLD_USER_OR_LP64 */
2156
2157 /*******************************************************************************
2158 *******************************************************************************/
2159 kern_return_t
2160 kxld_object_index_symbols_by_name(KXLDObject *object)
2161 {
2162 return kxld_symtab_index_symbols_by_name(object->symtab);
2163 }
2164
2165 /*******************************************************************************
2166 *******************************************************************************/
2167 kern_return_t
2168 kxld_object_index_cxx_symbols_by_value(KXLDObject *object)
2169 {
2170 return kxld_symtab_index_cxx_symbols_by_value(object->symtab);
2171 }
2172
2173 /*******************************************************************************
2174 *******************************************************************************/
2175 kern_return_t
2176 kxld_object_relocate(KXLDObject *object, kxld_addr_t link_address)
2177 {
2178 kern_return_t rval = KERN_FAILURE;
2179 KXLDSeg *seg = NULL;
2180 u_int i = 0;
2181
2182 check(object);
2183
2184 object->link_addr = link_address;
2185
2186 /* Relocate segments (which relocates the sections) */
2187 for (i = 0; i < object->segs.nitems; ++i) {
2188 seg = kxld_array_get_item(&object->segs, i);
2189 kxld_seg_relocate(seg, link_address);
2190 } // for...
2191
2192 /* Relocate symbols */
2193 rval = kxld_symtab_relocate(object->symtab, &object->sects);
2194 require_noerr(rval, finish);
2195
2196 rval = KERN_SUCCESS;
2197 finish:
2198 return rval;
2199 }
2200
2201 /*******************************************************************************
2202 *******************************************************************************/
2203 static KXLDSym *
2204 get_mutable_sym(const KXLDObject *object, const KXLDSym *sym)
2205 {
2206 KXLDSym *rval = NULL;
2207 kern_return_t result = KERN_FAILURE;
2208 u_int i = 0;
2209
2210 result = kxld_symtab_get_sym_index(object->symtab, sym, &i);
2211 require_noerr(result, finish);
2212
2213 rval = kxld_symtab_get_symbol_by_index(object->symtab, i);
2214 require_action(rval == sym, finish, rval=NULL);
2215
2216 finish:
2217 return rval;
2218 }
2219
2220 /*******************************************************************************
2221 *******************************************************************************/
2222 kern_return_t
2223 kxld_object_resolve_symbol(KXLDObject *object,
2224 const KXLDSym *sym, kxld_addr_t addr)
2225 {
2226 kern_return_t rval = KERN_FAILURE;
2227 KXLDSym *resolved_sym = NULL;
2228
2229 resolved_sym = get_mutable_sym(object, sym);
2230 require_action(resolved_sym, finish, rval=KERN_FAILURE);
2231
2232 rval = kxld_sym_resolve(resolved_sym, addr);
2233 require_noerr(rval, finish);
2234
2235 rval = KERN_SUCCESS;
2236 finish:
2237 return rval;
2238 }
2239
2240 /*******************************************************************************
2241 *******************************************************************************/
2242 kern_return_t
2243 kxld_object_patch_symbol(KXLDObject *object, const struct kxld_sym *sym)
2244 {
2245 kern_return_t rval = KERN_FAILURE;
2246 KXLDSym *patched_sym = NULL;
2247
2248 patched_sym = get_mutable_sym(object, sym);
2249 require_action(patched_sym, finish, rval=KERN_FAILURE);
2250
2251 (void) kxld_sym_patch(patched_sym);
2252 rval = KERN_SUCCESS;
2253 finish:
2254 return rval;
2255 }
2256
2257 /*******************************************************************************
2258 *******************************************************************************/
2259 kern_return_t
2260 kxld_object_add_symbol(KXLDObject *object, char *name, kxld_addr_t link_addr,
2261 const KXLDSym **sym_out)
2262 {
2263 kern_return_t rval = KERN_FAILURE;
2264 KXLDSym *sym = NULL;
2265
2266 rval = kxld_symtab_add_symbol(object->symtab, name, link_addr, &sym);
2267 require_noerr(rval, finish);
2268
2269 *sym_out = sym;
2270 rval = KERN_SUCCESS;
2271 finish:
2272 return rval;
2273 }
2274
2275 /*******************************************************************************
2276 *******************************************************************************/
2277 kern_return_t
2278 kxld_object_process_relocations(KXLDObject *object,
2279 const KXLDDict *patched_vtables)
2280 {
2281 kern_return_t rval = KERN_FAILURE;
2282
2283 (void) kxld_relocator_set_vtables(&object->relocator, patched_vtables);
2284
2285 /* Process relocation entries and populate the global offset table.
2286 *
2287 * For final linked images: the relocation entries are contained in a couple
2288 * of tables hanging off the end of the symbol table. The GOT has its own
2289 * section created by the linker; we simply need to fill it.
2290 *
2291 * For object files: the relocation entries are bound to each section.
2292 * The GOT, if it exists for the target architecture, is created by kxld,
2293 * and we must populate it according to our internal structures.
2294 */
2295 if (object->is_final_image) {
2296 #if KXLD_USER_OR_BUNDLE
2297 rval = process_symbol_pointers(object);
2298 require_noerr(rval, finish);
2299
2300 rval = process_relocs_from_tables(object);
2301 require_noerr(rval, finish);
2302 #else
2303 require_action(FALSE, finish, rval=KERN_FAILURE);
2304 #endif /* KXLD_USER_OR_BUNDLE */
2305 } else {
2306 #if KXLD_USER_OR_GOT
2307 /* Populate GOT */
2308 rval = populate_got(object);
2309 require_noerr(rval, finish);
2310 #endif /* KXLD_USER_OR_GOT */
2311 #if KXLD_USER_OR_OBJECT
2312 rval = process_relocs_from_sections(object);
2313 require_noerr(rval, finish);
2314 #else
2315 require_action(FALSE, finish, rval=KERN_FAILURE);
2316 #endif /* KXLD_USER_OR_OBJECT */
2317 }
2318
2319 /* Populate kmod info structure */
2320 rval = populate_kmod_info(object);
2321 require_noerr(rval, finish);
2322
2323 rval = KERN_SUCCESS;
2324 finish:
2325 return rval;
2326 }
2327
2328 #if KXLD_USER_OR_BUNDLE
2329
2330 #if SPLIT_KEXTS_DEBUG
2331 static boolean_t kxld_show_ptr_value;
2332 #endif
2333
2334 #define SECT_SYM_PTRS "__nl_symbol_ptr"
2335
2336 /*******************************************************************************
2337 * Final linked images create an __nl_symbol_ptr section for the global offset
2338 * table and for symbol pointer lookups in general. Rather than use relocation
2339 * entries, the linker creates an "indirect symbol table" which stores indexes
2340 * into the symbol table corresponding to the entries of this section. This
2341 * function populates the section with the relocated addresses of those symbols.
2342 *******************************************************************************/
2343 static kern_return_t
2344 process_symbol_pointers(KXLDObject *object)
2345 {
2346 kern_return_t rval = KERN_FAILURE;
2347 KXLDSect *sect = NULL;
2348 KXLDSym *sym = NULL;
2349 int32_t *symidx = NULL;
2350 u_char *symptr = NULL;
2351 u_long symptrsize = 0;
2352 u_int nsyms = 0;
2353 u_int firstsym = 0;
2354 u_int i = 0;
2355
2356 check(object);
2357
2358 require_action(object->is_final_image && object->dysymtab_hdr,
2359 finish, rval=KERN_FAILURE);
2360
2361 /* Get the __DATA,__nl_symbol_ptr section. If it doesn't exist, we have
2362 * nothing to do.
2363 */
2364
2365 sect = kxld_object_get_sect_by_name(object, SEG_DATA, SECT_SYM_PTRS);
2366 if (!sect || !(sect->flags & S_NON_LAZY_SYMBOL_POINTERS)) {
2367 rval = KERN_SUCCESS;
2368 goto finish;
2369 }
2370
2371 /* Calculate the table offset and number of entries in the section */
2372
2373 if (kxld_object_is_32_bit(object)) {
2374 symptrsize = sizeof(uint32_t);
2375 } else {
2376 symptrsize = sizeof(uint64_t);
2377 }
2378
2379 nsyms = (u_int) (sect->size / symptrsize);
2380 firstsym = sect->reserved1;
2381
2382 require_action(firstsym + nsyms <= object->dysymtab_hdr->nindirectsyms,
2383 finish, rval=KERN_FAILURE;
2384 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogMalformedMachO
2385 "firstsym + nsyms > object->dysymtab_hdr->nindirectsyms"));
2386
2387 /* Iterate through the indirect symbol table and fill in the section of
2388 * symbol pointers. There are three cases:
2389 * 1) A normal symbol - put its value directly in the table
2390 * 2) An INDIRECT_SYMBOL_LOCAL - symbols that are local and already have
2391 * their offset from the start of the file in the section. Simply
2392 * add the file's link address to fill this entry.
2393 * 3) An INDIRECT_SYMBOL_ABS - prepopulated absolute symbols. No
2394 * action is required.
2395 */
2396
2397 if (isOldInterface) {
2398 symidx = (int32_t *) ((void *) (object->file + object->dysymtab_hdr->indirectsymoff));
2399 }
2400 else {
2401 symidx = (int32_t *) ((void *) (object->split_info.kextExecutable + object->dysymtab_hdr->indirectsymoff));
2402 }
2403
2404 symidx += firstsym;
2405 symptr = sect->data;
2406 for (i = 0; i < nsyms; ++i, ++symidx, symptr+=symptrsize) {
2407 if (*symidx & INDIRECT_SYMBOL_LOCAL) {
2408 if (*symidx & INDIRECT_SYMBOL_ABS) continue;
2409
2410 if (isOldInterface) {
2411 add_to_ptr(symptr, object->link_addr, kxld_object_is_32_bit(object));
2412 }
2413 else {
2414 add_to_ptr(symptr, object->split_info.vmaddr_TEXT, kxld_object_is_32_bit(object));
2415 }
2416 } else {
2417 sym = kxld_symtab_get_symbol_by_index(object->symtab, *symidx);
2418 require_action(sym, finish, rval=KERN_FAILURE);
2419
2420 if (isOldInterface) {
2421 add_to_ptr(symptr, sym->link_addr, kxld_object_is_32_bit(object));
2422 }
2423 else {
2424 add_to_ptr(symptr, object->split_info.vmaddr_TEXT, kxld_object_is_32_bit(object));
2425 }
2426 }
2427 }
2428
2429 rval = KERN_SUCCESS;
2430 finish:
2431 return rval;
2432 }
2433
2434 /*******************************************************************************
2435 *******************************************************************************/
2436 static KXLDSeg *
2437 get_seg_by_base_addr(KXLDObject *object, kxld_addr_t base_addr)
2438 {
2439 KXLDSeg *seg = NULL;
2440 kxld_addr_t start = 0;
2441 kxld_addr_t end = 0;
2442 u_int i = 0;
2443
2444 for (i = 0; i < object->segs.nitems; ++i) {
2445 seg = kxld_array_get_item(&object->segs, i);
2446 start = seg->base_addr;
2447 end = seg->base_addr + seg->vmsize;
2448
2449 if (start <= base_addr && base_addr < end) return seg;
2450 }
2451
2452 return NULL;
2453 }
2454
2455 /*******************************************************************************
2456 *******************************************************************************/
2457 static kern_return_t
2458 process_relocs_from_tables(KXLDObject *object)
2459 {
2460 kern_return_t rval = KERN_FAILURE;
2461 KXLDReloc *reloc = NULL;
2462 KXLDSeg *seg = NULL;
2463 u_int i = 0;
2464
2465 /* Process external relocations */
2466 for (i = 0; i < object->extrelocs.nitems; ++i) {
2467 reloc = kxld_array_get_item(&object->extrelocs, i);
2468
2469 seg = get_seg_by_base_addr(object, reloc->address);
2470 require_action(seg, finish, rval=KERN_FAILURE);
2471
2472 if (isOldInterface) {
2473 rval = kxld_relocator_process_table_reloc(&object->relocator, reloc,
2474 seg, object->link_addr);
2475 }
2476 else {
2477 kxld_addr_t my_link_addr = object->split_info.vmaddr_TEXT;
2478 if (isSplitKext) {
2479 if (kxld_seg_is_text_exec_seg(seg)) {
2480 my_link_addr = object->split_info.vmaddr_TEXT_EXEC;
2481 }
2482 else if (kxld_seg_is_data_seg(seg)) {
2483 my_link_addr = object->split_info.vmaddr_DATA;
2484 }
2485 else if (kxld_seg_is_data_const_seg(seg)) {
2486 my_link_addr = object->split_info.vmaddr_DATA_CONST;
2487 }
2488 else if (kxld_seg_is_llvm_cov_seg(seg)) {
2489 my_link_addr = object->split_info.vmaddr_LLVM_COV;
2490 }
2491 else if (kxld_seg_is_linkedit_seg(seg)) {
2492 my_link_addr = object->split_info.vmaddr_LINKEDIT;
2493 }
2494 }
2495 rval = kxld_relocator_process_table_reloc(&object->relocator,
2496 reloc,
2497 seg,
2498 my_link_addr);
2499 }
2500 require_noerr(rval, finish);
2501 }
2502
2503 /* Process local relocations */
2504 for (i = 0; i < object->locrelocs.nitems; ++i) {
2505 reloc = kxld_array_get_item(&object->locrelocs, i);
2506
2507 seg = get_seg_by_base_addr(object, reloc->address);
2508 require_action(seg, finish, rval=KERN_FAILURE);
2509
2510 if (isOldInterface) {
2511 rval = kxld_relocator_process_table_reloc(&object->relocator, reloc,
2512 seg, object->link_addr);
2513 }
2514 else {
2515 kxld_addr_t my_link_addr = object->split_info.vmaddr_TEXT;
2516 if (isSplitKext) {
2517 if (kxld_seg_is_text_exec_seg(seg)) {
2518 my_link_addr = object->split_info.vmaddr_TEXT_EXEC;
2519 }
2520 else if (kxld_seg_is_data_seg(seg)) {
2521 my_link_addr = object->split_info.vmaddr_DATA;
2522 }
2523 else if (kxld_seg_is_data_const_seg(seg)) {
2524 my_link_addr = object->split_info.vmaddr_DATA_CONST;
2525 }
2526 else if (kxld_seg_is_llvm_cov_seg(seg)) {
2527 my_link_addr = object->split_info.vmaddr_LLVM_COV;
2528 }
2529 else if (kxld_seg_is_linkedit_seg(seg)) {
2530 my_link_addr = object->split_info.vmaddr_LINKEDIT;
2531 }
2532 }
2533 rval = kxld_relocator_process_table_reloc(&object->relocator,
2534 reloc,
2535 seg,
2536 my_link_addr);
2537 }
2538 require_noerr(rval, finish);
2539 }
2540
2541 rval = KERN_SUCCESS;
2542 finish:
2543 return rval;
2544 }
2545
2546 /*******************************************************************************
2547 *******************************************************************************/
2548 static void
2549 add_to_ptr(u_char *symptr, kxld_addr_t val, boolean_t is_32_bit)
2550 {
2551 if (is_32_bit) {
2552 uint32_t *ptr = (uint32_t *) ((void *) symptr);
2553
2554 *ptr += (uint32_t) val;
2555 } else {
2556 uint64_t *ptr = (uint64_t *) ((void *) symptr);
2557
2558 *ptr += (uint64_t) val;
2559 }
2560
2561 #if SPLIT_KEXTS_DEBUG
2562 kxld_show_ptr_value = FALSE;
2563 #endif
2564
2565 }
2566 #endif /* KXLD_USER_OR_BUNDLE */
2567
2568 #if KXLD_USER_OR_OBJECT
2569 /*******************************************************************************
2570 *******************************************************************************/
2571 static kern_return_t
2572 process_relocs_from_sections(KXLDObject *object)
2573 {
2574 kern_return_t rval = KERN_FAILURE;
2575 KXLDSect *sect = NULL;
2576 u_int i = 0;
2577
2578 for (i = 0; i < object->sects.nitems; ++i) {
2579 sect = kxld_array_get_item(&object->sects, i);
2580 rval = kxld_sect_process_relocs(sect, &object->relocator);
2581 require_noerr(rval, finish);
2582 }
2583
2584 rval = KERN_SUCCESS;
2585 finish:
2586 return rval;
2587 }
2588 #endif /* KXLD_USER_OR_OBJECT */
2589
2590 /*******************************************************************************
2591 *******************************************************************************/
2592 static kern_return_t
2593 populate_kmod_info(KXLDObject *object)
2594 {
2595 kern_return_t rval = KERN_FAILURE;
2596 KXLDSect *kmodsect = NULL;
2597 KXLDSym *kmodsym = NULL;
2598 kmod_info_t *kmod_info = NULL;
2599 u_long kmod_offset = 0;
2600 u_long header_size;
2601 u_long size;
2602
2603 if (kxld_object_is_kernel(object)) {
2604 rval = KERN_SUCCESS;
2605 goto finish;
2606 }
2607
2608 kxld_object_get_vmsize(object, &header_size, &size);
2609
2610 kmodsym = kxld_symtab_get_locally_defined_symbol_by_name(object->symtab,
2611 KXLD_KMOD_INFO_SYMBOL);
2612 require_action(kmodsym, finish, rval=KERN_FAILURE;
2613 kxld_log(kKxldLogLinking, kKxldLogErr, kKxldLogNoKmodInfo));
2614
2615 kmodsect = kxld_array_get_item(&object->sects, kmodsym->sectnum);
2616
2617 kmod_offset = (u_long) (kmodsym->base_addr - kmodsect->base_addr);
2618 kmod_info = (kmod_info_t *) ((void *) (kmodsect->data + kmod_offset));
2619
2620 if (kxld_object_is_32_bit(object)) {
2621 kmod_info_32_v1_t *kmod = (kmod_info_32_v1_t *) (kmod_info);
2622
2623 if (isOldInterface) {
2624 kmod->address = (uint32_t) object->link_addr;
2625 }
2626 else {
2627 kmod->address = (uint32_t) object->split_info.vmaddr_TEXT;
2628 }
2629
2630 kmod->size = (uint32_t) size;
2631 kmod->hdr_size = (uint32_t) header_size;
2632
2633 #if !KERNEL
2634 if (kxld_object_target_needs_swap(object)) {
2635 kmod->address = OSSwapInt32(kmod->address);
2636 kmod->size = OSSwapInt32(kmod->size);
2637 kmod->hdr_size = OSSwapInt32(kmod->hdr_size);
2638 }
2639 #endif /* !KERNEL */
2640 } else {
2641 kmod_info_64_v1_t *kmod = (kmod_info_64_v1_t *) (kmod_info);
2642
2643 if (isOldInterface) {
2644 kmod->address = object->link_addr;
2645 }
2646 else {
2647 kmod->address = object->split_info.vmaddr_TEXT;
2648 }
2649
2650 kmod->size = size;
2651 kmod->hdr_size = header_size;
2652
2653 #if !KERNEL
2654 if (kxld_object_target_needs_swap(object)) {
2655 kmod->address = OSSwapInt64(kmod->address);
2656 kmod->size = OSSwapInt64(kmod->size);
2657 kmod->hdr_size = OSSwapInt64(kmod->hdr_size);
2658 }
2659 #endif /* !KERNEL */
2660
2661 #if SPLIT_KEXTS_DEBUG
2662 {
2663 kxld_log(kKxldLogLinking, kKxldLogErr,
2664 " kmodsect %p kmod_info %p = kmodsect->data %p + kmod_offset %lu <%s>",
2665 (void *) kmodsect,
2666 (void *) kmod_info,
2667 (void *) kmodsect->data,
2668 kmod_offset,
2669 __func__);
2670
2671 kxld_log(kKxldLogLinking, kKxldLogErr,
2672 " kmod_info data: address %p size %llu hdr_size %llu start_addr %p stop_addr %p <%s>",
2673 (void *) kmod->address,
2674 kmod->size,
2675 kmod->hdr_size,
2676 (void *) kmod->start_addr,
2677 (void *) kmod->stop_addr,
2678 __func__);
2679 }
2680 #endif
2681
2682 }
2683
2684 rval = KERN_SUCCESS;
2685
2686 finish:
2687 return rval;
2688 }
2689
2690 #if KXLD_PIC_KEXTS
2691 /*******************************************************************************
2692 *******************************************************************************/
2693 static boolean_t
2694 target_supports_slideable_kexts(const KXLDObject *object)
2695 {
2696 check(object);
2697
2698 return (object->cputype != CPU_TYPE_I386 && object->include_kaslr_relocs);
2699 }
2700 #endif /* KXLD_PIC_KEXTS */