Lines Matching +full:os +full:- +full:data +full:- +full:offset
1 //===- yaml2macho - Convert YAML to a Mach object file --------------------===//
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
12 //===----------------------------------------------------------------------===//
40 Error writeMachO(raw_ostream &OS);
43 void writeHeader(raw_ostream &OS);
44 void writeLoadCommands(raw_ostream &OS);
45 Error writeSectionData(raw_ostream &OS);
46 void writeRelocations(raw_ostream &OS);
47 void writeLinkEditData(raw_ostream &OS);
49 void writeBindOpcodes(raw_ostream &OS,
52 void writeRebaseOpcodes(raw_ostream &OS);
53 void writeBasicBindOpcodes(raw_ostream &OS);
54 void writeWeakBindOpcodes(raw_ostream &OS);
55 void writeLazyBindOpcodes(raw_ostream &OS);
56 void writeNameList(raw_ostream &OS);
57 void writeStringTable(raw_ostream &OS);
58 void writeExportTrie(raw_ostream &OS);
59 void writeDynamicSymbolTable(raw_ostream &OS);
60 void writeFunctionStarts(raw_ostream &OS);
61 void writeChainedFixups(raw_ostream &OS);
62 void writeDyldExportsTrie(raw_ostream &OS);
63 void writeDataInCode(raw_ostream &OS);
65 void dumpExportEntry(raw_ostream &OS, MachOYAML::ExportEntry &Entry);
66 void ZeroToOffset(raw_ostream &OS, size_t offset);
73 // Old PPC Object Files didn't have __LINKEDIT segments, the data was just
78 Error MachOWriter::writeMachO(raw_ostream &OS) {
79 fileStart = OS.tell();
80 writeHeader(OS);
81 writeLoadCommands(OS);
82 if (Error Err = writeSectionData(OS))
84 writeRelocations(OS);
86 writeLinkEditData(OS);
90 void MachOWriter::writeHeader(raw_ostream &OS) {
105 OS.write((const char *)&Header, header_size);
115 TempSec.offset = Sec.offset;
126 size_t writeLoadCommandData(MachOYAML::LoadCommand &LC, raw_ostream &OS,
133 raw_ostream &OS,
140 OS.write(reinterpret_cast<const char *>(&(TempSec)),
149 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
156 OS.write(reinterpret_cast<const char *>(&(TempSec)),
163 size_t writePayloadString(MachOYAML::LoadCommand &LC, raw_ostream &OS) {
166 OS.write(LC.Content.c_str(), LC.Content.length());
174 raw_ostream &OS,
176 return writePayloadString(LC, OS);
181 raw_ostream &OS,
183 return writePayloadString(LC, OS);
188 raw_ostream &OS,
190 return writePayloadString(LC, OS);
195 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
196 return writePayloadString(LC, OS);
201 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
202 return writePayloadString(LC, OS);
207 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
208 return writePayloadString(LC, OS);
213 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
214 return writePayloadString(LC, OS);
219 MachOYAML::LoadCommand &LC, raw_ostream &OS, bool IsLittleEndian) {
225 OS.write(reinterpret_cast<const char *>(&tool),
232 void ZeroFillBytes(raw_ostream &OS, size_t Size) {
234 OS.write(reinterpret_cast<char *>(FillData.data()), Size);
237 void Fill(raw_ostream &OS, size_t Size, uint32_t Data) {
238 std::vector<uint32_t> FillData((Size / 4) + 1, Data);
239 OS.write(reinterpret_cast<char *>(FillData.data()), Size);
242 void MachOWriter::ZeroToOffset(raw_ostream &OS, size_t Offset) {
243 auto currOffset = OS.tell() - fileStart;
244 if (currOffset < Offset)
245 ZeroFillBytes(OS, Offset - currOffset);
248 void MachOWriter::writeLoadCommands(raw_ostream &OS) {
251 llvm::MachO::macho_load_command Data = LC.Data;
256 MachO::swapStruct(Data.LCStruct##_data); \
257 OS.write(reinterpret_cast<const char *>(&(Data.LCStruct##_data)), \
261 writeLoadCommandData<MachO::LCStruct>(LC, OS, Obj.IsLittleEndian); \
264 switch (LC.Data.load_command_data.cmd) {
267 MachO::swapStruct(Data.load_command_data);
268 OS.write(reinterpret_cast<const char *>(&(Data.load_command_data)),
272 writeLoadCommandData<MachO::load_command>(LC, OS, Obj.IsLittleEndian);
278 OS.write(reinterpret_cast<const char *>(LC.PayloadBytes.data()),
284 ZeroFillBytes(OS, LC.ZeroPadBytes);
290 auto BytesRemaining = LC.Data.load_command_data.cmdsize - BytesWritten;
292 ZeroFillBytes(OS, BytesRemaining);
297 Error MachOWriter::writeSectionData(raw_ostream &OS) {
300 switch (LC.Data.load_command_data.cmd) {
303 uint64_t segOff = is64Bit ? LC.Data.segment_command_64_data.fileoff
304 : LC.Data.segment_command_data.fileoff;
306 strncmp(&LC.Data.segment_command_data.segname[0], "__LINKEDIT", 16)) {
311 writeLinkEditData(OS);
314 ZeroToOffset(OS, Sec.offset);
315 // Zero Fill any data between the end of the last thing we wrote and the
317 if (OS.tell() - fileStart > Sec.offset && Sec.offset != (uint32_t)0)
321 "wrote too much data somewhere, section offsets in "
324 Sec.sectname, Sec.segname, OS.tell(), fileStart,
325 Sec.offset.value));
338 if (Error Err = EmitFunc(OS, Obj.DWARF))
349 Content.writeAsBinary(OS);
350 ZeroFillBytes(OS, Sec.size - Content.binary_size());
352 // Fill section data with 0xDEADBEEF.
353 Fill(OS, Sec.size, 0xDEADBEEFu);
356 uint64_t segSize = is64Bit ? LC.Data.segment_command_64_data.filesize
357 : LC.Data.segment_command_data.filesize;
358 ZeroToOffset(OS, segOff + segSize);
364 ZeroToOffset(OS, LinkEditOff);
365 if (OS.tell() - fileStart > LinkEditOff || !LinkEditOff)
368 Obj.RawLinkEditSegment->writeAsBinary(OS);
379 assert(!R.is_scattered && "non-scattered relocation expected");
404 void MachOWriter::writeRelocations(raw_ostream &OS) {
406 switch (LC.Data.load_command_data.cmd) {
412 ZeroToOffset(OS, Sec.reloff);
419 OS.write(reinterpret_cast<const char *>(&MRE),
428 raw_ostream &OS, std::vector<MachOYAML::BindOpcode> &BindOpcodes) {
432 OS.write(reinterpret_cast<char *>(&OpByte), 1);
433 for (auto Data : Opcode.ULEBExtraData) {
434 encodeULEB128(Data, OS);
436 for (auto Data : Opcode.SLEBExtraData) {
437 encodeSLEB128(Data, OS);
440 OS.write(Opcode.Symbol.data(), Opcode.Symbol.size());
441 OS.write('\0');
446 void MachOWriter::dumpExportEntry(raw_ostream &OS,
448 encodeULEB128(Entry.TerminalSize, OS);
450 encodeULEB128(Entry.Flags, OS);
452 encodeULEB128(Entry.Other, OS);
453 OS << Entry.ImportName;
454 OS.write('\0');
456 encodeULEB128(Entry.Address, OS);
458 encodeULEB128(Entry.Other, OS);
461 OS.write(static_cast<uint8_t>(Entry.Children.size()));
463 OS << EE.Name;
464 OS.write('\0');
465 encodeULEB128(EE.NodeOffset, OS);
468 dumpExportEntry(OS, EE);
471 void MachOWriter::writeExportTrie(raw_ostream &OS) {
472 dumpExportEntry(OS, Obj.LinkEdit.ExportTrie);
476 void writeNListEntry(MachOYAML::NListEntry &NLE, raw_ostream &OS,
487 OS.write(reinterpret_cast<const char *>(&ListEntry), sizeof(NListType));
490 void MachOWriter::writeLinkEditData(raw_ostream &OS) {
503 switch (LC.Data.load_command_data.cmd) {
505 SymtabCmd = &LC.Data.symtab_command_data;
507 std::make_pair(SymtabCmd->symoff, &MachOWriter::writeNameList));
509 std::make_pair(SymtabCmd->stroff, &MachOWriter::writeStringTable));
512 DyldInfoOnlyCmd = &LC.Data.dyld_info_command_data;
513 WriteQueue.push_back(std::make_pair(DyldInfoOnlyCmd->rebase_off,
515 WriteQueue.push_back(std::make_pair(DyldInfoOnlyCmd->bind_off,
517 WriteQueue.push_back(std::make_pair(DyldInfoOnlyCmd->weak_bind_off,
519 WriteQueue.push_back(std::make_pair(DyldInfoOnlyCmd->lazy_bind_off,
521 WriteQueue.push_back(std::make_pair(DyldInfoOnlyCmd->export_off,
525 DSymtabCmd = &LC.Data.dysymtab_command_data;
527 DSymtabCmd->indirectsymoff, &MachOWriter::writeDynamicSymbolTable));
530 FunctionStartsCmd = &LC.Data.linkedit_data_command_data;
531 WriteQueue.push_back(std::make_pair(FunctionStartsCmd->dataoff,
535 ChainedFixupsCmd = &LC.Data.linkedit_data_command_data;
536 WriteQueue.push_back(std::make_pair(ChainedFixupsCmd->dataoff,
540 DyldExportsTrieCmd = &LC.Data.linkedit_data_command_data;
541 WriteQueue.push_back(std::make_pair(DyldExportsTrieCmd->dataoff,
545 DataInCodeCmd = &LC.Data.linkedit_data_command_data;
546 WriteQueue.push_back(std::make_pair(DataInCodeCmd->dataoff,
555 ZeroToOffset(OS, writeOp.first);
556 (this->*writeOp.second)(OS);
560 void MachOWriter::writeRebaseOpcodes(raw_ostream &OS) {
565 OS.write(reinterpret_cast<char *>(&OpByte), 1);
566 for (auto Data : Opcode.ExtraData)
567 encodeULEB128(Data, OS);
571 void MachOWriter::writeBasicBindOpcodes(raw_ostream &OS) {
572 writeBindOpcodes(OS, Obj.LinkEdit.BindOpcodes);
575 void MachOWriter::writeWeakBindOpcodes(raw_ostream &OS) {
576 writeBindOpcodes(OS, Obj.LinkEdit.WeakBindOpcodes);
579 void MachOWriter::writeLazyBindOpcodes(raw_ostream &OS) {
580 writeBindOpcodes(OS, Obj.LinkEdit.LazyBindOpcodes);
583 void MachOWriter::writeNameList(raw_ostream &OS) {
586 writeNListEntry<MachO::nlist_64>(NLE, OS, Obj.IsLittleEndian);
588 writeNListEntry<MachO::nlist>(NLE, OS, Obj.IsLittleEndian);
592 void MachOWriter::writeStringTable(raw_ostream &OS) {
594 OS.write(Str.data(), Str.size());
595 OS.write('\0');
599 void MachOWriter::writeDynamicSymbolTable(raw_ostream &OS) {
600 for (auto Data : Obj.LinkEdit.IndirectSymbols)
601 OS.write(reinterpret_cast<const char *>(&Data),
605 void MachOWriter::writeFunctionStarts(raw_ostream &OS) {
608 uint64_t Delta = NextAddr - Addr;
609 encodeULEB128(Delta, OS);
613 OS.write('\0');
616 void MachOWriter::writeDataInCode(raw_ostream &OS) {
618 MachO::data_in_code_entry DICE{Entry.Offset, Entry.Length, Entry.Kind};
621 OS.write(reinterpret_cast<const char *>(&DICE),
626 void MachOWriter::writeChainedFixups(raw_ostream &OS) {
628 OS.write(reinterpret_cast<const char *>(Obj.LinkEdit.ChainedFixups.data()),
632 void MachOWriter::writeDyldExportsTrie(raw_ostream &OS) {
633 dumpExportEntry(OS, Obj.LinkEdit.ExportTrie);
641 Error writeMachO(raw_ostream &OS);
644 void writeFatHeader(raw_ostream &OS);
645 void writeFatArchs(raw_ostream &OS);
647 void ZeroToOffset(raw_ostream &OS, size_t offset);
653 Error UniversalWriter::writeMachO(raw_ostream &OS) {
654 fileStart = OS.tell();
657 return Writer.writeMachO(OS);
660 writeFatHeader(OS);
661 writeFatArchs(OS);
670 ZeroToOffset(OS, FatFile.FatArchs[i].offset);
672 if (Error Err = Writer.writeMachO(OS))
675 auto SliceEnd = FatFile.FatArchs[i].offset + FatFile.FatArchs[i].size;
676 ZeroToOffset(OS, SliceEnd);
682 void UniversalWriter::writeFatHeader(raw_ostream &OS) {
689 OS.write(reinterpret_cast<const char *>(&header), sizeof(MachO::fat_header));
697 FatArch.offset = Arch.offset;
704 void writeFatArch(MachOYAML::FatArch &LC, raw_ostream &OS) {}
707 void writeFatArch<MachO::fat_arch>(MachOYAML::FatArch &Arch, raw_ostream &OS) {
711 OS.write(reinterpret_cast<const char *>(&FatArch), sizeof(MachO::fat_arch));
716 raw_ostream &OS) {
721 OS.write(reinterpret_cast<const char *>(&FatArch),
725 void UniversalWriter::writeFatArchs(raw_ostream &OS) {
730 writeFatArch<MachO::fat_arch_64>(Arch, OS);
732 writeFatArch<MachO::fat_arch>(Arch, OS);
736 void UniversalWriter::ZeroToOffset(raw_ostream &OS, size_t Offset) {
737 auto currOffset = OS.tell() - fileStart;
738 if (currOffset < Offset)
739 ZeroFillBytes(OS, Offset - currOffset);