<div dir="ltr"><br><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Oct 15, 2015 at 3:27 PM, Rui Ueyama via llvm-commits <span dir="ltr"><<a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: ruiu<br>
Date: Thu Oct 15 17:27:29 2015<br>
New Revision: 250466<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=250466&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=250466&view=rev</a><br>
Log:<br>
ELF2: Use ELFT to template OutputSections.<br>
<br>
This patch is to use ELFT instead of Is64Bits to template OutputSection<br>
and its subclasses. This increases code size slightly because it creates<br>
two identical functions for some classes, but that's only 20 KB out of<br>
33 MB, so it's negligible.<br></blockquote><div><br></div><div>Are you doing this for the convenience of the users? (so they can specify ELFT instead of having to extract the 64bit-ness from it?) If so, you could keep the code size down by using an alias template, perhaps?<br><br>template<typename T><br>using OutputSectionBase = OutputSectionBaseRealThing<T::is64Bits>;</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<br>
This is as per discussion with Rafael. He's not fan of the idea but OK<br>
with this. We'll revisit later to this topic.<br>
<br>
Modified:<br>
    lld/trunk/ELF/InputSection.h<br>
    lld/trunk/ELF/OutputSections.cpp<br>
    lld/trunk/ELF/OutputSections.h<br>
    lld/trunk/ELF/SymbolTable.cpp<br>
    lld/trunk/ELF/SymbolTable.h<br>
    lld/trunk/ELF/Symbols.h<br>
    lld/trunk/ELF/Writer.cpp<br>
<br>
Modified: lld/trunk/ELF/InputSection.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/InputSection.h?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/InputSection.h?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/InputSection.h (original)<br>
+++ lld/trunk/ELF/InputSection.h Thu Oct 15 17:27:29 2015<br>
@@ -18,7 +18,7 @@ namespace elf2 {<br>
<br>
 template <class ELFT> class ObjectFile;<br>
 template <class ELFT> class OutputSection;<br>
-template <bool Is64Bits> class OutputSectionBase;<br>
+template <class ELFT> class OutputSectionBase;<br>
<br>
 // This corresponds to a section of an input file.<br>
 template <class ELFT> class InputSection {<br>
@@ -55,7 +55,7 @@ public:<br>
   // The offset from beginning of the output sections this section was assigned<br>
   // to. The writer sets a value.<br>
   uint64_t OutSecOff = 0;<br>
-  OutputSectionBase<ELFT::Is64Bits> *OutSec = nullptr;<br>
+  OutputSectionBase<ELFT> *OutSec = nullptr;<br>
<br>
   static InputSection<ELFT> Discarded;<br>
<br>
<br>
Modified: lld/trunk/ELF/OutputSections.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.cpp?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.cpp?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/OutputSections.cpp (original)<br>
+++ lld/trunk/ELF/OutputSections.cpp Thu Oct 15 17:27:29 2015<br>
@@ -20,20 +20,19 @@ using namespace llvm::ELF;<br>
 using namespace lld;<br>
 using namespace lld::elf2;<br>
<br>
-template <bool Is64Bits><br>
-OutputSectionBase<Is64Bits>::OutputSectionBase(StringRef Name, uint32_t sh_type,<br>
-                                               uintX_t sh_flags)<br>
+template <class ELFT><br>
+OutputSectionBase<ELFT>::OutputSectionBase(StringRef Name, uint32_t sh_type,<br>
+                                           uintX_t sh_flags)<br>
     : Name(Name) {<br>
-  memset(&Header, 0, sizeof(HeaderT));<br>
+  memset(&Header, 0, sizeof(Elf_Shdr));<br>
   Header.sh_type = sh_type;<br>
   Header.sh_flags = sh_flags;<br>
 }<br>
<br>
 template <class ELFT><br>
 GotSection<ELFT>::GotSection()<br>
-    : OutputSectionBase<ELFT::Is64Bits>(".got", llvm::ELF::SHT_PROGBITS,<br>
-                                        llvm::ELF::SHF_ALLOC |<br>
-                                            llvm::ELF::SHF_WRITE) {<br>
+    : OutputSectionBase<ELFT>(".got", llvm::ELF::SHT_PROGBITS,<br>
+                              llvm::ELF::SHF_ALLOC | llvm::ELF::SHF_WRITE) {<br>
   this->Header.sh_addralign = sizeof(uintX_t);<br>
 }<br>
<br>
@@ -61,9 +60,8 @@ template <class ELFT> void GotSection<EL<br>
<br>
 template <class ELFT><br>
 PltSection<ELFT>::PltSection()<br>
-    : OutputSectionBase<ELFT::Is64Bits>(".plt", llvm::ELF::SHT_PROGBITS,<br>
-                                        llvm::ELF::SHF_ALLOC |<br>
-                                            llvm::ELF::SHF_EXECINSTR) {<br>
+    : OutputSectionBase<ELFT>(".plt", llvm::ELF::SHT_PROGBITS,<br>
+                              llvm::ELF::SHF_ALLOC | llvm::ELF::SHF_EXECINSTR) {<br>
   this->Header.sh_addralign = 16;<br>
 }<br>
<br>
@@ -95,10 +93,9 @@ void PltSection<ELFT>::finalize() {<br>
<br>
 template <class ELFT><br>
 RelocationSection<ELFT>::RelocationSection(bool IsRela)<br>
-    : OutputSectionBase<ELFT::Is64Bits>(IsRela ? ".rela.dyn" : ".rel.dyn",<br>
-                                        IsRela ? llvm::ELF::SHT_RELA<br>
-                                               : llvm::ELF::SHT_REL,<br>
-                                        llvm::ELF::SHF_ALLOC),<br>
+    : OutputSectionBase<ELFT>(IsRela ? ".rela.dyn" : ".rel.dyn",<br>
+                              IsRela ? llvm::ELF::SHT_RELA : llvm::ELF::SHT_REL,<br>
+                              llvm::ELF::SHF_ALLOC),<br>
       IsRela(IsRela) {<br>
   this->Header.sh_entsize = IsRela ? sizeof(Elf_Rela) : sizeof(Elf_Rel);<br>
   this->Header.sh_addralign = ELFT::Is64Bits ? 8 : 4;<br>
@@ -158,38 +155,27 @@ template <class ELFT> void RelocationSec<br>
   this->Header.sh_size = Relocs.size() * this->Header.sh_entsize;<br>
 }<br>
<br>
-template <bool Is64Bits><br>
-InterpSection<Is64Bits>::InterpSection()<br>
-    : OutputSectionBase<Is64Bits>(".interp", llvm::ELF::SHT_PROGBITS,<br>
-                                  llvm::ELF::SHF_ALLOC) {<br>
+template <class ELFT><br>
+InterpSection<ELFT>::InterpSection()<br>
+    : OutputSectionBase<ELFT>(".interp", llvm::ELF::SHT_PROGBITS,<br>
+                              llvm::ELF::SHF_ALLOC) {<br>
   this->Header.sh_size = Config->DynamicLinker.size() + 1;<br>
   this->Header.sh_addralign = 1;<br>
 }<br>
<br>
-template <bool Is64Bits><br>
-template <endianness E><br>
-void OutputSectionBase<Is64Bits>::writeHeaderTo(<br>
-    typename ELFFile<ELFType<E, Is64Bits>>::Elf_Shdr *SHdr) {<br>
-  SHdr->sh_name = Header.sh_name;<br>
-  SHdr->sh_type = Header.sh_type;<br>
-  SHdr->sh_flags = Header.sh_flags;<br>
-  SHdr->sh_addr = Header.sh_addr;<br>
-  SHdr->sh_offset = Header.sh_offset;<br>
-  SHdr->sh_size = Header.sh_size;<br>
-  SHdr->sh_link = Header.sh_link;<br>
-  SHdr->sh_info = Header.sh_info;<br>
-  SHdr->sh_addralign = Header.sh_addralign;<br>
-  SHdr->sh_entsize = Header.sh_entsize;<br>
+template <class ELFT><br>
+void OutputSectionBase<ELFT>::writeHeaderTo(Elf_Shdr *SHdr) {<br>
+  *SHdr = Header;<br>
 }<br>
<br>
-template <bool Is64Bits> void InterpSection<Is64Bits>::writeTo(uint8_t *Buf) {<br>
+template <class ELFT> void InterpSection<ELFT>::writeTo(uint8_t *Buf) {<br>
   memcpy(Buf, Config->DynamicLinker.data(), Config->DynamicLinker.size());<br>
 }<br>
<br>
 template <class ELFT><br>
 HashTableSection<ELFT>::HashTableSection()<br>
-    : OutputSectionBase<ELFT::Is64Bits>(".hash", llvm::ELF::SHT_HASH,<br>
-                                        llvm::ELF::SHF_ALLOC) {<br>
+    : OutputSectionBase<ELFT>(".hash", llvm::ELF::SHT_HASH,<br>
+                              llvm::ELF::SHF_ALLOC) {<br>
   this->Header.sh_entsize = sizeof(Elf_Word);<br>
   this->Header.sh_addralign = sizeof(Elf_Word);<br>
 }<br>
@@ -245,11 +231,10 @@ template <class ELFT> void HashTableSect<br>
<br>
 template <class ELFT><br>
 DynamicSection<ELFT>::DynamicSection(SymbolTable<ELFT> &SymTab)<br>
-    : OutputSectionBase<ELFT::Is64Bits>(".dynamic", llvm::ELF::SHT_DYNAMIC,<br>
-                                        llvm::ELF::SHF_ALLOC |<br>
-                                            llvm::ELF::SHF_WRITE),<br>
+    : OutputSectionBase<ELFT>(".dynamic", llvm::ELF::SHT_DYNAMIC,<br>
+                              llvm::ELF::SHF_ALLOC | llvm::ELF::SHF_WRITE),<br>
       SymTab(SymTab) {<br>
-  typename Base::HeaderT &Header = this->Header;<br>
+  Elf_Shdr &Header = this->Header;<br>
   Header.sh_addralign = ELFT::Is64Bits ? 8 : 4;<br>
   Header.sh_entsize = ELFT::Is64Bits ? 16 : 8;<br>
 }<br>
@@ -258,7 +243,7 @@ template <class ELFT> void DynamicSectio<br>
   if (this->Header.sh_size)<br>
     return; // Already finalized.<br>
<br>
-  typename Base::HeaderT &Header = this->Header;<br>
+  Elf_Shdr &Header = this->Header;<br>
   Header.sh_link = Out<ELFT>::DynStrTab->SectionIndex;<br>
<br>
   unsigned NumEntries = 0;<br>
@@ -358,7 +343,7 @@ template <class ELFT> void DynamicSectio<br>
     WriteVal(DT_SONAME, Out<ELFT>::DynStrTab->getFileOff(Config->SoName));<br>
<br>
   auto WriteArray = [&](int32_t T1, int32_t T2,<br>
-                        const OutputSectionBase<ELFT::Is64Bits> *Sec) {<br>
+                        const OutputSectionBase<ELFT> *Sec) {<br>
     if (!Sec)<br>
       return;<br>
     WritePtr(T1, Sec->getVA());<br>
@@ -391,7 +376,7 @@ template <class ELFT> void DynamicSectio<br>
 template <class ELFT><br>
 OutputSection<ELFT>::OutputSection(StringRef Name, uint32_t sh_type,<br>
                                    uintX_t sh_flags)<br>
-    : OutputSectionBase<ELFT::Is64Bits>(Name, sh_type, sh_flags) {}<br>
+    : OutputSectionBase<ELFT>(Name, sh_type, sh_flags) {}<br>
<br>
 template <class ELFT><br>
 void OutputSection<ELFT>::addSection(InputSection<ELFT> *C) {<br>
@@ -506,17 +491,16 @@ template <class ELFT> void OutputSection<br>
     C->writeTo(Buf);<br>
 }<br>
<br>
-template <bool Is64Bits><br>
-StringTableSection<Is64Bits>::StringTableSection(bool Dynamic)<br>
-    : OutputSectionBase<Is64Bits>(Dynamic ? ".dynstr" : ".strtab",<br>
-                                  llvm::ELF::SHT_STRTAB,<br>
-                                  Dynamic ? (uintX_t)llvm::ELF::SHF_ALLOC : 0),<br>
+template <class ELFT><br>
+StringTableSection<ELFT>::StringTableSection(bool Dynamic)<br>
+    : OutputSectionBase<ELFT>(Dynamic ? ".dynstr" : ".strtab",<br>
+                              llvm::ELF::SHT_STRTAB,<br>
+                              Dynamic ? (uintX_t)llvm::ELF::SHF_ALLOC : 0),<br>
       Dynamic(Dynamic) {<br>
   this->Header.sh_addralign = 1;<br>
 }<br>
<br>
-template <bool Is64Bits><br>
-void StringTableSection<Is64Bits>::writeTo(uint8_t *Buf) {<br>
+template <class ELFT> void StringTableSection<ELFT>::writeTo(uint8_t *Buf) {<br>
   StringRef Data = StrTabBuilder.data();<br>
   memcpy(Buf, Data.data(), Data.size());<br>
 }<br>
@@ -571,14 +555,14 @@ bool lld::elf2::shouldKeepInSymtab(const<br>
<br>
 template <class ELFT><br>
 SymbolTableSection<ELFT>::SymbolTableSection(<br>
-    SymbolTable<ELFT> &Table, StringTableSection<ELFT::Is64Bits> &StrTabSec)<br>
-    : OutputSectionBase<ELFT::Is64Bits>(<br>
+    SymbolTable<ELFT> &Table, StringTableSection<ELFT> &StrTabSec)<br>
+    : OutputSectionBase<ELFT>(<br>
           StrTabSec.isDynamic() ? ".dynsym" : ".symtab",<br>
           StrTabSec.isDynamic() ? llvm::ELF::SHT_DYNSYM : llvm::ELF::SHT_SYMTAB,<br>
           StrTabSec.isDynamic() ? (uintX_t)llvm::ELF::SHF_ALLOC : 0),<br>
       Table(Table), StrTabSec(StrTabSec) {<br>
-  typedef OutputSectionBase<ELFT::Is64Bits> Base;<br>
-  typename Base::HeaderT &Header = this->Header;<br>
+  typedef OutputSectionBase<ELFT> Base;<br>
+  typename Base::Elf_Shdr &Header = this->Header;<br>
<br>
   Header.sh_entsize = sizeof(Elf_Sym);<br>
   Header.sh_addralign = ELFT::Is64Bits ? 8 : 4;<br>
@@ -664,7 +648,7 @@ void SymbolTableSection<ELFT>::writeGlob<br>
<br>
     ESym->st_name = StrTabSec.getFileOff(Name);<br>
<br>
-    const OutputSectionBase<ELFT::Is64Bits> *OutSec = nullptr;<br>
+    const OutputSectionBase<ELFT> *OutSec = nullptr;<br>
     const InputSection<ELFT> *Section = nullptr;<br>
<br>
     switch (Body->kind()) {<br>
@@ -721,17 +705,10 @@ void SymbolTableSection<ELFT>::writeGlob<br>
<br>
 namespace lld {<br>
 namespace elf2 {<br>
-template class OutputSectionBase<false>;<br>
-template class OutputSectionBase<true>;<br>
-<br>
-template void OutputSectionBase<false>::writeHeaderTo<support::little>(<br>
-    ELFFile<ELFType<support::little, false>>::Elf_Shdr *SHdr);<br>
-template void OutputSectionBase<true>::writeHeaderTo<support::little>(<br>
-    ELFFile<ELFType<support::little, true>>::Elf_Shdr *SHdr);<br>
-template void OutputSectionBase<false>::writeHeaderTo<support::big>(<br>
-    ELFFile<ELFType<support::big, false>>::Elf_Shdr *SHdr);<br>
-template void OutputSectionBase<true>::writeHeaderTo<support::big>(<br>
-    ELFFile<ELFType<support::big, true>>::Elf_Shdr *SHdr);<br>
+template class OutputSectionBase<ELF32LE>;<br>
+template class OutputSectionBase<ELF32BE>;<br>
+template class OutputSectionBase<ELF64LE>;<br>
+template class OutputSectionBase<ELF64BE>;<br>
<br>
 template class GotSection<ELF32LE>;<br>
 template class GotSection<ELF32BE>;<br>
@@ -748,8 +725,10 @@ template class RelocationSection<ELF32BE<br>
 template class RelocationSection<ELF64LE>;<br>
 template class RelocationSection<ELF64BE>;<br>
<br>
-template class InterpSection<false>;<br>
-template class InterpSection<true>;<br>
+template class InterpSection<ELF32LE>;<br>
+template class InterpSection<ELF32BE>;<br>
+template class InterpSection<ELF64LE>;<br>
+template class InterpSection<ELF64BE>;<br>
<br>
 template class HashTableSection<ELF32LE>;<br>
 template class HashTableSection<ELF32BE>;<br>
@@ -766,8 +745,10 @@ template class OutputSection<ELF32BE>;<br>
 template class OutputSection<ELF64LE>;<br>
 template class OutputSection<ELF64BE>;<br>
<br>
-template class StringTableSection<false>;<br>
-template class StringTableSection<true>;<br>
+template class StringTableSection<ELF32LE>;<br>
+template class StringTableSection<ELF32BE>;<br>
+template class StringTableSection<ELF64LE>;<br>
+template class StringTableSection<ELF64BE>;<br>
<br>
 template class SymbolTableSection<ELF32LE>;<br>
 template class SymbolTableSection<ELF32BE>;<br>
<br>
Modified: lld/trunk/ELF/OutputSections.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.h?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/OutputSections.h?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/OutputSections.h (original)<br>
+++ lld/trunk/ELF/OutputSections.h Thu Oct 15 17:27:29 2015<br>
@@ -25,7 +25,7 @@ namespace elf2 {<br>
 class SymbolBody;<br>
 template <class ELFT> class SymbolTable;<br>
 template <class ELFT> class SymbolTableSection;<br>
-template <bool Is64Bits> class StringTableSection;<br>
+template <class ELFT> class StringTableSection;<br>
 template <class ELFT> class InputSection;<br>
 template <class ELFT> class OutputSection;<br>
 template <class ELFT> class ObjectFile;<br>
@@ -54,19 +54,16 @@ bool shouldKeepInSymtab(<br>
 // input sections, others are created by the linker.<br>
 // The writer creates multiple OutputSections and assign them unique,<br>
 // non-overlapping file offsets and VAs.<br>
-template <bool Is64Bits> class OutputSectionBase {<br>
+template <class ELFT> class OutputSectionBase {<br>
 public:<br>
-  typedef typename std::conditional<Is64Bits, uint64_t, uint32_t>::type uintX_t;<br>
-  typedef typename std::conditional<Is64Bits, llvm::ELF::Elf64_Shdr,<br>
-                                    llvm::ELF::Elf32_Shdr>::type HeaderT;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::Elf_Shdr Elf_Shdr;<br>
<br>
   OutputSectionBase(StringRef Name, uint32_t sh_type, uintX_t sh_flags);<br>
   void setVA(uintX_t VA) { Header.sh_addr = VA; }<br>
   uintX_t getVA() const { return Header.sh_addr; }<br>
   void setFileOffset(uintX_t Off) { Header.sh_offset = Off; }<br>
-  template <llvm::object::endianness E><br>
-  void writeHeaderTo(typename llvm::object::ELFFile<<br>
-                     llvm::object::ELFType<E, Is64Bits>>::Elf_Shdr *SHdr);<br>
+  void writeHeaderTo(Elf_Shdr *SHdr);<br>
   StringRef getName() { return Name; }<br>
   void setNameOffset(uintX_t Offset) { Header.sh_name = Offset; }<br>
<br>
@@ -89,13 +86,12 @@ public:<br>
<br>
 protected:<br>
   StringRef Name;<br>
-  HeaderT Header;<br>
+  Elf_Shdr Header;<br>
   ~OutputSectionBase() = default;<br>
 };<br>
<br>
-template <class ELFT><br>
-class GotSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
-  typedef OutputSectionBase<ELFT::Is64Bits> Base;<br>
+template <class ELFT> class GotSection final : public OutputSectionBase<ELFT> {<br>
+  typedef OutputSectionBase<ELFT> Base;<br>
   typedef typename Base::uintX_t uintX_t;<br>
<br>
 public:<br>
@@ -112,9 +108,8 @@ private:<br>
   std::vector<const SymbolBody *> Entries;<br>
 };<br>
<br>
-template <class ELFT><br>
-class PltSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
-  typedef OutputSectionBase<ELFT::Is64Bits> Base;<br>
+template <class ELFT> class PltSection final : public OutputSectionBase<ELFT> {<br>
+  typedef OutputSectionBase<ELFT> Base;<br>
   typedef typename Base::uintX_t uintX_t;<br>
<br>
 public:<br>
@@ -136,19 +131,19 @@ template <class ELFT> struct DynamicRelo<br>
 };<br>
<br>
 template <class ELFT><br>
-class SymbolTableSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
+class SymbolTableSection final : public OutputSectionBase<ELFT> {<br>
 public:<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Shdr Elf_Shdr;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Sym Elf_Sym;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Sym_Range Elf_Sym_Range;<br>
-  typedef typename OutputSectionBase<ELFT::Is64Bits>::uintX_t uintX_t;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
   SymbolTableSection(SymbolTable<ELFT> &Table,<br>
-                     StringTableSection<ELFT::Is64Bits> &StrTabSec);<br>
+                     StringTableSection<ELFT> &StrTabSec);<br>
<br>
   void finalize() override;<br>
   void writeTo(uint8_t *Buf) override;<br>
   void addSymbol(StringRef Name, bool isLocal = false);<br>
-  StringTableSection<ELFT::Is64Bits> &getStrTabSec() const { return StrTabSec; }<br>
+  StringTableSection<ELFT> &getStrTabSec() const { return StrTabSec; }<br>
   unsigned getNumSymbols() const { return NumVisible + 1; }<br>
<br>
 private:<br>
@@ -156,13 +151,13 @@ private:<br>
   void writeGlobalSymbols(uint8_t *&Buf);<br>
<br>
   SymbolTable<ELFT> &Table;<br>
-  StringTableSection<ELFT::Is64Bits> &StrTabSec;<br>
+  StringTableSection<ELFT> &StrTabSec;<br>
   unsigned NumVisible = 0;<br>
   unsigned NumLocals = 0;<br>
 };<br>
<br>
 template <class ELFT><br>
-class RelocationSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
+class RelocationSection final : public OutputSectionBase<ELFT> {<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rel Elf_Rel;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rela Elf_Rela;<br>
   typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
@@ -181,13 +176,13 @@ private:<br>
 };<br>
<br>
 template <class ELFT><br>
-class OutputSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
+class OutputSection final : public OutputSectionBase<ELFT> {<br>
 public:<br>
-  typedef typename OutputSectionBase<ELFT::Is64Bits>::uintX_t uintX_t;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Shdr Elf_Shdr;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Sym Elf_Sym;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rel Elf_Rel;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rela Elf_Rela;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
   OutputSection(StringRef Name, uint32_t sh_type, uintX_t sh_flags);<br>
   void addSection(InputSection<ELFT> *C);<br>
   void writeTo(uint8_t *Buf) override;<br>
@@ -196,18 +191,17 @@ private:<br>
   std::vector<InputSection<ELFT> *> Sections;<br>
 };<br>
<br>
-template <bool Is64Bits><br>
-class InterpSection final : public OutputSectionBase<Is64Bits> {<br>
+template <class ELFT><br>
+class InterpSection final : public OutputSectionBase<ELFT> {<br>
 public:<br>
   InterpSection();<br>
-<br>
   void writeTo(uint8_t *Buf);<br>
 };<br>
<br>
-template <bool Is64Bits><br>
-class StringTableSection final : public OutputSectionBase<Is64Bits> {<br>
+template <class ELFT><br>
+class StringTableSection final : public OutputSectionBase<ELFT> {<br>
 public:<br>
-  typedef typename OutputSectionBase<Is64Bits>::uintX_t uintX_t;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
   StringTableSection(bool Dynamic);<br>
   void add(StringRef S) { StrTabBuilder.add(S); }<br>
   size_t getFileOff(StringRef S) const { return StrTabBuilder.getOffset(S); }<br>
@@ -227,7 +221,7 @@ private:<br>
 };<br>
<br>
 template <class ELFT><br>
-class HashTableSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
+class HashTableSection final : public OutputSectionBase<ELFT> {<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Word Elf_Word;<br>
<br>
 public:<br>
@@ -241,22 +235,22 @@ private:<br>
 };<br>
<br>
 template <class ELFT><br>
-class DynamicSection final : public OutputSectionBase<ELFT::Is64Bits> {<br>
-  typedef OutputSectionBase<ELFT::Is64Bits> Base;<br>
-  typedef typename Base::HeaderT HeaderT;<br>
+class DynamicSection final : public OutputSectionBase<ELFT> {<br>
+  typedef OutputSectionBase<ELFT> Base;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::Elf_Dyn Elf_Dyn;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rel Elf_Rel;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Rela Elf_Rela;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::Elf_Shdr Elf_Shdr;<br>
   typedef typename llvm::object::ELFFile<ELFT>::Elf_Sym Elf_Sym;<br>
-  typedef typename llvm::object::ELFFile<ELFT>::Elf_Dyn Elf_Dyn;<br>
<br>
 public:<br>
   DynamicSection(SymbolTable<ELFT> &SymTab);<br>
   void finalize() override;<br>
   void writeTo(uint8_t *Buf) override;<br>
<br>
-  OutputSectionBase<ELFT::Is64Bits> *PreInitArraySec = nullptr;<br>
-  OutputSectionBase<ELFT::Is64Bits> *InitArraySec = nullptr;<br>
-  OutputSectionBase<ELFT::Is64Bits> *FiniArraySec = nullptr;<br>
+  OutputSectionBase<ELFT> *PreInitArraySec = nullptr;<br>
+  OutputSectionBase<ELFT> *InitArraySec = nullptr;<br>
+  OutputSectionBase<ELFT> *FiniArraySec = nullptr;<br>
<br>
 private:<br>
   SymbolTable<ELFT> &SymTab;<br>
@@ -271,14 +265,14 @@ template <class ELFT> struct Out {<br>
   static DynamicSection<ELFT> *Dynamic;<br>
   static GotSection<ELFT> *Got;<br>
   static HashTableSection<ELFT> *HashTab;<br>
-  static InterpSection<ELFT::Is64Bits> *Interp;<br>
+  static InterpSection<ELFT> *Interp;<br>
   static OutputSection<ELFT> *Bss;<br>
-  static OutputSectionBase<ELFT::Is64Bits> *Opd;<br>
+  static OutputSectionBase<ELFT> *Opd;<br>
   static uint8_t *OpdBuf;<br>
   static PltSection<ELFT> *Plt;<br>
   static RelocationSection<ELFT> *RelaDyn;<br>
-  static StringTableSection<ELFT::Is64Bits> *DynStrTab;<br>
-  static StringTableSection<ELFT::Is64Bits> *StrTab;<br>
+  static StringTableSection<ELFT> *DynStrTab;<br>
+  static StringTableSection<ELFT> *StrTab;<br>
   static SymbolTableSection<ELFT> *DynSymTab;<br>
   static SymbolTableSection<ELFT> *SymTab;<br>
 };<br>
@@ -286,14 +280,14 @@ template <class ELFT> struct Out {<br>
 template <class ELFT> DynamicSection<ELFT> *Out<ELFT>::Dynamic;<br>
 template <class ELFT> GotSection<ELFT> *Out<ELFT>::Got;<br>
 template <class ELFT> HashTableSection<ELFT> *Out<ELFT>::HashTab;<br>
-template <class ELFT> InterpSection<ELFT::Is64Bits> *Out<ELFT>::Interp;<br>
+template <class ELFT> InterpSection<ELFT> *Out<ELFT>::Interp;<br>
 template <class ELFT> OutputSection<ELFT> *Out<ELFT>::Bss;<br>
-template <class ELFT> OutputSectionBase<ELFT::Is64Bits> *Out<ELFT>::Opd;<br>
+template <class ELFT> OutputSectionBase<ELFT> *Out<ELFT>::Opd;<br>
 template <class ELFT> uint8_t *Out<ELFT>::OpdBuf;<br>
 template <class ELFT> PltSection<ELFT> *Out<ELFT>::Plt;<br>
 template <class ELFT> RelocationSection<ELFT> *Out<ELFT>::RelaDyn;<br>
-template <class ELFT> StringTableSection<ELFT::Is64Bits> *Out<ELFT>::DynStrTab;<br>
-template <class ELFT> StringTableSection<ELFT::Is64Bits> *Out<ELFT>::StrTab;<br>
+template <class ELFT> StringTableSection<ELFT> *Out<ELFT>::DynStrTab;<br>
+template <class ELFT> StringTableSection<ELFT> *Out<ELFT>::StrTab;<br>
 template <class ELFT> SymbolTableSection<ELFT> *Out<ELFT>::DynSymTab;<br>
 template <class ELFT> SymbolTableSection<ELFT> *Out<ELFT>::SymTab;<br>
 }<br>
<br>
Modified: lld/trunk/ELF/SymbolTable.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.cpp?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.cpp?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/SymbolTable.cpp (original)<br>
+++ lld/trunk/ELF/SymbolTable.cpp Thu Oct 15 17:27:29 2015<br>
@@ -71,9 +71,9 @@ SymbolBody *SymbolTable<ELFT>::addUndefi<br>
 }<br>
<br>
 template <class ELFT><br>
-void SymbolTable<ELFT>::addSyntheticSym(<br>
-    StringRef Name, OutputSectionBase<ELFT::Is64Bits> &Section,<br>
-    typename ELFFile<ELFT>::uintX_t Value) {<br>
+void SymbolTable<ELFT>::addSyntheticSym(StringRef Name,<br>
+                                        OutputSectionBase<ELFT> &Section,<br>
+                                        typename ELFFile<ELFT>::uintX_t Value) {<br>
   typedef typename DefinedSynthetic<ELFT>::Elf_Sym Elf_Sym;<br>
   auto ESym = new (Alloc) Elf_Sym;<br>
   memset(ESym, 0, sizeof(Elf_Sym));<br>
<br>
Modified: lld/trunk/ELF/SymbolTable.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.h?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/SymbolTable.h?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/SymbolTable.h (original)<br>
+++ lld/trunk/ELF/SymbolTable.h Thu Oct 15 17:27:29 2015<br>
@@ -15,7 +15,7 @@<br>
<br>
 namespace lld {<br>
 namespace elf2 {<br>
-template <bool Is64Bits> class OutputSectionBase;<br>
+template <class ELFT> class OutputSectionBase;<br>
 struct Symbol;<br>
<br>
 // SymbolTable is a bucket of all known symbols, including defined,<br>
@@ -50,8 +50,7 @@ public:<br>
<br>
   SymbolBody *addUndefined(StringRef Name);<br>
   SymbolBody *addUndefinedOpt(StringRef Name);<br>
-  void addSyntheticSym(StringRef Name,<br>
-                       OutputSectionBase<ELFT::Is64Bits> &Section,<br>
+  void addSyntheticSym(StringRef Name, OutputSectionBase<ELFT> &Section,<br>
                        typename llvm::object::ELFFile<ELFT>::uintX_t Value);<br>
   void addIgnoredSym(StringRef Name);<br>
   bool isUndefined(StringRef Name);<br>
<br>
Modified: lld/trunk/ELF/Symbols.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.h?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.h?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/Symbols.h (original)<br>
+++ lld/trunk/ELF/Symbols.h Thu Oct 15 17:27:29 2015<br>
@@ -37,7 +37,7 @@ class InputFile;<br>
 class SymbolBody;<br>
 template <class ELFT> class ObjectFile;<br>
 template <class ELFT> class OutputSection;<br>
-template <bool Is64Bits> class OutputSectionBase;<br>
+template <class ELFT> class OutputSectionBase;<br>
 template <class ELFT> class SharedFile;<br>
<br>
 // Initializes global objects defined in this file.<br>
@@ -193,8 +193,7 @@ template <class ELFT> class DefinedCommo<br>
   typedef typename Base::Elf_Sym Elf_Sym;<br>
<br>
 public:<br>
-  typedef typename std::conditional<ELFT::Is64Bits, uint64_t, uint32_t>::type<br>
-      uintX_t;<br>
+  typedef typename llvm::object::ELFFile<ELFT>::uintX_t uintX_t;<br>
   DefinedCommon(StringRef N, const Elf_Sym &Sym)<br>
       : Defined<ELFT>(Base::DefinedCommonKind, N, Sym) {<br>
     MaxAlignment = Sym.st_value;<br>
@@ -234,14 +233,14 @@ template <class ELFT> class DefinedSynth<br>
 public:<br>
   typedef typename Base::Elf_Sym Elf_Sym;<br>
   DefinedSynthetic(StringRef N, const Elf_Sym &Sym,<br>
-                   OutputSectionBase<ELFT::Is64Bits> &Section)<br>
+                   OutputSectionBase<ELFT> &Section)<br>
       : Defined<ELFT>(Base::DefinedSyntheticKind, N, Sym), Section(Section) {}<br>
<br>
   static bool classof(const SymbolBody *S) {<br>
     return S->kind() == Base::DefinedSyntheticKind;<br>
   }<br>
<br>
-  const OutputSectionBase<ELFT::Is64Bits> &Section;<br>
+  const OutputSectionBase<ELFT> &Section;<br>
 };<br>
<br>
 // Undefined symbol.<br>
<br>
Modified: lld/trunk/ELF/Writer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=250466&r1=250465&r2=250466&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=250466&r1=250465&r2=250466&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/Writer.cpp (original)<br>
+++ lld/trunk/ELF/Writer.cpp Thu Oct 15 17:27:29 2015<br>
@@ -72,13 +72,13 @@ private:<br>
<br>
   SpecificBumpPtrAllocator<OutputSection<ELFT>> SecAlloc;<br>
   BumpPtrAllocator Alloc;<br>
-  std::vector<OutputSectionBase<ELFT::Is64Bits> *> OutputSections;<br>
+  std::vector<OutputSectionBase<ELFT> *> OutputSections;<br>
   unsigned getNumSections() const { return OutputSections.size() + 1; }<br>
<br>
-  void addStartStopSymbols(OutputSectionBase<ELFT::Is64Bits> *Sec);<br>
+  void addStartStopSymbols(OutputSectionBase<ELFT> *Sec);<br>
   void setPhdr(Elf_Phdr *PH, uint32_t Type, uint32_t Flags, uintX_t FileOff,<br>
                uintX_t VA, uintX_t Align);<br>
-  void copyPhdr(Elf_Phdr *PH, OutputSectionBase<ELFT::Is64Bits> *From);<br>
+  void copyPhdr(Elf_Phdr *PH, OutputSectionBase<ELFT> *From);<br>
<br>
   SymbolTable<ELFT> &Symtab;<br>
   std::vector<Elf_Phdr> Phdrs;<br>
@@ -91,11 +91,11 @@ private:<br>
 template <class ELFT> void lld::elf2::writeResult(SymbolTable<ELFT> *Symtab) {<br>
   // Initialize output sections that are handled by Writer specially.<br>
   // Don't reorder because the order of initialization matters.<br>
-  InterpSection<ELFT::Is64Bits> Interp;<br>
+  InterpSection<ELFT> Interp;<br>
   Out<ELFT>::Interp = &Interp;<br>
-  StringTableSection<ELFT::Is64Bits> StrTab(false);<br>
+  StringTableSection<ELFT> StrTab(false);<br>
   Out<ELFT>::StrTab = &StrTab;<br>
-  StringTableSection<ELFT::Is64Bits> DynStrTab(true);<br>
+  StringTableSection<ELFT> DynStrTab(true);<br>
   Out<ELFT>::DynStrTab = &DynStrTab;<br>
   OutputSection<ELFT> Bss(".bss", SHT_NOBITS, SHF_ALLOC | SHF_WRITE);<br>
   Out<ELFT>::Bss = &Bss;<br>
@@ -284,8 +284,8 @@ static int getPPC64SectionRank(StringRef<br>
<br>
 // Output section ordering is determined by this function.<br>
 template <class ELFT><br>
-static bool compareOutputSections(OutputSectionBase<ELFT::Is64Bits> *A,<br>
-                                  OutputSectionBase<ELFT::Is64Bits> *B) {<br>
+static bool compareOutputSections(OutputSectionBase<ELFT> *A,<br>
+                                  OutputSectionBase<ELFT> *B) {<br>
   typedef typename ELFFile<ELFT>::uintX_t uintX_t;<br>
<br>
   uintX_t AFlags = A->getFlags();<br>
@@ -403,7 +403,7 @@ template <class ELFT> void Writer<ELFT>:<br>
   if (!isOutputDynamic())<br>
     Symtab.addIgnoredSym("__tls_get_addr");<br>
<br>
-  std::vector<OutputSectionBase<ELFT::Is64Bits> *> RegularSections;<br>
+  std::vector<OutputSectionBase<ELFT> *> RegularSections;<br>
<br>
   for (const std::unique_ptr<ObjectFile<ELFT>> &F : Symtab.getObjectFiles()) {<br>
     for (InputSection<ELFT> *C : F->getSections()) {<br>
@@ -425,7 +425,7 @@ template <class ELFT> void Writer<ELFT>:<br>
     }<br>
   }<br>
<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : RegularSections)<br>
+  for (OutputSectionBase<ELFT> *Sec : RegularSections)<br>
     addStartStopSymbols(Sec);<br>
<br>
   Out<ELFT>::Dynamic->PreInitArraySec =<br>
@@ -436,7 +436,7 @@ template <class ELFT> void Writer<ELFT>:<br>
       Map.lookup({".fini_array", SHT_FINI_ARRAY, SHF_WRITE | SHF_ALLOC});<br>
<br>
   auto AddStartEnd = [&](StringRef Start, StringRef End,<br>
-                         OutputSectionBase<ELFT::Is64Bits> *OS) {<br>
+                         OutputSectionBase<ELFT> *OS) {<br>
     if (OS) {<br>
       Symtab.addSyntheticSym(Start, *OS, 0);<br>
       Symtab.addSyntheticSym(End, *OS, OS->getSize());<br>
@@ -493,7 +493,7 @@ template <class ELFT> void Writer<ELFT>:<br>
   for (unsigned I = 0, N = OutputSections.size(); I < N; ++I)<br>
     OutputSections[I]->SectionIndex = I + 1;<br>
<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections)<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections)<br>
     Out<ELFT>::StrTab->add(Sec->getName());<br>
<br>
   // Fill the DynStrTab early because Dynamic adds strings to<br>
@@ -501,7 +501,7 @@ template <class ELFT> void Writer<ELFT>:<br>
   Out<ELFT>::Dynamic->finalize();<br>
<br>
   // Fill other section headers.<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections)<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections)<br>
     Sec->finalize();<br>
<br>
   // If we have a .opd section (used under PPC64 for function descriptors),<br>
@@ -529,7 +529,7 @@ static bool isValidCIdentifier(StringRef<br>
 // respectively. This is not requested by the ELF standard, but GNU ld and<br>
 // gold provide the feature, and used by many programs.<br>
 template <class ELFT><br>
-void Writer<ELFT>::addStartStopSymbols(OutputSectionBase<ELFT::Is64Bits> *Sec) {<br>
+void Writer<ELFT>::addStartStopSymbols(OutputSectionBase<ELFT> *Sec) {<br>
   StringRef S = Sec->getName();<br>
   if (!isValidCIdentifier(S))<br>
     return;<br>
@@ -542,8 +542,7 @@ void Writer<ELFT>::addStartStopSymbols(O<br>
     Symtab.addSyntheticSym(Stop, *Sec, Sec->getSize());<br>
 }<br>
<br>
-template <class ELFT><br>
-static bool needsPhdr(OutputSectionBase<ELFT::Is64Bits> *Sec) {<br>
+template <class ELFT> static bool needsPhdr(OutputSectionBase<ELFT> *Sec) {<br>
   return Sec->getFlags() & SHF_ALLOC;<br>
 }<br>
<br>
@@ -561,7 +560,7 @@ template <class ELFT> void Writer<ELFT>:<br>
   if (isOutputDynamic())<br>
     ++NumPhdrs;<br>
   uintX_t Last = PF_R;<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections) {<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections) {<br>
     if (!Sec->getSize() || !needsPhdr<ELFT>(Sec))<br>
       continue;<br>
     uintX_t Flags = toPhdrFlags(Sec->getFlags());<br>
@@ -595,7 +594,7 @@ template <class ELFT> void Writer<ELFT>:<br>
   setPhdr(FileHeader, PT_LOAD, PF_R, 0, getVAStart(), Target->getPageSize());<br>
<br>
   SmallPtrSet<Elf_Phdr *, 8> Closed;<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections) {<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections) {<br>
     if (Sec->getSize()) {<br>
       uintX_t Flags = toPhdrFlags(Sec->getFlags());<br>
       Elf_Phdr *Last = &Phdrs.back();<br>
@@ -699,9 +698,9 @@ template <class ELFT> void Writer<ELFT>:<br>
   auto SHdrs = reinterpret_cast<Elf_Shdr *>(Buf + EHdr->e_shoff);<br>
   // First entry is null.<br>
   ++SHdrs;<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections) {<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections) {<br>
     Sec->setNameOffset(Out<ELFT>::StrTab->getFileOff(Sec->getName()));<br>
-    Sec->template writeHeaderTo<ELFT::TargetEndianness>(SHdrs++);<br>
+    Sec->writeHeaderTo(SHdrs++);<br>
   }<br>
 }<br>
<br>
@@ -718,12 +717,12 @@ template <class ELFT> void Writer<ELFT>:<br>
<br>
   // PPC64 needs to process relocations in the .opd section before processing<br>
   // relocations in code-containing sections.<br>
-  if (OutputSectionBase<ELFT::Is64Bits> *Sec = Out<ELFT>::Opd) {<br>
+  if (OutputSectionBase<ELFT> *Sec = Out<ELFT>::Opd) {<br>
     Out<ELFT>::OpdBuf = Buf + Sec->getFileOff();<br>
     Sec->writeTo(Buf + Sec->getFileOff());<br>
   }<br>
<br>
-  for (OutputSectionBase<ELFT::Is64Bits> *Sec : OutputSections)<br>
+  for (OutputSectionBase<ELFT> *Sec : OutputSections)<br>
     if (Sec != Out<ELFT>::Opd)<br>
       Sec->writeTo(Buf + Sec->getFileOff());<br>
 }<br>
@@ -740,8 +739,7 @@ void Writer<ELFT>::setPhdr(Elf_Phdr *PH,<br>
 }<br>
<br>
 template <class ELFT><br>
-void Writer<ELFT>::copyPhdr(Elf_Phdr *PH,<br>
-                            OutputSectionBase<ELFT::Is64Bits> *From) {<br>
+void Writer<ELFT>::copyPhdr(Elf_Phdr *PH, OutputSectionBase<ELFT> *From) {<br>
   PH->p_flags = toPhdrFlags(From->getFlags());<br>
   PH->p_offset = From->getFileOff();<br>
   PH->p_vaddr = From->getVA();<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div></div>