Skip to content

Commit a667178

Browse files
DianaChenigcbot
authored andcommitted
ZEBinary: support Rela format in ZEELFObjectBuilder
1 parent 8e1ed2c commit a667178

File tree

4 files changed

+109
-57
lines changed

4 files changed

+109
-57
lines changed

IGC/AdaptorOCL/OCL/sp/zebin_builder.cpp

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -416,7 +416,7 @@ void ZEBinaryBuilder::addKernelRelocations(
416416
// Take the value directly
417417
if (!relocs.empty())
418418
for (auto reloc : relocs)
419-
mBuilder.addRelocation(reloc.r_offset, reloc.r_symbol, (zebin::R_TYPE_ZEBIN)reloc.r_type, targetId);
419+
mBuilder.addRelRelocation(reloc.r_offset, reloc.r_symbol, (zebin::R_TYPE_ZEBIN)reloc.r_type, targetId);
420420
}
421421

422422
void ZEBinaryBuilder::addKernelExperimentalProperties(const SOpenCLKernelInfo& annotations,
@@ -500,18 +500,18 @@ void ZEBinaryBuilder::addLocalIds(uint32_t simdSize, uint32_t grfSize,
500500
// Calculate correct (pure) size of ELF binary, because debugDataSize taken from pOutput->m_debugDataVISASize
501501
// contains something else.
502502
// If ELF is validated successfully then return a calculated size. Othwerwise, return 0.
503-
size_t ZEBinaryBuilder::calcElfSize(void* elfBin, size_t debugDataSize)
503+
size_t ZEBinaryBuilder::calcElfSize(void* elfBin, size_t elfSize)
504504
{
505505
SElf64Header* elf64Header = (SElf64Header*)elfBin;
506506
size_t elfBinSize = 0; // Correct (pure) size of ELF binary to be calculated
507507

508-
if (debugDataSize == 0)
508+
if (elfSize == 0)
509509
{
510510
IGC_ASSERT_MESSAGE(false, "Empty ELF file - nothing to be transfered to zeBinary");
511511
return 0; // ELF binary incorrect
512512
}
513513

514-
if ((debugDataSize < ID_IDX_NUM_BYTES) ||
514+
if ((elfSize < ID_IDX_NUM_BYTES) ||
515515
(elf64Header->Identity[ID_IDX_MAGIC0] != ELF_MAG0) || (elf64Header->Identity[ID_IDX_MAGIC1] != ELF_MAG1) ||
516516
(elf64Header->Identity[ID_IDX_MAGIC2] != ELF_MAG2) || (elf64Header->Identity[ID_IDX_MAGIC3] != ELF_MAG3) ||
517517
(elf64Header->Identity[ID_IDX_CLASS] != EH_CLASS_64))
@@ -590,22 +590,22 @@ void ZEBinaryBuilder::getElfSymbol(CElfReader* elfReader, const unsigned int sym
590590
}
591591

592592
// Copy every section of ELF file (a buffer in memory) to zeBinary
593-
void ZEBinaryBuilder::addElfSections(void* elfBin, size_t debugDataSize)
593+
void ZEBinaryBuilder::addElfSections(void* elfBin, size_t elfSize)
594594
{
595595
// Correct (pure) size of ELF binary to be calculated
596-
size_t elfBinSize = calcElfSize(elfBin, debugDataSize);
597-
if (!elfBinSize)
596+
size_t pureElfBinSize = calcElfSize(elfBin, elfSize);
597+
if (!pureElfBinSize)
598598
{
599599
return; // ELF file incorrect
600600
}
601601

602602
SElf64Header* elf64Header = (SElf64Header*)elfBin;
603603
size_t entrySize = elf64Header->SectionHeaderEntrySize; // Get the section header entry size
604604

605-
CElfReader* elfReader = CElfReader::Create((char*)elfBin, elfBinSize);
605+
CElfReader* elfReader = CElfReader::Create((char*)elfBin, pureElfBinSize);
606606
RAIIElf ElfObj(elfReader);
607607

608-
if (!elfReader || !elfReader->IsValidElf64(elfBin, elfBinSize))
608+
if (!elfReader || !elfReader->IsValidElf64(elfBin, pureElfBinSize))
609609
{
610610
IGC_ASSERT_MESSAGE(false, "ELF file invalid - nothing to be transfered to zeBinary");
611611
return;
@@ -691,7 +691,7 @@ void ZEBinaryBuilder::addElfSections(void* elfBin, size_t debugDataSize)
691691

692692
mBuilder.addSymbol(zeSym.s_name, zeSym.s_offset, zeSym.s_size, getSymbolElfBinding(zeSym),
693693
getSymbolElfType(zeSym), nonRelaSectionID);
694-
mBuilder.addRelocation(relocEntry.r_offset, zeSym.s_name, R_TYPE_ZEBIN::R_ZE_SYM_ADDR, nonRelaSectionID);
694+
mBuilder.addRelRelocation(relocEntry.r_offset, zeSym.s_name, R_TYPE_ZEBIN::R_ZE_SYM_ADDR, nonRelaSectionID);
695695
}
696696
}
697697
}

IGC/AdaptorOCL/OCL/sp/zebin_builder.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ class ZEBinaryBuilder : DisallowCopy
6262
char*& symName);
6363

6464
/// addElfSections - copy every section of ELF file (a buffer in memory) to zeBinary
65-
void addElfSections(void* elfBin, size_t debugDataSize);
65+
void addElfSections(void* elfBin, size_t elfSize);
6666

6767
/// getBinaryObject - get the final ze object
6868
void getBinaryObject(llvm::raw_pwrite_stream& os);
@@ -106,7 +106,7 @@ class ZEBinaryBuilder : DisallowCopy
106106
void addKernelExperimentalProperties(const IGC::SOpenCLKernelInfo& annotations,
107107
zebin::zeInfoKernel& zeinfoKernel);
108108

109-
/// add symbols of this kernel corresponding to kernek binary
109+
/// add symbols of this kernel corresponding to kernel binary
110110
/// added by addKernelBinary
111111
void addSymbols(
112112
zebin::ZEELFObjectBuilder::SectionID kernelSectId,
@@ -155,7 +155,7 @@ class ZEBinaryBuilder : DisallowCopy
155155

156156
/// Calculate correct (pure) size of ELF binary, because m_debugDataVISASize in kernel output
157157
/// contains something else.
158-
size_t calcElfSize(void* elfBin, size_t debugDataSize);
158+
size_t calcElfSize(void* elfBin, size_t elfSize);
159159

160160
private:
161161
// mBuilder - Builder of a ZE ELF object

IGC/ZEBinWriter/zebin/source/ZEELFObjectBuilder.cpp

Lines changed: 60 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -88,8 +88,8 @@ class ELFWriter {
8888
uint64_t writeSectionData(const uint8_t* data, uint64_t size, uint32_t padding);
8989
// write symbol table section, return section size
9090
uint64_t writeSymTab();
91-
// write relocation table section
92-
uint64_t writeRelocTab(const RelocationListTy& relocs);
91+
// write rel or rela relocation table section
92+
uint64_t writeRelocTab(const RelocationListTy& relocs, bool isRelFormat);
9393
// write ze info section
9494
uint64_t writeZEInfo();
9595
// write string table
@@ -118,13 +118,14 @@ class ELFWriter {
118118
SectionHdrEntry& createNullSectionHdrEntry();
119119

120120
uint32_t getSymTabEntSize();
121-
uint32_t getRelocTabEntSize();
121+
uint32_t getRelocTabEntSize(bool isRelFormat);
122122

123123
// name is the string table index of the symbol name
124124
void writeSymbol(uint32_t name, uint64_t value, uint64_t size,
125125
uint8_t binding, uint8_t type, uint8_t other, uint16_t shndx);
126126

127-
void writeRelocation(uint64_t offset, uint64_t type, uint64_t symIdx);
127+
void writeRelRelocation(uint64_t offset, uint64_t type, uint64_t symIdx);
128+
void writeRelaRelocation(uint64_t offset, uint64_t type, uint64_t symIdx, uint64_t addend);
128129

129130
void writeSecHdrEntry(uint32_t name, uint32_t type, uint64_t flags,
130131
uint64_t address, uint64_t offset,
@@ -171,8 +172,8 @@ ZEELFObjectBuilder::addStandardSection(
171172
// total required padding is (padding + need_padding_for_align)
172173
sections.emplace_back(
173174
ZEELFObjectBuilder::StandardSection(sectName, data, size, type,
174-
(need_padding_for_align + padding), m_sectionId));
175-
++m_sectionId;
175+
(need_padding_for_align + padding), m_sectionIdCount));
176+
++m_sectionIdCount;
176177
return sections.back();
177178
}
178179

@@ -263,8 +264,8 @@ ZEELFObjectBuilder::addSectionZEInfo(zeInfoContainer& zeInfo)
263264
{
264265
// every object should have exactly one ze_info section
265266
IGC_ASSERT(nullptr == m_zeInfoSection);
266-
m_zeInfoSection = new ZEInfoSection(zeInfo, m_sectionId);
267-
++m_sectionId;
267+
m_zeInfoSection = new ZEInfoSection(zeInfo, m_sectionIdCount);
268+
++m_sectionIdCount;
268269
}
269270

270271
void ZEELFObjectBuilder::addSymbol(
@@ -280,40 +281,49 @@ void ZEELFObjectBuilder::addSymbol(
280281
}
281282

282283
ZEELFObjectBuilder::RelocSection&
283-
ZEELFObjectBuilder::getOrCreateRelocSection(SectionID targetSectId)
284+
ZEELFObjectBuilder::getOrCreateRelocSection(SectionID targetSectId, bool isRelFormat)
284285
{
285-
// linear search to see if there's existed reloc section with given target id
286+
// linear search to see if there's existed reloc section with given target id and rel format
286287
// reversly iterate that the latest added might hit first
287288
for (RelocSectionListTy::reverse_iterator it = m_relocSections.rbegin();
288289
it != m_relocSections.rend(); ++it) {
289-
if ((*it).m_TargetID == targetSectId)
290+
if ((*it).m_TargetID == targetSectId && (*it).isRelFormat() == isRelFormat)
290291
return *it;
291292
}
292293
// if not found, create one
293-
// adjust the section name to be .rel.applyTergetName
294-
// If the targt name is empty, we use the defualt name .rel as the section name
294+
// adjust the section name to be .rel.applyTargetName or .rela.applyTargetName
295+
// If the targt name is empty, we use the defualt name .rel/.rela as the section name
295296
// though in our case this should not happen
296297
std::string sectName;
297298
std::string targetName = getSectionNameBySectionID(targetSectId);
298299
if (!targetName.empty())
299-
sectName = m_RelName + targetName;
300+
sectName = (isRelFormat? m_RelName : m_RelaName) + targetName;
300301
else
301-
sectName = m_RelName;
302+
sectName = isRelFormat? m_RelName : m_RelaName;
302303

303-
m_relocSections.emplace_back(m_sectionId, targetSectId, sectName);
304-
++m_sectionId;
304+
m_relocSections.emplace_back(RelocSection(m_sectionIdCount, targetSectId, sectName, isRelFormat));
305+
++m_sectionIdCount;
305306
return m_relocSections.back();
306307
}
307308

308-
void ZEELFObjectBuilder::addRelocation(
309+
void ZEELFObjectBuilder::addRelRelocation(
309310
uint64_t offset, std::string symName, R_TYPE_ZEBIN type, SectionID sectionId)
310311
{
311-
RelocSection& reloc_sect = getOrCreateRelocSection(sectionId);
312+
RelocSection& reloc_sect = getOrCreateRelocSection(sectionId, true);
312313
// create the relocation
313314
reloc_sect.m_Relocations.emplace_back(
314315
ZEELFObjectBuilder::Relocation(offset, symName, type));
315316
}
316317

318+
void ZEELFObjectBuilder::addRelaRelocation(
319+
uint64_t offset, std::string symName, R_TYPE_ZEBIN type, uint64_t addend, SectionID sectionId)
320+
{
321+
RelocSection& reloc_sect = getOrCreateRelocSection(sectionId, false);
322+
// create the relocation
323+
reloc_sect.m_Relocations.emplace_back(
324+
ZEELFObjectBuilder::Relocation(offset, symName, type, addend));
325+
}
326+
317327
uint64_t ZEELFObjectBuilder::finalize(llvm::raw_pwrite_stream& os)
318328
{
319329
ELFWriter w(os, *this);
@@ -387,12 +397,12 @@ uint32_t ELFWriter::getSymTabEntSize()
387397
return sizeof(ELF::Elf32_Sym);
388398
}
389399

390-
uint32_t ELFWriter::getRelocTabEntSize()
400+
uint32_t ELFWriter::getRelocTabEntSize(bool isRelFormat)
391401
{
392402
if (is64Bit())
393-
return sizeof(ELF::Elf64_Rel);
403+
return isRelFormat ? sizeof(ELF::Elf64_Rel) : sizeof(ELF::Elf64_Rela);
394404
else
395-
return sizeof(ELF::Elf32_Rel);
405+
return isRelFormat ? sizeof(ELF::Elf32_Rel) : sizeof(ELF::Elf32_Rela);
396406
}
397407

398408
void ELFWriter::writeSymbol(uint32_t name, uint64_t value, uint64_t size,
@@ -416,7 +426,7 @@ void ELFWriter::writeSymbol(uint32_t name, uint64_t value, uint64_t size,
416426
}
417427
}
418428

419-
void ELFWriter::writeRelocation(uint64_t offset, uint64_t type, uint64_t symIdx)
429+
void ELFWriter::writeRelRelocation(uint64_t offset, uint64_t type, uint64_t symIdx)
420430
{
421431
if (is64Bit()) {
422432
uint64_t info = (symIdx << 32) | (type & 0xffffffffL);
@@ -429,15 +439,30 @@ void ELFWriter::writeRelocation(uint64_t offset, uint64_t type, uint64_t symIdx)
429439
}
430440
}
431441

432-
uint64_t ELFWriter::writeRelocTab(const RelocationListTy& relocs)
442+
void ELFWriter::writeRelaRelocation(uint64_t offset, uint64_t type, uint64_t symIdx, uint64_t addend)
443+
{
444+
writeRelRelocation(offset, type, symIdx);
445+
if (is64Bit()) {
446+
m_W.write(addend);
447+
} else {
448+
m_W.write(uint32_t(addend));
449+
}
450+
}
451+
452+
uint64_t ELFWriter::writeRelocTab(const RelocationListTy& relocs, bool isRelFormat)
433453
{
434454
uint64_t start_off = m_W.OS.tell();
435455

436456
for (const ZEELFObjectBuilder::Relocation& reloc : relocs) {
437457
// the target symbol's name must have been added into symbol table
438458
IGC_ASSERT(m_SymNameIdxMap.find(reloc.symName()) != m_SymNameIdxMap.end());
439-
writeRelocation(
440-
reloc.offset(), reloc.type(), m_SymNameIdxMap[reloc.symName()]);
459+
460+
if (isRelFormat)
461+
writeRelRelocation(
462+
reloc.offset(), reloc.type(), m_SymNameIdxMap[reloc.symName()]);
463+
else
464+
writeRelaRelocation(
465+
reloc.offset(), reloc.type(), m_SymNameIdxMap[reloc.symName()], reloc.addend());
441466
}
442467

443468
return m_W.OS.tell() - start_off;
@@ -576,14 +601,15 @@ void ELFWriter::writeSections()
576601
entry.info = m_ObjBuilder.m_localSymbols.size() + 1;
577602
break;
578603

579-
case ELF::SHT_REL: {
604+
case ELF::SHT_REL:
605+
case ELF::SHT_RELA: {
580606
IGC_ASSERT(nullptr != entry.section);
581607
IGC_ASSERT(entry.section->getKind() == Section::RELOC);
582608
const RelocSection* const relocSec =
583609
static_cast<const RelocSection*>(entry.section);
584610
IGC_ASSERT(nullptr != relocSec);
585-
entry.size = writeRelocTab(relocSec->m_Relocations);
586-
entry.entsize = getRelocTabEntSize();
611+
entry.size = writeRelocTab(relocSec->m_Relocations, relocSec->isRelFormat());
612+
entry.entsize = getRelocTabEntSize(relocSec->isRelFormat());
587613
break;
588614
}
589615
case SHT_ZEBIN_ZEINFO:
@@ -737,7 +763,7 @@ void ELFWriter::createSectionHdrEntries()
737763
// .data
738764
// .symtab
739765
// all other standard sections follow the order of being added (spv, debug)
740-
// .rel
766+
// .rel and .rela
741767
// .ze_info
742768
// .strtab
743769

@@ -774,12 +800,14 @@ void ELFWriter::createSectionHdrEntries()
774800
createSectionHdrEntry(sect.m_sectName, sect.m_type, &sect);
775801
}
776802

777-
// .rel
803+
// .rel and .rela
778804
if (!m_ObjBuilder.m_relocSections.empty()) {
779805
// go through relocation sections
780806
for (RelocSection& sect : m_ObjBuilder.m_relocSections) {
781807
SectionHdrEntry& entry =
782-
createSectionHdrEntry(sect.m_sectName, ELF::SHT_REL, &sect);
808+
sect.isRelFormat() ?
809+
createSectionHdrEntry(sect.m_sectName, ELF::SHT_REL, &sect) :
810+
createSectionHdrEntry(sect.m_sectName, ELF::SHT_RELA, &sect);
783811
// set apply target's section index
784812
// relocations could only apply to standard sections. At this point,
785813
// all standard section's section index should be adjusted

0 commit comments

Comments
 (0)