diff --git a/include/llvm/MC/MCAsmLayout.h b/include/llvm/MC/MCAsmLayout.h index bfd177d995b..c4492a62993 100644 --- a/include/llvm/MC/MCAsmLayout.h +++ b/include/llvm/MC/MCAsmLayout.h @@ -50,11 +50,12 @@ public: /// @name Section Access (in layout order) /// @{ - iterator begin() { return SectionOrder.begin(); } - const_iterator begin() const { return SectionOrder.begin(); } - - iterator end() {return SectionOrder.end();} - const_iterator end() const {return SectionOrder.end();} + llvm::SmallVectorImpl &getSectionOrder() { + return SectionOrder; + } + const llvm::SmallVectorImpl &getSectionOrder() const { + return SectionOrder; + } /// @} /// @name Fragment Layout Data diff --git a/include/llvm/MC/MCAssembler.h b/include/llvm/MC/MCAssembler.h index 08500f8d7aa..c34c9519cd0 100644 --- a/include/llvm/MC/MCAssembler.h +++ b/include/llvm/MC/MCAssembler.h @@ -668,14 +668,10 @@ private: bool FragmentNeedsRelaxation(const MCInstFragment *IF, const MCAsmLayout &Layout) const; - /// LayoutSection - Assign the section the given \arg StartAddress, and then - /// assign offsets and sizes to the fragments in the section \arg SD, and - /// update the section size. - /// - /// \return The address at the end of the section, for use in laying out the - /// succeeding section. - uint64_t LayoutSection(MCSectionData &SD, MCAsmLayout &Layout, - uint64_t StartAddress); + /// LayoutSection - Performs layout of the section referenced by the given + /// \arg SectionOrderIndex. The layout assumes that the previous section has + /// already been layed out correctly. + void LayoutSection(MCAsmLayout &Layout, unsigned SectionOrderIndex); /// LayoutOnce - Perform one layout iteration and return true if any offsets /// were adjusted. diff --git a/lib/MC/MCAssembler.cpp b/lib/MC/MCAssembler.cpp index 60349e69aa2..aefe2c42946 100644 --- a/lib/MC/MCAssembler.cpp +++ b/lib/MC/MCAssembler.cpp @@ -68,12 +68,9 @@ void MCAsmLayout::UpdateForSlide(MCFragment *F, int SlideAmount) { // // FIXME-PERF: This is O(N^2), but will be eliminated once we get smarter. - // Layout the concrete sections and fragments. - uint64_t Address = 0; - for (iterator it = begin(), ie = end(); it != ie; ++it) { - // Layout the section fragments and its size. - Address = getAssembler().LayoutSection(**it, *this, Address); - } + // Layout the sections in order. + for (unsigned i = 0, e = getSectionOrder().size(); i != e; ++i) + getAssembler().LayoutSection(*this, i); } uint64_t MCAsmLayout::getFragmentAddress(const MCFragment *F) const { @@ -365,13 +362,20 @@ bool MCAssembler::EvaluateFixup(const MCAsmLayout &Layout, return IsResolved; } -uint64_t MCAssembler::LayoutSection(MCSectionData &SD, - MCAsmLayout &Layout, - uint64_t StartAddress) { +void MCAssembler::LayoutSection(MCAsmLayout &Layout, + unsigned SectionOrderIndex) { + MCSectionData &SD = *Layout.getSectionOrder()[SectionOrderIndex]; bool IsVirtual = getBackend().isVirtualSection(SD.getSection()); ++stats::SectionLayouts; + // Get the section start address. + uint64_t StartAddress = 0; + if (SectionOrderIndex) { + MCSectionData *Prev = Layout.getSectionOrder()[SectionOrderIndex - 1]; + StartAddress = Layout.getSectionAddress(Prev) + Layout.getSectionSize(Prev); + } + // Align this section if necessary by adding padding bytes to the previous // section. It is safe to adjust this out-of-band, because no symbol or // fragment is allowed to point past the end of the section at any time. @@ -469,8 +473,6 @@ uint64_t MCAssembler::LayoutSection(MCSectionData &SD, Layout.setSectionFileSize(&SD, 0); else Layout.setSectionFileSize(&SD, Address - StartAddress); - - return Address; } /// WriteFragmentData - Write the \arg F data to the output file. @@ -705,13 +707,9 @@ bool MCAssembler::FragmentNeedsRelaxation(const MCInstFragment *IF, bool MCAssembler::LayoutOnce(MCAsmLayout &Layout) { ++stats::RelaxationSteps; - // Layout the concrete sections and fragments. - uint64_t Address = 0; - for (MCAsmLayout::iterator it = Layout.begin(), - ie = Layout.end(); it != ie; ++it) { - // Layout the section fragments and its size. - Address = LayoutSection(**it, Layout, Address); - } + // Layout the sections in order. + for (unsigned i = 0, e = Layout.getSectionOrder().size(); i != e; ++i) + LayoutSection(Layout, i); // Scan for fragments that need relaxation. bool WasRelaxed = false;