[llvm] r240366 - Extract an utility for computing symbol sizes on MachO and COFF.

Filipe Cabecinhas filcab at gmail.com
Mon Jun 22 20:42:16 PDT 2015


On Monday, June 22, 2015, Rafael Espindola <rafael.espindola at gmail.com>
wrote:

> Author: rafael
> Date: Mon Jun 22 21:08:48 2015
> New Revision: 240366
>
> URL: http://llvm.org/viewvc/llvm-project?rev=240366&view=rev
> Log:
> Extract an utility for computing symbol sizes on MachO and COFF.
>
> I will add a second user in the next commit.
>
> Added:
>     llvm/trunk/include/llvm/Object/SymbolSize.h
>     llvm/trunk/lib/Object/SymbolSize.cpp
> Modified:
>     llvm/trunk/lib/Object/CMakeLists.txt
>     llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp
>
> Added: llvm/trunk/include/llvm/Object/SymbolSize.h
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/Object/SymbolSize.h?rev=240366&view=auto
>
> ==============================================================================
> --- llvm/trunk/include/llvm/Object/SymbolSize.h (added)
> +++ llvm/trunk/include/llvm/Object/SymbolSize.h Mon Jun 22 21:08:48 2015
> @@ -0,0 +1,26 @@
> +//===- SymbolSize.h ---------------------------------------------*- C++
> -*-===//
> +//
> +//                     The LLVM Compiler Infrastructure
> +//
> +// This file is distributed under the University of Illinois Open Source
> +// License. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +//
> +// Declares the writeArchive function for writing an archive file.

But does it really declare writeArchive? ;-)


> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef LLVM_OBJECT_SYMBOLSIZE_H
> +#define LLVM_OBJECT_SYMBOLSIZE_H
> +
> +#include "llvm/Object/ObjectFile.h"
> +
> +namespace llvm {
> +namespace object {
> +ErrorOr<std::vector<std::pair<SymbolRef, uint64_t>>>
> +computeSymbolSizes(const ObjectFile &O);
> +}
> +} // namespace llvm
> +
> +#endif
>
> Modified: llvm/trunk/lib/Object/CMakeLists.txt
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Object/CMakeLists.txt?rev=240366&r1=240365&r2=240366&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Object/CMakeLists.txt (original)
> +++ llvm/trunk/lib/Object/CMakeLists.txt Mon Jun 22 21:08:48 2015
> @@ -16,6 +16,7 @@ add_llvm_library(LLVMObject
>    ObjectFile.cpp
>    RecordStreamer.cpp
>    SymbolicFile.cpp
> +  SymbolSize.cpp
>
>    ADDITIONAL_HEADER_DIRS
>    ${LLVM_MAIN_INCLUDE_DIR}/llvm/Object
>
> Added: llvm/trunk/lib/Object/SymbolSize.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Object/SymbolSize.cpp?rev=240366&view=auto
>
> ==============================================================================
> --- llvm/trunk/lib/Object/SymbolSize.cpp (added)
> +++ llvm/trunk/lib/Object/SymbolSize.cpp Mon Jun 22 21:08:48 2015
> @@ -0,0 +1,88 @@
> +//===- SymbolSize.cpp
> -----------------------------------------------------===//
> +//
> +//                     The LLVM Compiler Infrastructure
> +//
> +// This file is distributed under the University of Illinois Open Source
> +// License. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#include "llvm/Object/SymbolSize.h"
> +#include "llvm/ADT/STLExtras.h"
> +#include "llvm/Object/ELFObjectFile.h"
> +
> +using namespace llvm;
> +using namespace object;
> +
> +namespace {
> +struct SymEntry {
> +  symbol_iterator I;
> +  uint64_t Address;
> +  unsigned Number;
> +  SectionRef Section;
> +};
> +}
> +
> +static int compareAddress(const SymEntry *A, const SymEntry *B) {
> +  if (A->Section == B->Section)
> +    return A->Address - B->Address;
> +  if (A->Section < B->Section)
> +    return -1;
> +  return 1;
> +}
> +
> +static int compareNumber(const SymEntry *A, const SymEntry *B) {
> +  return A->Number - B->Number;
> +}
> +
> +ErrorOr<std::vector<std::pair<SymbolRef, uint64_t>>>
> +llvm::object::computeSymbolSizes(const ObjectFile &O) {
> +  std::vector<std::pair<SymbolRef, uint64_t>> Ret;
> +
> +  if (isa<ELFObjectFileBase>(&O)) {
> +    for (SymbolRef Sym : O.symbols()) {
> +      Ret.push_back({Sym, Sym.getSize()});
> +    }
> +    return Ret;
> +  }
> +
> +  // Collect sorted symbol addresses. Include dummy addresses for the end
> +  // of each section.
> +  std::vector<SymEntry> Addresses;
> +  unsigned SymNum = 0;
> +  for (symbol_iterator I = O.symbol_begin(), E = O.symbol_end(); I != E;
> ++I) {

Why don't you use .symbols()?


> +    SymbolRef Sym = *I;
> +    uint64_t Address;
> +    if (std::error_code EC = Sym.getAddress(Address))
> +      return EC;
> +    section_iterator SecI = O.section_end();
> +    if (std::error_code EC = Sym.getSection(SecI))
> +      return EC;
> +    Addresses.push_back({I, Address, SymNum, *SecI});
> +    ++SymNum;
> +  }
> +  for (const SectionRef Sec : O.sections()) {
> +    uint64_t Address = Sec.getAddress();
> +    uint64_t Size = Sec.getSize();
> +    Addresses.push_back({O.symbol_end(), Address + Size, 0, Sec});
> +  }
> +  array_pod_sort(Addresses.begin(), Addresses.end(), compareAddress);
> +
> +  // Compute the size as the gap to the next symbol
> +  for (unsigned I = 0, N = Addresses.size() - 1; I < N; ++I) {
> +    auto &P = Addresses[I];
> +    if (P.I == O.symbol_end())
> +      continue;
> +    uint64_t Size = Addresses[I + 1].Address - P.Address;
> +    P.Address = Size;
> +  }
> +
> +  // Put back in the original order and copy the result
> +  array_pod_sort(Addresses.begin(), Addresses.end(), compareNumber);
> +  for (SymEntry &P : Addresses) {
> +    if (P.I == O.symbol_end())
> +      continue;
> +    Ret.push_back({*P.I, P.Address});
> +  }
> +  return Ret;
> +}
>
> Modified: llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp?rev=240366&r1=240365&r2=240366&view=diff
>
> ==============================================================================
> --- llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp (original)
> +++ llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp Mon Jun 22 21:08:48 2015
> @@ -25,6 +25,7 @@
>  #include "llvm/MC/MCRegisterInfo.h"
>  #include "llvm/MC/MCSubtargetInfo.h"
>  #include "llvm/Object/MachO.h"
> +#include "llvm/Object/SymbolSize.h"
>  #include "llvm/Support/CommandLine.h"
>  #include "llvm/Support/DynamicLibrary.h"
>  #include "llvm/Support/ManagedStatic.h"
> @@ -252,38 +253,14 @@ static int printLineInfoForInput(bool Lo
>      std::unique_ptr<DIContext> Context(
>        new DWARFContextInMemory(*SymbolObj,LoadedObjInfo.get()));
>
> -    // FIXME: This is generally useful. Figure out a place in lib/Object
> to
> -    // put utility functions.
> -    std::map<object::SectionRef, std::vector<uint64_t>> FuncAddresses;
> -    if (!isa<ELFObjectFileBase>(SymbolObj)) {
> -      for (object::SymbolRef Sym : SymbolObj->symbols()) {
> -        object::SymbolRef::Type SymType;
> -        if (Sym.getType(SymType))
> -          continue;
> -        if (SymType != object::SymbolRef::ST_Function)
> -          continue;
> -        uint64_t Addr;
> -        if (Sym.getAddress(Addr))
> -          continue;
> -        object::section_iterator Sec = SymbolObj->section_end();
> -        if (Sym.getSection(Sec))
> -          continue;
> -        std::vector<uint64_t> &Addrs = FuncAddresses[*Sec];
> -        if (Addrs.empty()) {
> -          uint64_t SecAddr = Sec->getAddress();
> -          uint64_t SecSize = Sec->getSize();
> -          Addrs.push_back(SecAddr + SecSize);
> -        }
> -        Addrs.push_back(Addr);
> -      }
> -      for (auto &Pair : FuncAddresses) {
> -        std::vector<uint64_t> &Addrs = Pair.second;
> -        array_pod_sort(Addrs.begin(), Addrs.end());
> -      }
> -    }
> +    ErrorOr<std::vector<std::pair<SymbolRef, uint64_t>>> SymAddrOrErr =
> +        object::computeSymbolSizes(*SymbolObj);
> +    if (std::error_code EC = SymAddrOrErr.getError())
> +      return Error(EC.message());
>
>      // Use symbol info to iterate functions in the object.
> -    for (object::SymbolRef Sym : SymbolObj->symbols()) {
> +    for (const auto &P : *SymAddrOrErr) {
> +      object::SymbolRef Sym = P.first;
>        object::SymbolRef::Type SymType;
>        if (Sym.getType(SymType))
>          continue;
> @@ -295,20 +272,7 @@ static int printLineInfoForInput(bool Lo
>          if (Sym.getAddress(Addr))
>            continue;
>
> -        uint64_t Size;
> -        if (isa<ELFObjectFileBase>(SymbolObj)) {
> -          Size = Sym.getSize();
> -        } else {
> -          object::section_iterator Sec = SymbolObj->section_end();
> -          if (Sym.getSection(Sec))
> -            continue;
> -          const std::vector<uint64_t> &Addrs = FuncAddresses[*Sec];
> -          auto AddrI = std::find(Addrs.begin(), Addrs.end(), Addr);
> -          assert(AddrI != Addrs.end() && (AddrI + 1) != Addrs.end());
> -          assert(*AddrI == Addr);
> -          Size = *(AddrI + 1) - Addr;
> -        }
> -
> +        uint64_t Size = P.second;
>          // If we're not using the debug object, compute the address of the
>          // symbol in memory (rather than that in the unrelocated object
> file)
>          // and use that to query the DWARFContext.
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu <javascript:;>
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
>


-- 
  F
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20150622/a0170271/attachment.html>


More information about the llvm-commits mailing list