mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-06-19 03:24:09 +00:00
MC: Switch to using explicit MCAlignFragments with OnlyAlignAddress bit instead
of manually doing padding/editing layout in LayoutSection(). - This probably seems like six-of-one and half-dozen of another, but there is a method to my madness. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@103693 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
@ -442,7 +442,7 @@ void MCAssembler::LayoutSection(MCAsmLayout &Layout,
|
|||||||
|
|
||||||
++stats::SectionLayouts;
|
++stats::SectionLayouts;
|
||||||
|
|
||||||
// Get the section start address.
|
// Compute the section start address.
|
||||||
uint64_t StartAddress = 0;
|
uint64_t StartAddress = 0;
|
||||||
if (SectionOrderIndex) {
|
if (SectionOrderIndex) {
|
||||||
MCSectionData *Prev = Layout.getSectionOrder()[SectionOrderIndex - 1];
|
MCSectionData *Prev = Layout.getSectionOrder()[SectionOrderIndex - 1];
|
||||||
@ -450,22 +450,10 @@ void MCAssembler::LayoutSection(MCAsmLayout &Layout,
|
|||||||
Layout.getSectionAddressSize(Prev));
|
Layout.getSectionAddressSize(Prev));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Align this section if necessary by adding padding bytes to the previous
|
// Honor the section alignment requirements.
|
||||||
// section. It is safe to adjust this out-of-band, because no symbol or
|
StartAddress = RoundUpToAlignment(StartAddress, SD.getAlignment());
|
||||||
// fragment is allowed to point past the end of the section at any time.
|
|
||||||
if (uint64_t Pad = OffsetToAlignment(StartAddress, SD.getAlignment())) {
|
|
||||||
// Unless this section is virtual (where we are allowed to adjust the offset
|
|
||||||
// freely), the padding goes in the previous section.
|
|
||||||
if (!IsVirtual) {
|
|
||||||
assert(SectionOrderIndex && "Invalid initial section address!");
|
|
||||||
MCSectionData *Prev = Layout.getSectionOrder()[SectionOrderIndex - 1];
|
|
||||||
Layout.setSectionFileSize(Prev, Layout.getSectionFileSize(Prev) + Pad);
|
|
||||||
}
|
|
||||||
|
|
||||||
StartAddress += Pad;
|
// Set the section address.
|
||||||
}
|
|
||||||
|
|
||||||
// Set the aligned section address.
|
|
||||||
Layout.setSectionAddress(&SD, StartAddress);
|
Layout.setSectionAddress(&SD, StartAddress);
|
||||||
|
|
||||||
for (MCSectionData::iterator it = SD.begin(), ie = SD.end(); it != ie; ++it)
|
for (MCSectionData::iterator it = SD.begin(), ie = SD.end(); it != ie; ++it)
|
||||||
@ -587,7 +575,6 @@ static void WriteFragmentData(const MCAssembler &Asm, const MCAsmLayout &Layout,
|
|||||||
void MCAssembler::WriteSectionData(const MCSectionData *SD,
|
void MCAssembler::WriteSectionData(const MCSectionData *SD,
|
||||||
const MCAsmLayout &Layout,
|
const MCAsmLayout &Layout,
|
||||||
MCObjectWriter *OW) const {
|
MCObjectWriter *OW) const {
|
||||||
uint64_t SectionSize = Layout.getSectionSize(SD);
|
|
||||||
uint64_t SectionFileSize = Layout.getSectionFileSize(SD);
|
uint64_t SectionFileSize = Layout.getSectionFileSize(SD);
|
||||||
|
|
||||||
// Ignore virtual sections.
|
// Ignore virtual sections.
|
||||||
@ -621,10 +608,6 @@ void MCAssembler::WriteSectionData(const MCSectionData *SD,
|
|||||||
ie = SD->end(); it != ie; ++it)
|
ie = SD->end(); it != ie; ++it)
|
||||||
WriteFragmentData(*this, Layout, *it, OW);
|
WriteFragmentData(*this, Layout, *it, OW);
|
||||||
|
|
||||||
// Add section padding.
|
|
||||||
assert(SectionFileSize >= SectionSize && "Invalid section sizes!");
|
|
||||||
OW->WriteZeros(SectionFileSize - SectionSize);
|
|
||||||
|
|
||||||
assert(OW->getStream().tell() - Start == SectionFileSize);
|
assert(OW->getStream().tell() - Start == SectionFileSize);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -645,8 +628,34 @@ void MCAssembler::Finish() {
|
|||||||
it2->setOrdinal(FragmentIndex++);
|
it2->setOrdinal(FragmentIndex++);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Layout until everything fits.
|
// Create the layout object.
|
||||||
MCAsmLayout Layout(*this);
|
MCAsmLayout Layout(*this);
|
||||||
|
|
||||||
|
// Insert additional align fragments for concrete sections to explicitly pad
|
||||||
|
// the previous section to match their alignment requirements. This is for
|
||||||
|
// 'gas' compatibility, it shouldn't strictly be necessary.
|
||||||
|
//
|
||||||
|
// FIXME: This may be Mach-O specific.
|
||||||
|
for (unsigned i = 1, e = Layout.getSectionOrder().size(); i < e; ++i) {
|
||||||
|
MCSectionData *SD = Layout.getSectionOrder()[i];
|
||||||
|
|
||||||
|
// Ignore sections without alignment requirements.
|
||||||
|
unsigned Align = SD->getAlignment();
|
||||||
|
if (Align <= 1)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// Ignore virtual sections, they don't cause file size modifications.
|
||||||
|
if (getBackend().isVirtualSection(SD->getSection()))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
// Otherwise, create a new align fragment at the end of the previous
|
||||||
|
// section.
|
||||||
|
MCAlignFragment *AF = new MCAlignFragment(Align, 0, 1, Align,
|
||||||
|
Layout.getSectionOrder()[i - 1]);
|
||||||
|
AF->setOnlyAlignAddress(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Layout until everything fits.
|
||||||
while (LayoutOnce(Layout))
|
while (LayoutOnce(Layout))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user