================
@@ -204,59 +232,108 @@ OffloadBinary::create(MemoryBufferRef Buf) {
new OffloadBinary(Buf, TheHeader, TheEntry));
}
-SmallString<0> OffloadBinary::write(const OffloadingImage &OffloadingData) {
+Expected<std::unique_ptr<OffloadBinary>>
+OffloadBinary::createV2(MemoryBufferRef Buf) {
+ auto HeaderOrErr = extractHeader(Buf);
+ if (!HeaderOrErr)
+ return HeaderOrErr.takeError();
+ const Header *TheHeader = *HeaderOrErr;
+
+ const char *Start = Buf.getBufferStart();
+
+ const Entry *Entries =
+ reinterpret_cast<const Entry *>(&Start[TheHeader->EntriesOffset]);
+ for (uint32_t I = 0; I < TheHeader->EntriesCount; ++I) {
+ const Entry *TheEntry = &Entries[I];
+
+ if (TheEntry->ImageOffset > Buf.getBufferSize() ||
+ TheEntry->StringOffset > Buf.getBufferSize())
+ return errorCodeToError(object_error::unexpected_eof);
+ }
+
+ return std::unique_ptr<OffloadBinary>(
+ new OffloadBinary(Buf, TheHeader, Entries));
+}
+
+SmallString<0> OffloadBinary::write(ArrayRef<OffloadingImage> OffloadingData) {
+ uint64_t EntriesCount = OffloadingData.size();
+ assert(EntriesCount > 0 && "At least one offloading image is required");
+
// Create a null-terminated string table with all the used strings.
+ // Also calculate total size of images.
StringTableBuilder StrTab(StringTableBuilder::ELF);
- for (auto &KeyAndValue : OffloadingData.StringData) {
- StrTab.add(KeyAndValue.first);
- StrTab.add(KeyAndValue.second);
+ uint64_t TotalStringEntries = 0;
+ uint64_t TotalImagesSize = 0;
+ for (const OffloadingImage &Img : OffloadingData) {
+ for (auto &KeyAndValue : Img.StringData) {
+ StrTab.add(KeyAndValue.first);
+ StrTab.add(KeyAndValue.second);
+ }
+ TotalStringEntries += Img.StringData.size();
+ TotalImagesSize += Img.Image->getBufferSize();
}
StrTab.finalize();
- uint64_t StringEntrySize =
- sizeof(StringEntry) * OffloadingData.StringData.size();
+ uint64_t StringEntrySize = sizeof(StringEntry) * TotalStringEntries;
+ uint64_t EntriesSize = sizeof(Entry) * EntriesCount;
+ uint64_t StrTabOffset = sizeof(Header) + EntriesSize + StringEntrySize;
// Make sure the image we're wrapping around is aligned as well.
- uint64_t BinaryDataSize = alignTo(sizeof(Header) + sizeof(Entry) +
- StringEntrySize + StrTab.getSize(),
- getAlignment());
+ uint64_t BinaryDataSize =
+ alignTo(StrTabOffset + StrTab.getSize(), getAlignment());
- // Create the header and fill in the offsets. The entry will be directly
+ // Create the header and fill in the offsets. The entries will be directly
// placed after the header in memory. Align the size to the alignment of the
// header so this can be placed contiguously in a single section.
Header TheHeader;
- TheHeader.Size = alignTo(
- BinaryDataSize + OffloadingData.Image->getBufferSize(), getAlignment());
- TheHeader.EntryOffset = sizeof(Header);
- TheHeader.EntrySize = sizeof(Entry);
-
- // Create the entry using the string table offsets. The string table will be
- // placed directly after the entry in memory, and the image after that.
- Entry TheEntry;
- TheEntry.TheImageKind = OffloadingData.TheImageKind;
- TheEntry.TheOffloadKind = OffloadingData.TheOffloadKind;
- TheEntry.Flags = OffloadingData.Flags;
- TheEntry.StringOffset = sizeof(Header) + sizeof(Entry);
- TheEntry.NumStrings = OffloadingData.StringData.size();
-
- TheEntry.ImageOffset = BinaryDataSize;
- TheEntry.ImageSize = OffloadingData.Image->getBufferSize();
+ TheHeader.Size = alignTo(BinaryDataSize + TotalImagesSize, getAlignment());
+ TheHeader.EntriesOffset = sizeof(Header);
+ TheHeader.EntriesCount = EntriesCount;
SmallString<0> Data;
Data.reserve(TheHeader.Size);
raw_svector_ostream OS(Data);
OS << StringRef(reinterpret_cast<char *>(&TheHeader), sizeof(Header));
- OS << StringRef(reinterpret_cast<char *>(&TheEntry), sizeof(Entry));
- for (auto &KeyAndValue : OffloadingData.StringData) {
- uint64_t Offset = sizeof(Header) + sizeof(Entry) + StringEntrySize;
- StringEntry Map{Offset + StrTab.getOffset(KeyAndValue.first),
- Offset + StrTab.getOffset(KeyAndValue.second)};
- OS << StringRef(reinterpret_cast<char *>(&Map), sizeof(StringEntry));
+
+ // Create the entries using the string table offsets. The string table will
be
+ // placed directly after the set of entries in memory, and all the images are
+ // after that.
+ uint64_t StringEntryOffset = sizeof(Header) + EntriesSize;
----------------
jhuber6 wrote:
Right, forgot about the change to the size of the string. I guess it's fine
because the same information is present in either version so the parsing
functions should be compatible. If it's version 1 we use strlen, if it's
version 2 we use the given size, I think that's the only change needed. I was
just a little confused because it seemed like the placement of the string data
changed here
https://github.com/llvm/llvm-project/pull/169425
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits