llvm.org GIT mirror llvm / 045015e
Add support for the new LC_NOTE load command. It describes a region of arbitrary data included in a Mach-O file. Its initial use is to record extra data in MH_CORE files. rdar://30001545 rdar://30001731 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@292500 91177308-0d34-0410-b5e6-96231b3b80d8 Kevin Enderby 2 years ago
11 changed file(s) with 137 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
350350 getLinkerOptionLoadCommand(const LoadCommandInfo &L) const;
351351 MachO::version_min_command
352352 getVersionMinLoadCommand(const LoadCommandInfo &L) const;
353 MachO::note_command
354 getNoteLoadCommand(const LoadCommandInfo &L) const;
353355 MachO::dylib_command
354356 getDylibIDLoadCommand(const LoadCommandInfo &L) const;
355357 MachO::dyld_info_command
7272 HANDLE_LOAD_COMMAND(LC_LINKER_OPTIMIZATION_HINT, 0x0000002Eu, linkedit_data_command)
7373 HANDLE_LOAD_COMMAND(LC_VERSION_MIN_TVOS, 0x0000002Fu, version_min_command)
7474 HANDLE_LOAD_COMMAND(LC_VERSION_MIN_WATCHOS, 0x00000030u, version_min_command)
75 HANDLE_LOAD_COMMAND(LC_NOTE, 0x00000031u, note_command)
7576
7677 #endif
7778
108109 LOAD_COMMAND_STRUCT(twolevel_hints_command)
109110 LOAD_COMMAND_STRUCT(uuid_command)
110111 LOAD_COMMAND_STRUCT(version_min_command)
112 LOAD_COMMAND_STRUCT(note_command)
111113
112114 #endif
113115
818818 uint32_t sdk; // X.Y.Z is encoded in nibbles xxxx.yy.zz
819819 };
820820
821 struct note_command {
822 uint32_t cmd; // LC_NOTE
823 uint32_t cmdsize; // sizeof(struct note_command)
824 char data_owner[16]; // owner name for this LC_NOTE
825 uint64_t offset; // file offset of this data
826 uint64_t size; // length of data region
827 };
828
821829 struct dyld_info_command {
822830 uint32_t cmd;
823831 uint32_t cmdsize;
12631271 sys::swapByteOrder(C.cmdsize);
12641272 sys::swapByteOrder(C.version);
12651273 sys::swapByteOrder(C.sdk);
1274 }
1275
1276 inline void swapStruct(note_command &C) {
1277 sys::swapByteOrder(C.cmd);
1278 sys::swapByteOrder(C.cmdsize);
1279 sys::swapByteOrder(C.offset);
1280 sys::swapByteOrder(C.size);
12661281 }
12671282
12681283 inline void swapStruct(data_in_code_entry &C) {
783783 return Error::success();
784784 }
785785
786 static Error checkNoteCommand(const MachOObjectFile &Obj,
787 const MachOObjectFile::LoadCommandInfo &Load,
788 uint32_t LoadCommandIndex,
789 std::list &Elements) {
790 if (Load.C.cmdsize != sizeof(MachO::note_command))
791 return malformedError("load command " + Twine(LoadCommandIndex) +
792 " LC_NOTE has incorrect cmdsize");
793 MachO::note_command Nt = getStruct(Obj, Load.Ptr);
794 uint64_t FileSize = Obj.getData().size();
795 if (Nt.offset > FileSize)
796 return malformedError("offset field of LC_NOTE command " +
797 Twine(LoadCommandIndex) + " extends "
798 "past the end of the file");
799 uint64_t BigSize = Nt.offset;
800 BigSize += Nt.size;
801 if (BigSize > FileSize)
802 return malformedError("size field plus offset field of LC_NOTE command " +
803 Twine(LoadCommandIndex) + " extends past the end of "
804 "the file");
805 if (Error Err = checkOverlappingElement(Elements, Nt.offset, Nt.size,
806 "LC_NOTE data"))
807 return Err;
808 return Error::success();
809 }
810
786811 static Error checkRpathCommand(const MachOObjectFile &Obj,
787812 const MachOObjectFile::LoadCommandInfo &Load,
788813 uint32_t LoadCommandIndex) {
12781303 } else if (Load.C.cmd == MachO::LC_VERSION_MIN_WATCHOS) {
12791304 if ((Err = checkVersCommand(*this, Load, I, &VersLoadCmd,
12801305 "LC_VERSION_MIN_WATCHOS")))
1306 return;
1307 } else if (Load.C.cmd == MachO::LC_NOTE) {
1308 if ((Err = checkNoteCommand(*this, Load, I, Elements)))
12811309 return;
12821310 } else if (Load.C.cmd == MachO::LC_RPATH) {
12831311 if ((Err = checkRpathCommand(*this, Load, I)))
32883316 return getStruct(*this, L.Ptr);
32893317 }
32903318
3319 MachO::note_command
3320 MachOObjectFile::getNoteLoadCommand(const LoadCommandInfo &L) const {
3321 return getStruct(*this, L.Ptr);
3322 }
3323
32913324 MachO::dylib_command
32923325 MachOObjectFile::getDylibIDLoadCommand(const LoadCommandInfo &L) const {
32933326 return getStruct(*this, L.Ptr);
557557 IO.mapRequired("sdk", LoadCommand.sdk);
558558 }
559559
560 void MappingTraits::mapping(
561 IO &IO, MachO::note_command &LoadCommand) {
562
563 IO.mapRequired("data_owner", LoadCommand.data_owner);
564 IO.mapRequired("offset", LoadCommand.offset);
565 IO.mapRequired("size", LoadCommand.size);
566 }
567
560568 } // namespace llvm::yaml
561569
562570 } // namespace llvm
504504
505505 RUN: not llvm-objdump -macho -universal-headers %p/Inputs/macho-invalid-fat-arch-overlapheaders 2>&1 | FileCheck -check-prefix INVALID-FAT-ARCH-OVERLAPHEADERS %s
506506 INVALID-FAT-ARCH-OVERLAPHEADERS: macho-invalid-fat-arch-overlapheaders': truncated or malformed fat file (cputype (7) cpusubtype (3) offset 12 overlaps universal headers)
507
508 RUN: not llvm-objdump -macho -private-headers %p/Inputs/macho-invalid-note 2>&1 | FileCheck -check-prefix INVALID-NOTE-COMMAND %s
509 INVALID-NOTE-COMMAND: macho-invalid-note': truncated or malformed object (size field plus offset field of LC_NOTE command 0 extends past the end of the file)
0 # RUN: yaml2obj %s | obj2yaml | FileCheck %s
1
2 --- !mach-o
3 FileHeader:
4 magic: 0xFEEDFACE
5 cputype: 0x00000007
6 cpusubtype: 0x00000003
7 filetype: 0x00000004
8 ncmds: 2
9 sizeofcmds: 192
10 flags: 0x00000000
11 LoadCommands:
12 - cmd: LC_SEGMENT_64
13 cmdsize: 152
14 segname: __TEXT
15 vmaddr: 4294967296
16 vmsize: 8192
17 fileoff: 0
18 filesize: 3099
19 maxprot: 7
20 initprot: 5
21 nsects: 1
22 flags: 0
23 Sections:
24 - sectname: __text
25 segname: __TEXT
26 addr: 0x0000000100001160
27 size: 3099
28 offset: 0x00001160
29 align: 4
30 reloff: 0x00000000
31 nreloc: 0
32 flags: 0x80000400
33 reserved1: 0x00000000
34 reserved2: 0x00000000
35 reserved3: 0x00000000
36 - cmd: LC_NOTE
37 cmdsize: 40
38 data_owner: DATA OWNER
39 offset: 220
40 size: 8
41 ...
42
43
44 #CHECK: LoadCommands:
45 #CHECK: - cmd: LC_NOTE
46 #CHECK_NEXT: cmdsize: 40
47 #CHECK_NEXT: data_owner: DATA OWNER
48 #CHECK_NEXT: offset: 220
49 #CHECK_NEXT: size: 8
2222 // RUN: | FileCheck %s -check-prefix=NON_VERBOSE
2323 // RUN: llvm-objdump -p %p/Inputs/codesig.macho-x86_64 \
2424 // RUN: | FileCheck %s -check-prefix=CODESIG
25 // RUN: llvm-objdump -p %p/Inputs/note.macho-x86 \
26 // RUN: | FileCheck %s -check-prefix=NOTE
2527
2628 CHECK: Mach header
2729 CHECK: magic cputype cpusubtype caps filetype ncmds sizeofcmds flags
543545 CODESIG: cmdsize 16
544546 CODESIG: dataoff 8496
545547 CODESIG: datasize 64
548
549 NOTE: cmd LC_NOTE
550 NOTE: cmdsize 40
551 NOTE: data_owner DATA OWNER
552 NOTE: offset 68
553 NOTE: size 8
81668166 if (Update != 0)
81678167 outs() << "." << Update;
81688168 outs() << "\n";
8169 }
8170
8171 static void PrintNoteLoadCommand(MachO::note_command Nt) {
8172 outs() << " cmd LC_NOTE\n";
8173 outs() << " cmdsize " << Nt.cmdsize;
8174 if (Nt.cmdsize != sizeof(struct MachO::note_command))
8175 outs() << " Incorrect size\n";
8176 else
8177 outs() << "\n";
8178 const char *d = Nt.data_owner;
8179 outs() << "data_owner " << format("%.16s\n", d);
8180 outs() << " offset " << Nt.offset << "\n";
8181 outs() << " size " << Nt.size << "\n";
81698182 }
81708183
81718184 static void PrintSourceVersionCommand(MachO::source_version_command sd) {
90139026 Command.C.cmd == MachO::LC_VERSION_MIN_WATCHOS) {
90149027 MachO::version_min_command Vd = Obj->getVersionMinLoadCommand(Command);
90159028 PrintVersionMinLoadCommand(Vd);
9029 } else if (Command.C.cmd == MachO::LC_NOTE) {
9030 MachO::note_command Nt = Obj->getNoteLoadCommand(Command);
9031 PrintNoteLoadCommand(Nt);
90169032 } else if (Command.C.cmd == MachO::LC_SOURCE_VERSION) {
90179033 MachO::source_version_command Sd = Obj->getSourceVersionCommand(Command);
90189034 PrintSourceVersionCommand(Sd);