[llvm] r222810 - [MCJIT] Clean up RuntimeDyld's quirky object-ownership/modification scheme.
Aaron Ballman
aaron at aaronballman.com
Wed Nov 26 06:49:47 PST 2014
On Wed, Nov 26, 2014 at 1:53 AM, Lang Hames <lhames at gmail.com> wrote:
> Author: lhames
> Date: Wed Nov 26 00:53:26 2014
> New Revision: 222810
>
> URL: http://llvm.org/viewvc/llvm-project?rev=222810&view=rev
> Log:
> [MCJIT] Clean up RuntimeDyld's quirky object-ownership/modification scheme.
>
> Previously, when loading an object file, RuntimeDyld (1) took ownership of the
> ObjectFile instance (and associated MemoryBuffer), (2) potentially modified the
> object in-place, and (3) returned an ObjectImage that managed ownership of the
> now-modified object and provided some convenience methods. This scheme accreted
> over several years as features were tacked on to RuntimeDyld, and was both
> unintuitive and unsafe (See e.g. http://llvm.org/PR20722).
>
> This patch fixes the issue by removing all ownership and in-place modification
> of object files from RuntimeDyld. Existing behavior, including debugger
> registration, is preserved.
>
> Noteworthy changes include:
>
> (1) ObjectFile instances are now passed to RuntimeDyld by const-ref.
> (2) The ObjectImage and ObjectBuffer classes have been removed entirely, they
> existed to model ownership within RuntimeDyld, and so are no longer needed.
> (3) RuntimeDyld::loadObject now returns an instance of a new class,
> RuntimeDyld::LoadedObjectInfo, which can be used to construct a modified
> object suitable for registration with the debugger, following the existing
> debugger registration scheme.
> (4) The JITRegistrar class has been removed, and the GDBRegistrar class has been
> re-written as a JITEventListener.
>
> This should fix http://llvm.org/PR20722 .
>
>
> Added:
> llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h
> - copied, changed from r222801, llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp
> - copied, changed from r222764, llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> Removed:
> llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h
> llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h
> Modified:
> llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h
> llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h
> llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h
> llvm/trunk/lib/ExecutionEngine/CMakeLists.txt
> llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp
> llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp
> llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h
> llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h
> llvm/trunk/tools/lli/RemoteMemoryManager.cpp
> llvm/trunk/tools/lli/RemoteMemoryManager.h
> llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp
> llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h Wed Nov 26 00:53:26 2014
> @@ -15,6 +15,7 @@
> #ifndef LLVM_EXECUTIONENGINE_JITEVENTLISTENER_H
> #define LLVM_EXECUTIONENGINE_JITEVENTLISTENER_H
>
> +#include "RuntimeDyld.h"
> #include "llvm/Config/llvm-config.h"
> #include "llvm/IR/DebugLoc.h"
> #include "llvm/Support/DataTypes.h"
> @@ -25,7 +26,10 @@ class Function;
> class MachineFunction;
> class OProfileWrapper;
> class IntelJITEventsWrapper;
> -class ObjectImage;
> +
> +namespace object {
> + class ObjectFile;
> +}
>
> /// JITEvent_EmittedFunctionDetails - Helper struct for containing information
> /// about a generated machine code function.
> @@ -57,7 +61,7 @@ public:
>
> public:
> JITEventListener() {}
> - virtual ~JITEventListener();
> + virtual ~JITEventListener() {}
>
> /// NotifyObjectEmitted - Called after an object has been successfully
> /// emitted to memory. NotifyFunctionEmitted will not be called for
> @@ -67,11 +71,15 @@ public:
> /// The ObjectImage contains the generated object image
> /// with section headers updated to reflect the address at which sections
> /// were loaded and with relocations performed in-place on debug sections.
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj) {}
> + virtual void NotifyObjectEmitted(const object::ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {}
>
> /// NotifyFreeingObject - Called just before the memory associated with
> /// a previously emitted object is released.
> - virtual void NotifyFreeingObject(const ObjectImage &Obj) {}
> + virtual void NotifyFreeingObject(const object::ObjectFile &Obj) {}
> +
> + // Get a pointe to the GDB debugger registration listener.
> + static JITEventListener *createGDBRegistrationListener();
>
> #if LLVM_USE_INTEL_JITEVENTS
> // Construct an IntelJITEventListener
> @@ -105,7 +113,8 @@ public:
> return nullptr;
> }
> #endif // USE_OPROFILE
> -
> +private:
> + virtual void anchor();
> };
>
> } // end namespace llvm.
>
> Removed: llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (removed)
> @@ -1,76 +0,0 @@
> -//===---- ObjectBuffer.h - Utility class to wrap object image memory -----===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a wrapper class to hold the memory into which an
> -// object will be generated.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_EXECUTIONENGINE_OBJECTBUFFER_H
> -#define LLVM_EXECUTIONENGINE_OBJECTBUFFER_H
> -
> -#include "llvm/ADT/SmallVector.h"
> -#include "llvm/Support/MemoryBuffer.h"
> -#include "llvm/Support/raw_ostream.h"
> -
> -namespace llvm {
> -
> -/// This class acts as a container for the memory buffer used during generation
> -/// and loading of executable objects using MCJIT and RuntimeDyld. The
> -/// underlying memory for the object will be owned by the ObjectBuffer instance
> -/// throughout its lifetime.
> -class ObjectBuffer {
> - virtual void anchor();
> -public:
> - ObjectBuffer() {}
> - ObjectBuffer(std::unique_ptr<MemoryBuffer> Buf) : Buffer(std::move(Buf)) {}
> - virtual ~ObjectBuffer() {}
> -
> - MemoryBufferRef getMemBuffer() const { return Buffer->getMemBufferRef(); }
> -
> - const char *getBufferStart() const { return Buffer->getBufferStart(); }
> - size_t getBufferSize() const { return Buffer->getBufferSize(); }
> - StringRef getBuffer() const { return Buffer->getBuffer(); }
> - StringRef getBufferIdentifier() const {
> - return Buffer->getBufferIdentifier();
> - }
> -
> -protected:
> - // The memory contained in an ObjectBuffer
> - std::unique_ptr<MemoryBuffer> Buffer;
> -};
> -
> -/// This class encapsulates the SmallVector and raw_svector_ostream needed to
> -/// generate an object using MC code emission while providing a common
> -/// ObjectBuffer interface for access to the memory once the object has been
> -/// generated.
> -class ObjectBufferStream : public ObjectBuffer {
> - void anchor() override;
> -public:
> - ObjectBufferStream() : OS(SV) {}
> - virtual ~ObjectBufferStream() {}
> -
> - raw_ostream &getOStream() { return OS; }
> - void flush()
> - {
> - OS.flush();
> -
> - // Make the data accessible via the ObjectBuffer::Buffer
> - Buffer =
> - MemoryBuffer::getMemBuffer(StringRef(SV.data(), SV.size()), "", false);
> - }
> -
> -protected:
> - SmallVector<char, 4096> SV; // Working buffer into which we JIT.
> - raw_svector_ostream OS; // streaming wrapper
> -};
> -
> -} // namespace llvm
> -
> -#endif
>
> Removed: llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h (removed)
> @@ -1,76 +0,0 @@
> -//===---- ObjectImage.h - Format independent executuable object image -----===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a file format independent ObjectImage class.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
> -#define LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/Object/ObjectFile.h"
> -
> -namespace llvm {
> -
> -
> -/// ObjectImage - A container class that represents an ObjectFile that has been
> -/// or is in the process of being loaded into memory for execution.
> -class ObjectImage {
> - ObjectImage() LLVM_DELETED_FUNCTION;
> - ObjectImage(const ObjectImage &other) LLVM_DELETED_FUNCTION;
> - virtual void anchor();
> -
> -protected:
> - std::unique_ptr<ObjectBuffer> Buffer;
> -
> -public:
> - ObjectImage(std::unique_ptr<ObjectBuffer> Input) : Buffer(std::move(Input)) {}
> - virtual ~ObjectImage() {}
> -
> - virtual object::symbol_iterator begin_symbols() const = 0;
> - virtual object::symbol_iterator end_symbols() const = 0;
> - iterator_range<object::symbol_iterator> symbols() const {
> - return iterator_range<object::symbol_iterator>(begin_symbols(),
> - end_symbols());
> - }
> -
> - virtual object::section_iterator begin_sections() const = 0;
> - virtual object::section_iterator end_sections() const = 0;
> - iterator_range<object::section_iterator> sections() const {
> - return iterator_range<object::section_iterator>(begin_sections(),
> - end_sections());
> - }
> -
> - virtual /* Triple::ArchType */ unsigned getArch() const = 0;
> -
> - // Return the name associated with this ObjectImage.
> - // This is usually the name of the file or MemoryBuffer that the the
> - // ObjectBuffer was constructed from.
> - StringRef getImageName() const { return Buffer->getBufferIdentifier(); }
> -
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - virtual void updateSectionAddress(const object::SectionRef &Sec,
> - uint64_t Addr) = 0;
> - virtual void updateSymbolAddress(const object::SymbolRef &Sym,
> - uint64_t Addr) = 0;
> -
> - virtual StringRef getData() const = 0;
> -
> - virtual object::ObjectFile* getObjectFile() const = 0;
> -
> - // Subclasses can override these methods to provide JIT debugging support
> - virtual void registerWithDebugger() = 0;
> - virtual void deregisterWithDebugger() = 0;
> -};
> -
> -} // end namespace llvm
> -
> -#endif // LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h Wed Nov 26 00:53:26 2014
> @@ -22,7 +22,10 @@
> namespace llvm {
>
> class ExecutionEngine;
> -class ObjectImage;
> +
> + namespace object {
> + class ObjectFile;
> + }
>
> // RuntimeDyld clients often want to handle the memory management of
> // what gets placed where. For JIT clients, this is the subset of
> @@ -109,7 +112,7 @@ public:
> /// address space can use this call to remap the section addresses for the
> /// newly loaded object.
> virtual void notifyObjectLoaded(ExecutionEngine *EE,
> - const ObjectImage *) {}
> + const object::ObjectFile &) {}
>
> /// This method is called when object loading is complete and section page
> /// permissions can be applied. It is up to the memory manager implementation
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h Wed Nov 26 00:53:26 2014
> @@ -15,19 +15,19 @@
> #define LLVM_EXECUTIONENGINE_RUNTIMEDYLD_H
>
> #include "llvm/ADT/StringRef.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> #include "llvm/ExecutionEngine/RTDyldMemoryManager.h"
> #include "llvm/Support/Memory.h"
> +#include <memory>
>
> namespace llvm {
>
> namespace object {
> class ObjectFile;
> + template <typename T> class OwningBinary;
> }
>
> class RuntimeDyldImpl;
> class RuntimeDyldCheckerImpl;
> -class ObjectImage;
>
> class RuntimeDyld {
> friend class RuntimeDyldCheckerImpl;
> @@ -46,22 +46,35 @@ protected:
> // Any relocations already associated with the symbol will be re-resolved.
> void reassignSectionAddress(unsigned SectionID, uint64_t Addr);
> public:
> +
> + /// \brief Information about the loaded object.
> + class LoadedObjectInfo {
> + friend class RuntimeDyldImpl;
> + public:
> + LoadedObjectInfo(RuntimeDyldImpl &RTDyld, unsigned BeginIdx,
> + unsigned EndIdx)
> + : RTDyld(RTDyld), BeginIdx(BeginIdx), EndIdx(EndIdx) { }
> +
> + virtual ~LoadedObjectInfo() {}
> +
> + virtual object::OwningBinary<object::ObjectFile>
> + getObjectForDebug(const object::ObjectFile &Obj) const = 0;
> +
> + uint64_t getSectionLoadAddress(StringRef Name) const;
> +
> + protected:
> + virtual void anchor();
> +
> + RuntimeDyldImpl &RTDyld;
> + unsigned BeginIdx, EndIdx;
> + };
> +
> RuntimeDyld(RTDyldMemoryManager *);
> ~RuntimeDyld();
>
> - /// Prepare the object contained in the input buffer for execution.
> - /// Ownership of the input buffer is transferred to the ObjectImage
> - /// instance returned from this function if successful. In the case of load
> - /// failure, the input buffer will be deleted.
> - std::unique_ptr<ObjectImage>
> - loadObject(std::unique_ptr<ObjectBuffer> InputBuffer);
> -
> - /// Prepare the referenced object file for execution.
> - /// Ownership of the input object is transferred to the ObjectImage
> - /// instance returned from this function if successful. In the case of load
> - /// failure, the input object will be deleted.
> - std::unique_ptr<ObjectImage>
> - loadObject(std::unique_ptr<object::ObjectFile> InputObject);
> + /// Add the referenced object file to the list of objects to be loaded and
> + /// relocated.
> + std::unique_ptr<LoadedObjectInfo> loadObject(const object::ObjectFile &O);
>
> /// Get the address of our local copy of the symbol. This may or may not
> /// be the address used for relocation (clients can copy the data around
>
> Modified: llvm/trunk/lib/ExecutionEngine/CMakeLists.txt
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/CMakeLists.txt?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/CMakeLists.txt (original)
> +++ llvm/trunk/lib/ExecutionEngine/CMakeLists.txt Wed Nov 26 00:53:26 2014
> @@ -3,7 +3,6 @@
> add_llvm_library(LLVMExecutionEngine
> ExecutionEngine.cpp
> ExecutionEngineBindings.cpp
> - JITEventListener.cpp
> RTDyldMemoryManager.cpp
> TargetSelect.cpp
> )
>
> Modified: llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp Wed Nov 26 00:53:26 2014
> @@ -16,8 +16,7 @@
> #include "llvm/ADT/SmallString.h"
> #include "llvm/ADT/Statistic.h"
> #include "llvm/ExecutionEngine/GenericValue.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectCache.h"
> +#include "llvm/ExecutionEngine/JITEventListener.h"
> #include "llvm/IR/Constants.h"
> #include "llvm/IR/DataLayout.h"
> #include "llvm/IR/DerivedTypes.h"
> @@ -43,17 +42,15 @@ using namespace llvm;
> STATISTIC(NumInitBytes, "Number of bytes of global vars initialized");
> STATISTIC(NumGlobals , "Number of global vars initialized");
>
> -// Pin the vtable to this file.
> -void ObjectCache::anchor() {}
> -void ObjectBuffer::anchor() {}
> -void ObjectBufferStream::anchor() {}
> -
> ExecutionEngine *(*ExecutionEngine::MCJITCtor)(
> std::unique_ptr<Module> M, std::string *ErrorStr,
> RTDyldMemoryManager *MCJMM, std::unique_ptr<TargetMachine> TM) = nullptr;
> ExecutionEngine *(*ExecutionEngine::InterpCtor)(std::unique_ptr<Module> M,
> std::string *ErrorStr) =nullptr;
>
> +// Anchor for the JITEventListener class.
> +void JITEventListener::anchor() {}
> +
> ExecutionEngine::ExecutionEngine(std::unique_ptr<Module> M)
> : EEState(*this),
> LazyFunctionCreator(nullptr) {
>
> Modified: llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp Wed Nov 26 00:53:26 2014
> @@ -21,7 +21,6 @@
> #include "llvm/ADT/DenseMap.h"
> #include "llvm/CodeGen/MachineFunction.h"
> #include "llvm/DebugInfo/DIContext.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Debug.h"
> #include "llvm/Support/raw_ostream.h"
> @@ -32,6 +31,7 @@
>
> using namespace llvm;
> using namespace llvm::jitprofiling;
> +using namespace llvm::object;
>
> #define DEBUG_TYPE "amplifier-jit-event-listener"
>
> @@ -48,6 +48,7 @@ class IntelJITEventListener : public JIT
> typedef DenseMap<const void *, MethodAddressVector> ObjectMap;
>
> ObjectMap LoadedObjectMap;
> + std::map<const char*, OwningBinary<ObjectFile>> DebugObjects;
>
> public:
> IntelJITEventListener(IntelJITEventsWrapper* libraryWrapper) {
> @@ -57,9 +58,10 @@ public:
> ~IntelJITEventListener() {
> }
>
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj);
> + void NotifyObjectEmitted(const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> - virtual void NotifyFreeingObject(const ObjectImage &Obj);
> + void NotifyFreeingObject(const ObjectFile &Obj) override;
> };
>
> static LineNumberInfo DILineInfoToIntelJITFormat(uintptr_t StartAddress,
> @@ -95,23 +97,29 @@ static iJIT_Method_Load FunctionDescToIn
> return Result;
> }
>
> -void IntelJITEventListener::NotifyObjectEmitted(const ObjectImage &Obj) {
> +void IntelJITEventListener::NotifyObjectEmitted(
> + const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> +
> + OwningBinary<ObjectFile> DebugObjOwner = L.getObjectForDebug(Obj);
> + const ObjectFile &DebugObj = *DebugObjOwner.getBinary();
> +
> // Get the address of the object image for use as a unique identifier
> - const void* ObjData = Obj.getData().data();
> - DIContext* Context = DIContext::getDWARFContext(*Obj.getObjectFile());
> + const void* ObjData = DebugObj.getData().data();
> + DIContext* Context = DIContext::getDWARFContext(DebugObj);
> MethodAddressVector Functions;
>
> // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(),
> - E = Obj.end_symbols();
> + for (symbol_iterator I = DebugObj.symbol_begin(),
> + E = DebugObj.symbol_end();
> I != E;
> ++I) {
> std::vector<LineNumberInfo> LineInfo;
> std::string SourceFileName;
>
> - object::SymbolRef::Type SymType;
> + SymbolRef::Type SymType;
> if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> + if (SymType == SymbolRef::ST_Function) {
> StringRef Name;
> uint64_t Addr;
> uint64_t Size;
> @@ -162,11 +170,18 @@ void IntelJITEventListener::NotifyObject
> // registered function addresses for each loaded object. We will
> // use the MethodIDs map to get the registered ID for each function.
> LoadedObjectMap[ObjData] = Functions;
> + DebugObjects[Obj.getData().data()] = std::move(DebugObjOwner);
> }
>
> -void IntelJITEventListener::NotifyFreeingObject(const ObjectImage &Obj) {
> +void IntelJITEventListener::NotifyFreeingObject(const ObjectFile &Obj) {
> + // This object may not have been registered with the listener. If it wasn't,
> + // bail out.
> + if (DebugObjects.find(Obj.getData().data()) == DebugObjects.end())
> + return;
> +
> // Get the address of the object image for use as a unique identifier
> - const void* ObjData = Obj.getData().data();
> + const ObjectFile &DebugObj = *DebugObjects[Obj.getData().data()].getBinary();
> + const void* ObjData = DebugObj.getData().data();
>
> // Get the object's function list from LoadedObjectMap
> ObjectMap::iterator OI = LoadedObjectMap.find(ObjData);
> @@ -190,6 +205,7 @@ void IntelJITEventListener::NotifyFreein
>
> // Erase the object from LoadedObjectMap
> LoadedObjectMap.erase(OI);
> + DebugObjects.erase(Obj.getData().data());
> }
>
> } // anonymous namespace.
>
> Removed: llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp (removed)
> @@ -1,15 +0,0 @@
> -//===-- JITEventListener.cpp ----------------------------------------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#include "llvm/ExecutionEngine/JITEventListener.h"
> -
> -using namespace llvm;
> -
> -// Out-of-line definition of the virtual destructor as this is the key function.
> -JITEventListener::~JITEventListener() {}
>
> Modified: llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp Wed Nov 26 00:53:26 2014
> @@ -11,8 +11,6 @@
> #include "llvm/ExecutionEngine/GenericValue.h"
> #include "llvm/ExecutionEngine/JITEventListener.h"
> #include "llvm/ExecutionEngine/MCJIT.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/SectionMemoryManager.h"
> #include "llvm/IR/DataLayout.h"
> #include "llvm/IR/DerivedTypes.h"
> @@ -21,6 +19,7 @@
> #include "llvm/IR/Module.h"
> #include "llvm/MC/MCAsmInfo.h"
> #include "llvm/Object/Archive.h"
> +#include "llvm/Object/ObjectFile.h"
> #include "llvm/PassManager.h"
> #include "llvm/Support/DynamicLibrary.h"
> #include "llvm/Support/ErrorHandling.h"
> @@ -31,6 +30,8 @@
>
> using namespace llvm;
>
> +void ObjectCache::anchor() {}
> +
> namespace {
>
> static struct RegisterJIT {
> @@ -74,6 +75,7 @@ MCJIT::MCJIT(std::unique_ptr<Module> M,
>
> OwnedModules.addModule(std::move(First));
> setDataLayout(TM->getSubtargetImpl()->getDataLayout());
> + RegisterJITEventListener(JITEventListener::createGDBRegistrationListener());
> }
>
> MCJIT::~MCJIT() {
> @@ -99,13 +101,13 @@ bool MCJIT::removeModule(Module *M) {
> }
>
> void MCJIT::addObjectFile(std::unique_ptr<object::ObjectFile> Obj) {
> - std::unique_ptr<ObjectImage> LoadedObject = Dyld.loadObject(std::move(Obj));
> - if (!LoadedObject || Dyld.hasError())
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo> L = Dyld.loadObject(*Obj);
> + if (Dyld.hasError())
> report_fatal_error(Dyld.getErrorString());
>
> - NotifyObjectEmitted(*LoadedObject);
> + NotifyObjectEmitted(*Obj, *L);
>
> - LoadedObjects.push_back(std::move(LoadedObject));
> + LoadedObjects.push_back(std::move(Obj));
> }
>
> void MCJIT::addObjectFile(object::OwningBinary<object::ObjectFile> Obj) {
> @@ -125,7 +127,7 @@ void MCJIT::setObjectCache(ObjectCache*
> ObjCache = NewCache;
> }
>
> -std::unique_ptr<ObjectBufferStream> MCJIT::emitObject(Module *M) {
> +std::unique_ptr<MemoryBuffer> MCJIT::emitObject(Module *M) {
> MutexGuard locked(lock);
>
> // This must be a module which has already been added but not loaded to this
> @@ -138,30 +140,32 @@ std::unique_ptr<ObjectBufferStream> MCJI
> PM.add(new DataLayoutPass());
>
> // The RuntimeDyld will take ownership of this shortly
> - std::unique_ptr<ObjectBufferStream> CompiledObject(new ObjectBufferStream());
> + SmallVector<char, 4096> ObjBufferSV;
> + raw_svector_ostream ObjStream(ObjBufferSV);
>
> // Turn the machine code intermediate representation into bytes in memory
> // that may be executed.
> - if (TM->addPassesToEmitMC(PM, Ctx, CompiledObject->getOStream(),
> - !getVerifyModules())) {
> + if (TM->addPassesToEmitMC(PM, Ctx, ObjStream, !getVerifyModules()))
> report_fatal_error("Target does not support MC emission!");
> - }
>
> // Initialize passes.
> PM.run(*M);
> // Flush the output buffer to get the generated code into memory
> - CompiledObject->flush();
> + ObjStream.flush();
> +
> + std::unique_ptr<MemoryBuffer> CompiledObjBuffer(
> + new ObjectMemoryBuffer(std::move(ObjBufferSV)));
>
> // If we have an object cache, tell it about the new object.
> // Note that we're using the compiled image, not the loaded image (as below).
> if (ObjCache) {
> // MemoryBuffer is a thin wrapper around the actual memory, so it's OK
> // to create a temporary object here and delete it after the call.
> - MemoryBufferRef MB = CompiledObject->getMemBuffer();
> + MemoryBufferRef MB = CompiledObjBuffer->getMemBufferRef();
> ObjCache->notifyObjectCompiled(M, MB);
> }
>
> - return CompiledObject;
> + return CompiledObjBuffer;
> }
>
> void MCJIT::generateCodeForModule(Module *M) {
> @@ -176,14 +180,10 @@ void MCJIT::generateCodeForModule(Module
> if (OwnedModules.hasModuleBeenLoaded(M))
> return;
>
> - std::unique_ptr<ObjectBuffer> ObjectToLoad;
> + std::unique_ptr<MemoryBuffer> ObjectToLoad;
> // Try to load the pre-compiled object from cache if possible
> - if (ObjCache) {
> - if (std::unique_ptr<MemoryBuffer> PreCompiledObject =
> - ObjCache->getObject(M))
> - ObjectToLoad =
> - llvm::make_unique<ObjectBuffer>(std::move(PreCompiledObject));
> - }
> + if (ObjCache)
> + ObjectToLoad = ObjCache->getObject(M);
>
> // If the cache did not contain a suitable object, compile the object
> if (!ObjectToLoad) {
> @@ -193,17 +193,18 @@ void MCJIT::generateCodeForModule(Module
>
> // Load the object into the dynamic linker.
> // MCJIT now owns the ObjectImage pointer (via its LoadedObjects list).
> - std::unique_ptr<ObjectImage> LoadedObject =
> - Dyld.loadObject(std::move(ObjectToLoad));
> - if (!LoadedObject)
> - report_fatal_error(Dyld.getErrorString());
> + ErrorOr<std::unique_ptr<object::ObjectFile>> LoadedObject =
> + object::ObjectFile::createObjectFile(ObjectToLoad->getMemBufferRef());
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo> L =
> + Dyld.loadObject(*LoadedObject.get());
>
> - // FIXME: Make this optional, maybe even move it to a JIT event listener
> - LoadedObject->registerWithDebugger();
> + if (Dyld.hasError())
> + report_fatal_error(Dyld.getErrorString());
>
> - NotifyObjectEmitted(*LoadedObject);
> + NotifyObjectEmitted(*LoadedObject.get(), *L);
>
> - LoadedObjects.push_back(std::move(LoadedObject));
> + Buffers.push_back(std::move(ObjectToLoad));
> + LoadedObjects.push_back(std::move(*LoadedObject));
>
> OwnedModules.markModuleAsLoaded(M);
> }
> @@ -549,6 +550,7 @@ void MCJIT::RegisterJITEventListener(JIT
> MutexGuard locked(lock);
> EventListeners.push_back(L);
> }
> +
> void MCJIT::UnregisterJITEventListener(JITEventListener *L) {
> if (!L)
> return;
> @@ -559,14 +561,17 @@ void MCJIT::UnregisterJITEventListener(J
> EventListeners.pop_back();
> }
> }
> -void MCJIT::NotifyObjectEmitted(const ObjectImage& Obj) {
> +
> +void MCJIT::NotifyObjectEmitted(const object::ObjectFile& Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> MutexGuard locked(lock);
> - MemMgr.notifyObjectLoaded(this, &Obj);
> + MemMgr.notifyObjectLoaded(this, Obj);
> for (unsigned I = 0, S = EventListeners.size(); I < S; ++I) {
> - EventListeners[I]->NotifyObjectEmitted(Obj);
> + EventListeners[I]->NotifyObjectEmitted(Obj, L);
> }
> }
> -void MCJIT::NotifyFreeingObject(const ObjectImage& Obj) {
> +
> +void MCJIT::NotifyFreeingObject(const object::ObjectFile& Obj) {
> MutexGuard locked(lock);
> for (JITEventListener *L : EventListeners)
> L->NotifyFreeingObject(Obj);
>
> Modified: llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h Wed Nov 26 00:53:26 2014
> @@ -10,12 +10,12 @@
> #ifndef LLVM_LIB_EXECUTIONENGINE_MCJIT_MCJIT_H
> #define LLVM_LIB_EXECUTIONENGINE_MCJIT_MCJIT_H
>
> +#include "ObjectBuffer.h"
> #include "llvm/ADT/DenseMap.h"
> #include "llvm/ADT/SmallPtrSet.h"
> #include "llvm/ADT/SmallVector.h"
> #include "llvm/ExecutionEngine/ExecutionEngine.h"
> #include "llvm/ExecutionEngine/ObjectCache.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/IR/Module.h"
>
> @@ -57,7 +57,7 @@ public:
> }
>
> void notifyObjectLoaded(ExecutionEngine *EE,
> - const ObjectImage *Obj) override {
> + const object::ObjectFile &Obj) override {
> ClientMM->notifyObjectLoaded(EE, Obj);
> }
>
> @@ -222,7 +222,7 @@ class MCJIT : public ExecutionEngine {
> SmallVector<object::OwningBinary<object::Archive>, 2> Archives;
> SmallVector<std::unique_ptr<MemoryBuffer>, 2> Buffers;
>
> - SmallVector<std::unique_ptr<ObjectImage>, 2> LoadedObjects;
> + SmallVector<std::unique_ptr<object::ObjectFile>, 2> LoadedObjects;
>
> // An optional ObjectCache to be notified of compiled objects and used to
> // perform lookup of pre-compiled code to avoid re-compilation.
> @@ -341,10 +341,11 @@ protected:
> /// this function call is expected to be the contained module. The module
> /// is passed as a parameter here to prepare for multiple module support in
> /// the future.
> - std::unique_ptr<ObjectBufferStream> emitObject(Module *M);
> + std::unique_ptr<MemoryBuffer> emitObject(Module *M);
>
> - void NotifyObjectEmitted(const ObjectImage& Obj);
> - void NotifyFreeingObject(const ObjectImage& Obj);
> + void NotifyObjectEmitted(const object::ObjectFile& Obj,
> + const RuntimeDyld::LoadedObjectInfo &L);
> + void NotifyFreeingObject(const object::ObjectFile& Obj);
>
> uint64_t getExistingSymbolAddress(const std::string &Name);
> Module *findModuleForSymbol(const std::string &Name,
>
> Copied: llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h (from r222801, llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h)
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h?p2=llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h&p1=llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h&r1=222801&r2=222810&rev=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h Wed Nov 26 00:53:26 2014
> @@ -1,4 +1,4 @@
> -//===---- ObjectBuffer.h - Utility class to wrap object image memory -----===//
> +//===--- ObjectBuffer.h - Utility class to wrap object memory ---*- C++ -*-===//
> //
> // The LLVM Compiler Infrastructure
> //
> @@ -21,54 +21,26 @@
>
> namespace llvm {
>
> -/// This class acts as a container for the memory buffer used during generation
> -/// and loading of executable objects using MCJIT and RuntimeDyld. The
> -/// underlying memory for the object will be owned by the ObjectBuffer instance
> -/// throughout its lifetime.
> -class ObjectBuffer {
> - virtual void anchor();
> +class ObjectMemoryBuffer : public MemoryBuffer {
> public:
> - ObjectBuffer() {}
> - ObjectBuffer(std::unique_ptr<MemoryBuffer> Buf) : Buffer(std::move(Buf)) {}
> - virtual ~ObjectBuffer() {}
> -
> - MemoryBufferRef getMemBuffer() const { return Buffer->getMemBufferRef(); }
> -
> - const char *getBufferStart() const { return Buffer->getBufferStart(); }
> - size_t getBufferSize() const { return Buffer->getBufferSize(); }
> - StringRef getBuffer() const { return Buffer->getBuffer(); }
> - StringRef getBufferIdentifier() const {
> - return Buffer->getBufferIdentifier();
> + template <unsigned N>
> + ObjectMemoryBuffer(SmallVector<char, N> SV)
> + : SV(SV), BufferName("<in-memory object>") {
> + init(this->SV.begin(), this->SV.end(), false);
> }
>
> -protected:
> - // The memory contained in an ObjectBuffer
> - std::unique_ptr<MemoryBuffer> Buffer;
> -};
> -
> -/// This class encapsulates the SmallVector and raw_svector_ostream needed to
> -/// generate an object using MC code emission while providing a common
> -/// ObjectBuffer interface for access to the memory once the object has been
> -/// generated.
> -class ObjectBufferStream : public ObjectBuffer {
> - void anchor() override;
> -public:
> - ObjectBufferStream() : OS(SV) {}
> - virtual ~ObjectBufferStream() {}
> -
> - raw_ostream &getOStream() { return OS; }
> - void flush()
> - {
> - OS.flush();
> -
> - // Make the data accessible via the ObjectBuffer::Buffer
> - Buffer =
> - MemoryBuffer::getMemBuffer(StringRef(SV.data(), SV.size()), "", false);
> + template <unsigned N>
> + ObjectMemoryBuffer(SmallVector<char, N> SV, StringRef Name)
> + : SV(SV), BufferName(Name) {
> + init(this->SV.begin(), this->SV.end(), false);
> }
> + const char* getBufferIdentifier() const override { return BufferName.c_str(); }
> +
> + BufferKind getBufferKind() const override { return MemoryBuffer_Malloc; }
>
> -protected:
> - SmallVector<char, 4096> SV; // Working buffer into which we JIT.
> - raw_svector_ostream OS; // streaming wrapper
> +private:
> + SmallVector<char, 4096> SV;
> + std::string BufferName;
> };
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp Wed Nov 26 00:53:26 2014
> @@ -18,8 +18,8 @@
> #include "llvm/IR/DebugInfo.h"
> #include "llvm/IR/Function.h"
> #include "llvm/CodeGen/MachineFunction.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/OProfileWrapper.h"
> +#include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Debug.h"
> #include "llvm/Support/raw_ostream.h"
> @@ -31,31 +31,34 @@
>
> using namespace llvm;
> using namespace llvm::jitprofiling;
> +using namespace llvm::object;
>
> #define DEBUG_TYPE "oprofile-jit-event-listener"
>
> namespace {
>
> class OProfileJITEventListener : public JITEventListener {
> - OProfileWrapper& Wrapper;
> + std::unique_ptr<OProfileWrapper> Wrapper;
>
> void initialize();
> + std::map<const char*, OwningBinary<ObjectFile>> DebugObjects;
>
> public:
> - OProfileJITEventListener(OProfileWrapper& LibraryWrapper)
> - : Wrapper(LibraryWrapper) {
> + OProfileJITEventListener(std::unique_ptr<OProfileWrapper> LibraryWrapper)
> + : Wrapper(std::move(LibraryWrapper)) {
> initialize();
> }
>
> ~OProfileJITEventListener();
>
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj);
> + void NotifyObjectEmitted(const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> - virtual void NotifyFreeingObject(const ObjectImage &Obj);
> + void NotifyFreeingObject(const ObjectFile &Obj) override;
> };
>
> void OProfileJITEventListener::initialize() {
> - if (!Wrapper.op_open_agent()) {
> + if (!Wrapper->op_open_agent()) {
> const std::string err_str = sys::StrError();
> DEBUG(dbgs() << "Failed to connect to OProfile agent: " << err_str << "\n");
> } else {
> @@ -64,8 +67,8 @@ void OProfileJITEventListener::initializ
> }
>
> OProfileJITEventListener::~OProfileJITEventListener() {
> - if (Wrapper.isAgentAvailable()) {
> - if (Wrapper.op_close_agent() == -1) {
> + if (Wrapper->isAgentAvailable()) {
> + if (Wrapper->op_close_agent() == -1) {
> const std::string err_str = sys::StrError();
> DEBUG(dbgs() << "Failed to disconnect from OProfile agent: "
> << err_str << "\n");
> @@ -75,17 +78,22 @@ OProfileJITEventListener::~OProfileJITEv
> }
> }
>
> -void OProfileJITEventListener::NotifyObjectEmitted(const ObjectImage &Obj) {
> - if (!Wrapper.isAgentAvailable()) {
> +void OProfileJITEventListener::NotifyObjectEmitted(
> + const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> + if (!Wrapper->isAgentAvailable()) {
> return;
> }
>
> + OwningBinary<ObjectFile> DebugObjOwner = L.getObjectForDebug(Obj);
> + const ObjectFile &DebugObj = *DebugObjOwner.getBinary();
> +
> // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols();
> + for (symbol_iterator I = DebugObj.symbol_begin(), E = DebugObj.symbol_end();
> I != E; ++I) {
> - object::SymbolRef::Type SymType;
> + SymbolRef::Type SymType;
> if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> + if (SymType == SymbolRef::ST_Function) {
> StringRef Name;
> uint64_t Addr;
> uint64_t Size;
> @@ -93,7 +101,7 @@ void OProfileJITEventListener::NotifyObj
> if (I->getAddress(Addr)) continue;
> if (I->getSize(Size)) continue;
>
> - if (Wrapper.op_write_native_code(Name.data(), Addr, (void*)Addr, Size)
> + if (Wrapper->op_write_native_code(Name.data(), Addr, (void*)Addr, Size)
> == -1) {
> DEBUG(dbgs() << "Failed to tell OProfile about native function "
> << Name << " at ["
> @@ -103,45 +111,48 @@ void OProfileJITEventListener::NotifyObj
> // TODO: support line number info (similar to IntelJITEventListener.cpp)
> }
> }
> -}
>
> -void OProfileJITEventListener::NotifyFreeingObject(const ObjectImage &Obj) {
> - if (!Wrapper.isAgentAvailable()) {
> - return;
> - }
> + DebugObjects[Obj.getData().data()] = std::move(DebugObjOwner);
> +}
>
> - // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols();
> - I != E; ++I) {
> - object::SymbolRef::Type SymType;
> - if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> - uint64_t Addr;
> - if (I->getAddress(Addr)) continue;
> +void OProfileJITEventListener::NotifyFreeingObject(const ObjectFile &Obj) {
> + if (Wrapper->isAgentAvailable()) {
>
> - if (Wrapper.op_unload_native_code(Addr) == -1) {
> - DEBUG(dbgs()
> - << "Failed to tell OProfile about unload of native function at "
> - << (void*)Addr << "\n");
> - continue;
> + // If there was no agent registered when the original object was loaded then
> + // we won't have created a debug object for it, so bail out.
> + if (DebugObjects.find(Obj.getData().data()) == DebugObjects.end())
> + return;
> +
> + const ObjectFile &DebugObj = *DebugObjects[Obj.getData().data()].getBinary();
> +
> + // Use symbol info to iterate functions in the object.
> + for (symbol_iterator I = DebugObj.symbol_begin(),
> + E = DebugObj.symbol_end();
> + I != E; ++I) {
> + SymbolRef::Type SymType;
> + if (I->getType(SymType)) continue;
> + if (SymType == SymbolRef::ST_Function) {
> + uint64_t Addr;
> + if (I->getAddress(Addr)) continue;
> +
> + if (Wrapper->op_unload_native_code(Addr) == -1) {
> + DEBUG(dbgs()
> + << "Failed to tell OProfile about unload of native function at "
> + << (void*)Addr << "\n");
> + continue;
> + }
> }
> }
> }
> +
> + DebugObjects.erase(Obj.getData().data());
> }
>
> } // anonymous namespace.
>
> namespace llvm {
> JITEventListener *JITEventListener::createOProfileJITEventListener() {
> - static std::unique_ptr<OProfileWrapper> JITProfilingWrapper(
> - new OProfileWrapper);
> - return new OProfileJITEventListener(*JITProfilingWrapper);
> -}
> -
> -// for testing
> -JITEventListener *JITEventListener::createOProfileJITEventListener(
> - OProfileWrapper* TestImpl) {
> - return new OProfileJITEventListener(*TestImpl);
> + return new OProfileJITEventListener(llvm::make_unique<OProfileWrapper>());
> }
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt Wed Nov 26 00:53:26 2014
> @@ -1,5 +1,5 @@
> add_llvm_library(LLVMRuntimeDyld
> - GDBRegistrar.cpp
> + GDBRegistrationListener.cpp
> RuntimeDyld.cpp
> RuntimeDyldChecker.cpp
> RuntimeDyldELF.cpp
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (removed)
> @@ -1,213 +0,0 @@
> -//===-- GDBRegistrar.cpp - Registers objects with GDB ---------------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#include "JITRegistrar.h"
> -#include "llvm/ADT/DenseMap.h"
> -#include "llvm/Support/Compiler.h"
> -#include "llvm/Support/ErrorHandling.h"
> -#include "llvm/Support/Mutex.h"
> -#include "llvm/Support/MutexGuard.h"
> -#include "llvm/Support/ManagedStatic.h"
> -
> -using namespace llvm;
> -
> -// This must be kept in sync with gdb/gdb/jit.h .
> -extern "C" {
> -
> - typedef enum {
> - JIT_NOACTION = 0,
> - JIT_REGISTER_FN,
> - JIT_UNREGISTER_FN
> - } jit_actions_t;
> -
> - struct jit_code_entry {
> - struct jit_code_entry *next_entry;
> - struct jit_code_entry *prev_entry;
> - const char *symfile_addr;
> - uint64_t symfile_size;
> - };
> -
> - struct jit_descriptor {
> - uint32_t version;
> - // This should be jit_actions_t, but we want to be specific about the
> - // bit-width.
> - uint32_t action_flag;
> - struct jit_code_entry *relevant_entry;
> - struct jit_code_entry *first_entry;
> - };
> -
> - // We put information about the JITed function in this global, which the
> - // debugger reads. Make sure to specify the version statically, because the
> - // debugger checks the version before we can set it during runtime.
> - struct jit_descriptor __jit_debug_descriptor = { 1, 0, nullptr, nullptr };
> -
> - // Debuggers puts a breakpoint in this function.
> - LLVM_ATTRIBUTE_NOINLINE void __jit_debug_register_code() {
> - // The noinline and the asm prevent calls to this function from being
> - // optimized out.
> -#if !defined(_MSC_VER)
> - asm volatile("":::"memory");
> -#endif
> - }
> -
> -}
> -
> -namespace {
> -
> -// Buffer for an in-memory object file in executable memory
> -typedef llvm::DenseMap< const char*,
> - std::pair<std::size_t, jit_code_entry*> >
> - RegisteredObjectBufferMap;
> -
> -/// Global access point for the JIT debugging interface designed for use with a
> -/// singleton toolbox. Handles thread-safe registration and deregistration of
> -/// object files that are in executable memory managed by the client of this
> -/// class.
> -class GDBJITRegistrar : public JITRegistrar {
> - /// A map of in-memory object files that have been registered with the
> - /// JIT interface.
> - RegisteredObjectBufferMap ObjectBufferMap;
> -
> -public:
> - /// Instantiates the JIT service.
> - GDBJITRegistrar() : ObjectBufferMap() {}
> -
> - /// Unregisters each object that was previously registered and releases all
> - /// internal resources.
> - virtual ~GDBJITRegistrar();
> -
> - /// Creates an entry in the JIT registry for the buffer @p Object,
> - /// which must contain an object file in executable memory with any
> - /// debug information for the debugger.
> - void registerObject(const ObjectBuffer &Object) override;
> -
> - /// Removes the internal registration of @p Object, and
> - /// frees associated resources.
> - /// Returns true if @p Object was found in ObjectBufferMap.
> - bool deregisterObject(const ObjectBuffer &Object) override;
> -
> -private:
> - /// Deregister the debug info for the given object file from the debugger
> - /// and delete any temporary copies. This private method does not remove
> - /// the function from Map so that it can be called while iterating over Map.
> - void deregisterObjectInternal(RegisteredObjectBufferMap::iterator I);
> -};
> -
> -/// Lock used to serialize all jit registration events, since they
> -/// modify global variables.
> -ManagedStatic<sys::Mutex> JITDebugLock;
> -
> -/// Do the registration.
> -void NotifyDebugger(jit_code_entry* JITCodeEntry) {
> - __jit_debug_descriptor.action_flag = JIT_REGISTER_FN;
> -
> - // Insert this entry at the head of the list.
> - JITCodeEntry->prev_entry = nullptr;
> - jit_code_entry* NextEntry = __jit_debug_descriptor.first_entry;
> - JITCodeEntry->next_entry = NextEntry;
> - if (NextEntry) {
> - NextEntry->prev_entry = JITCodeEntry;
> - }
> - __jit_debug_descriptor.first_entry = JITCodeEntry;
> - __jit_debug_descriptor.relevant_entry = JITCodeEntry;
> - __jit_debug_register_code();
> -}
> -
> -GDBJITRegistrar::~GDBJITRegistrar() {
> - // Free all registered object files.
> - llvm::MutexGuard locked(*JITDebugLock);
> - for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(), E = ObjectBufferMap.end();
> - I != E; ++I) {
> - // Call the private method that doesn't update the map so our iterator
> - // doesn't break.
> - deregisterObjectInternal(I);
> - }
> - ObjectBufferMap.clear();
> -}
> -
> -void GDBJITRegistrar::registerObject(const ObjectBuffer &Object) {
> -
> - const char *Buffer = Object.getBufferStart();
> - size_t Size = Object.getBufferSize();
> -
> - assert(Buffer && "Attempt to register a null object with a debugger.");
> - llvm::MutexGuard locked(*JITDebugLock);
> - assert(ObjectBufferMap.find(Buffer) == ObjectBufferMap.end() &&
> - "Second attempt to perform debug registration.");
> - jit_code_entry* JITCodeEntry = new jit_code_entry();
> -
> - if (!JITCodeEntry) {
> - llvm::report_fatal_error(
> - "Allocation failed when registering a JIT entry!\n");
> - } else {
> - JITCodeEntry->symfile_addr = Buffer;
> - JITCodeEntry->symfile_size = Size;
> -
> - ObjectBufferMap[Buffer] = std::make_pair(Size, JITCodeEntry);
> - NotifyDebugger(JITCodeEntry);
> - }
> -}
> -
> -bool GDBJITRegistrar::deregisterObject(const ObjectBuffer& Object) {
> - const char *Buffer = Object.getBufferStart();
> - llvm::MutexGuard locked(*JITDebugLock);
> - RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Buffer);
> -
> - if (I != ObjectBufferMap.end()) {
> - deregisterObjectInternal(I);
> - ObjectBufferMap.erase(I);
> - return true;
> - }
> - return false;
> -}
> -
> -void GDBJITRegistrar::deregisterObjectInternal(
> - RegisteredObjectBufferMap::iterator I) {
> -
> - jit_code_entry*& JITCodeEntry = I->second.second;
> -
> - // Do the unregistration.
> - {
> - __jit_debug_descriptor.action_flag = JIT_UNREGISTER_FN;
> -
> - // Remove the jit_code_entry from the linked list.
> - jit_code_entry* PrevEntry = JITCodeEntry->prev_entry;
> - jit_code_entry* NextEntry = JITCodeEntry->next_entry;
> -
> - if (NextEntry) {
> - NextEntry->prev_entry = PrevEntry;
> - }
> - if (PrevEntry) {
> - PrevEntry->next_entry = NextEntry;
> - }
> - else {
> - assert(__jit_debug_descriptor.first_entry == JITCodeEntry);
> - __jit_debug_descriptor.first_entry = NextEntry;
> - }
> -
> - // Tell the debugger which entry we removed, and unregister the code.
> - __jit_debug_descriptor.relevant_entry = JITCodeEntry;
> - __jit_debug_register_code();
> - }
> -
> - delete JITCodeEntry;
> - JITCodeEntry = nullptr;
> -}
> -
> -llvm::ManagedStatic<GDBJITRegistrar> TheRegistrar;
> -
> -} // end namespace
> -
> -namespace llvm {
> -
> -JITRegistrar& JITRegistrar::getGDBRegistrar() {
> - return *TheRegistrar;
> -}
> -
> -} // namespace llvm
>
> Copied: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp (from r222764, llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp)
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp?p2=llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp&p1=llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp&r1=222764&r2=222810&rev=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp Wed Nov 26 00:53:26 2014
> @@ -1,4 +1,4 @@
> -//===-- GDBRegistrar.cpp - Registers objects with GDB ---------------------===//
> +//===----- GDBRegistrationListener.cpp - Registers objects with GDB -------===//
> //
> // The LLVM Compiler Infrastructure
> //
> @@ -7,8 +7,9 @@
> //
> //===----------------------------------------------------------------------===//
>
> -#include "JITRegistrar.h"
> #include "llvm/ADT/DenseMap.h"
> +#include "llvm/ExecutionEngine/JITEventListener.h"
> +#include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Compiler.h"
> #include "llvm/Support/ErrorHandling.h"
> #include "llvm/Support/Mutex.h"
> @@ -16,6 +17,7 @@
> #include "llvm/Support/ManagedStatic.h"
>
> using namespace llvm;
> +using namespace llvm::object;
>
> // This must be kept in sync with gdb/gdb/jit.h .
> extern "C" {
> @@ -60,37 +62,49 @@ extern "C" {
>
> namespace {
>
> +struct RegisteredObjectInfo {
> + RegisteredObjectInfo() {}
> +
> + RegisteredObjectInfo(std::size_t Size, jit_code_entry *Entry,
> + OwningBinary<ObjectFile> Obj)
> + : Size(Size), Entry(Entry), Obj(std::move(Obj)) {}
> +
> + std::size_t Size;
> + jit_code_entry *Entry;
> + OwningBinary<ObjectFile> Obj;
> +};
> +
> // Buffer for an in-memory object file in executable memory
> -typedef llvm::DenseMap< const char*,
> - std::pair<std::size_t, jit_code_entry*> >
> +typedef llvm::DenseMap< const char*, RegisteredObjectInfo>
> RegisteredObjectBufferMap;
>
> /// Global access point for the JIT debugging interface designed for use with a
> /// singleton toolbox. Handles thread-safe registration and deregistration of
> /// object files that are in executable memory managed by the client of this
> /// class.
> -class GDBJITRegistrar : public JITRegistrar {
> +class GDBJITRegistrationListener : public JITEventListener {
> /// A map of in-memory object files that have been registered with the
> /// JIT interface.
> RegisteredObjectBufferMap ObjectBufferMap;
>
> public:
> /// Instantiates the JIT service.
> - GDBJITRegistrar() : ObjectBufferMap() {}
> + GDBJITRegistrationListener() : ObjectBufferMap() {}
>
> /// Unregisters each object that was previously registered and releases all
> /// internal resources.
> - virtual ~GDBJITRegistrar();
> + virtual ~GDBJITRegistrationListener();
>
> /// Creates an entry in the JIT registry for the buffer @p Object,
> /// which must contain an object file in executable memory with any
> /// debug information for the debugger.
> - void registerObject(const ObjectBuffer &Object) override;
> + void NotifyObjectEmitted(const ObjectFile &Object,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> /// Removes the internal registration of @p Object, and
> /// frees associated resources.
> /// Returns true if @p Object was found in ObjectBufferMap.
> - bool deregisterObject(const ObjectBuffer &Object) override;
> + void NotifyFreeingObject(const ObjectFile &Object) override;
>
> private:
> /// Deregister the debug info for the given object file from the debugger
> @@ -119,10 +133,11 @@ void NotifyDebugger(jit_code_entry* JITC
> __jit_debug_register_code();
> }
>
> -GDBJITRegistrar::~GDBJITRegistrar() {
> +GDBJITRegistrationListener::~GDBJITRegistrationListener() {
> // Free all registered object files.
> llvm::MutexGuard locked(*JITDebugLock);
> - for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(), E = ObjectBufferMap.end();
> + for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(),
> + E = ObjectBufferMap.end();
> I != E; ++I) {
> // Call the private method that doesn't update the map so our iterator
> // doesn't break.
> @@ -131,14 +146,19 @@ GDBJITRegistrar::~GDBJITRegistrar() {
> ObjectBufferMap.clear();
> }
>
> -void GDBJITRegistrar::registerObject(const ObjectBuffer &Object) {
> +void GDBJITRegistrationListener::NotifyObjectEmitted(
> + const ObjectFile &Object,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> +
> + OwningBinary<ObjectFile> DebugObj = L.getObjectForDebug(Object);
> + const char *Buffer = DebugObj.getBinary()->getMemoryBufferRef().getBufferStart();
> + size_t Size = DebugObj.getBinary()->getMemoryBufferRef().getBufferSize();
>
> - const char *Buffer = Object.getBufferStart();
> - size_t Size = Object.getBufferSize();
> + const char *Key = Object.getMemoryBufferRef().getBufferStart();
>
> - assert(Buffer && "Attempt to register a null object with a debugger.");
> + assert(Key && "Attempt to register a null object with a debugger.");
> llvm::MutexGuard locked(*JITDebugLock);
> - assert(ObjectBufferMap.find(Buffer) == ObjectBufferMap.end() &&
> + assert(ObjectBufferMap.find(Key) == ObjectBufferMap.end() &&
> "Second attempt to perform debug registration.");
> jit_code_entry* JITCodeEntry = new jit_code_entry();
>
> @@ -149,28 +169,27 @@ void GDBJITRegistrar::registerObject(con
> JITCodeEntry->symfile_addr = Buffer;
> JITCodeEntry->symfile_size = Size;
>
> - ObjectBufferMap[Buffer] = std::make_pair(Size, JITCodeEntry);
> + ObjectBufferMap[Key] = RegisteredObjectInfo(Size, JITCodeEntry,
> + std::move(DebugObj));
This broke the build with MSVC -- it turns out that MSVC is attempting
to copy the RegisteredObjectInfo object into the DenseMap, which
triggers a use of the deleted unique_ptr::operator= (implicitly
created for OwningBinary).
http://bb.pgr.jp/builders/ninja-clang-i686-msc17-R/builds/11753/steps/build_llvm/logs/stdio
~Aaron
> NotifyDebugger(JITCodeEntry);
> }
> }
>
> -bool GDBJITRegistrar::deregisterObject(const ObjectBuffer& Object) {
> - const char *Buffer = Object.getBufferStart();
> +void GDBJITRegistrationListener::NotifyFreeingObject(const ObjectFile& Object) {
> + const char *Key = Object.getMemoryBufferRef().getBufferStart();
> llvm::MutexGuard locked(*JITDebugLock);
> - RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Buffer);
> + RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Key);
>
> if (I != ObjectBufferMap.end()) {
> deregisterObjectInternal(I);
> ObjectBufferMap.erase(I);
> - return true;
> }
> - return false;
> }
>
> -void GDBJITRegistrar::deregisterObjectInternal(
> +void GDBJITRegistrationListener::deregisterObjectInternal(
> RegisteredObjectBufferMap::iterator I) {
>
> - jit_code_entry*& JITCodeEntry = I->second.second;
> + jit_code_entry*& JITCodeEntry = I->second.Entry;
>
> // Do the unregistration.
> {
> @@ -200,14 +219,14 @@ void GDBJITRegistrar::deregisterObjectIn
> JITCodeEntry = nullptr;
> }
>
> -llvm::ManagedStatic<GDBJITRegistrar> TheRegistrar;
> +llvm::ManagedStatic<GDBJITRegistrationListener> GDBRegListener;
>
> } // end namespace
>
> namespace llvm {
>
> -JITRegistrar& JITRegistrar::getGDBRegistrar() {
> - return *TheRegistrar;
> +JITEventListener* JITEventListener::createGDBRegistrationListener() {
> + return &*GDBRegListener;
> }
>
> } // namespace llvm
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h (removed)
> @@ -1,44 +0,0 @@
> -//===-- JITRegistrar.h - Registers objects with a debugger ----------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_JITREGISTRAR_H
> -#define LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_JITREGISTRAR_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -
> -namespace llvm {
> -
> -/// Global access point for the JIT debugging interface.
> -class JITRegistrar {
> - virtual void anchor();
> -public:
> - /// Instantiates the JIT service.
> - JITRegistrar() {}
> -
> - /// Unregisters each object that was previously registered and releases all
> - /// internal resources.
> - virtual ~JITRegistrar() {}
> -
> - /// Creates an entry in the JIT registry for the buffer @p Object,
> - /// which must contain an object file in executable memory with any
> - /// debug information for the debugger.
> - virtual void registerObject(const ObjectBuffer &Object) = 0;
> -
> - /// Removes the internal registration of @p Object, and
> - /// frees associated resources.
> - /// Returns true if @p Object was previously registered.
> - virtual bool deregisterObject(const ObjectBuffer &Object) = 0;
> -
> - /// Returns a reference to a GDB JIT registrar singleton
> - static JITRegistrar& getGDBRegistrar();
> -};
> -
> -} // end namespace llvm
> -
> -#endif
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h (removed)
> @@ -1,86 +0,0 @@
> -//===-- ObjectImageCommon.h - Format independent executuable object image -===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a file format independent ObjectImage class.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_OBJECTIMAGECOMMON_H
> -#define LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_OBJECTIMAGECOMMON_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> -#include "llvm/Object/ObjectFile.h"
> -
> -#include <memory>
> -
> -namespace llvm {
> -
> -namespace object {
> - class ObjectFile;
> -}
> -
> -class ObjectImageCommon : public ObjectImage {
> - ObjectImageCommon(); // = delete
> - ObjectImageCommon(const ObjectImageCommon &other); // = delete
> - void anchor() override;
> -
> -protected:
> - std::unique_ptr<object::ObjectFile> ObjFile;
> -
> - // This form of the constructor allows subclasses to use
> - // format-specific subclasses of ObjectFile directly
> - ObjectImageCommon(std::unique_ptr<ObjectBuffer> Input,
> - std::unique_ptr<object::ObjectFile> Obj)
> - : ObjectImage(std::move(Input)), ObjFile(std::move(Obj)) {}
> -
> -public:
> - ObjectImageCommon(std::unique_ptr<ObjectBuffer> Input)
> - : ObjectImage(std::move(Input)) {
> - // FIXME: error checking? createObjectFile returns an ErrorOr<ObjectFile*>
> - // and should probably be checked for failure.
> - MemoryBufferRef Buf = Buffer->getMemBuffer();
> - ObjFile = std::move(object::ObjectFile::createObjectFile(Buf).get());
> - }
> - ObjectImageCommon(std::unique_ptr<object::ObjectFile> Input)
> - : ObjectImage(nullptr), ObjFile(std::move(Input)) {}
> - virtual ~ObjectImageCommon() { }
> -
> - object::symbol_iterator begin_symbols() const override
> - { return ObjFile->symbol_begin(); }
> - object::symbol_iterator end_symbols() const override
> - { return ObjFile->symbol_end(); }
> -
> - object::section_iterator begin_sections() const override
> - { return ObjFile->section_begin(); }
> - object::section_iterator end_sections() const override
> - { return ObjFile->section_end(); }
> -
> - /* Triple::ArchType */ unsigned getArch() const override
> - { return ObjFile->getArch(); }
> -
> - StringRef getData() const override { return ObjFile->getData(); }
> -
> - object::ObjectFile* getObjectFile() const override { return ObjFile.get(); }
> -
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - void updateSectionAddress(const object::SectionRef &Sec,
> - uint64_t Addr) override {}
> - void updateSymbolAddress(const object::SymbolRef &Sym,
> - uint64_t Addr) override {}
> -
> - // Subclasses can override these methods to provide JIT debugging support
> - void registerWithDebugger() override {}
> - void deregisterWithDebugger() override {}
> -};
> -
> -} // end namespace llvm
> -
> -#endif
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp Wed Nov 26 00:53:26 2014
> @@ -12,8 +12,6 @@
> //===----------------------------------------------------------------------===//
>
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> -#include "JITRegistrar.h"
> -#include "ObjectImageCommon.h"
> #include "RuntimeDyldCheckerImpl.h"
> #include "RuntimeDyldELF.h"
> #include "RuntimeDyldImpl.h"
> @@ -30,10 +28,8 @@ using namespace llvm::object;
> // Empty out-of-line virtual destructor as the key function.
> RuntimeDyldImpl::~RuntimeDyldImpl() {}
>
> -// Pin the JITRegistrar's and ObjectImage*'s vtables to this file.
> -void JITRegistrar::anchor() {}
> -void ObjectImage::anchor() {}
> -void ObjectImageCommon::anchor() {}
> +// Pin LoadedObjectInfo's vtables to this file.
> +void RuntimeDyld::LoadedObjectInfo::anchor() {}
>
> namespace llvm {
>
> @@ -139,22 +135,23 @@ static std::error_code getOffset(const S
> return object_error::success;
> }
>
> -std::unique_ptr<ObjectImage>
> -RuntimeDyldImpl::loadObject(std::unique_ptr<ObjectImage> Obj) {
> +std::pair<unsigned, unsigned>
> +RuntimeDyldImpl::loadObjectImpl(const object::ObjectFile &Obj) {
> MutexGuard locked(lock);
>
> - if (!Obj)
> - return nullptr;
> + // Grab the first Section ID. We'll use this later to construct the underlying
> + // range for the returned LoadedObjectInfo.
> + unsigned SectionsAddedBeginIdx = Sections.size();
>
> // Save information about our target
> - Arch = (Triple::ArchType)Obj->getArch();
> - IsTargetLittleEndian = Obj->getObjectFile()->isLittleEndian();
> + Arch = (Triple::ArchType)Obj.getArch();
> + IsTargetLittleEndian = Obj.isLittleEndian();
>
> // Compute the memory size required to load all sections to be loaded
> // and pass this information to the memory manager
> if (MemMgr->needsToReserveAllocationSpace()) {
> uint64_t CodeSize = 0, DataSizeRO = 0, DataSizeRW = 0;
> - computeTotalAllocSize(*Obj, CodeSize, DataSizeRO, DataSizeRW);
> + computeTotalAllocSize(Obj, CodeSize, DataSizeRO, DataSizeRW);
> MemMgr->reserveAllocationSpace(CodeSize, DataSizeRO, DataSizeRW);
> }
>
> @@ -170,7 +167,7 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> // Parse symbols
> DEBUG(dbgs() << "Parse symbols:\n");
> - for (symbol_iterator I = Obj->begin_symbols(), E = Obj->end_symbols(); I != E;
> + for (symbol_iterator I = Obj.symbol_begin(), E = Obj.symbol_end(); I != E;
> ++I) {
> object::SymbolRef::Type SymType;
> StringRef Name;
> @@ -196,15 +193,15 @@ RuntimeDyldImpl::loadObject(std::unique_
> SymType == object::SymbolRef::ST_Unknown) {
> uint64_t SectOffset;
> StringRef SectionData;
> - section_iterator SI = Obj->end_sections();
> + section_iterator SI = Obj.section_end();
> Check(getOffset(*I, SectOffset));
> Check(I->getSection(SI));
> - if (SI == Obj->end_sections())
> + if (SI == Obj.section_end())
> continue;
> Check(SI->getContents(SectionData));
> bool IsCode = SI->isText();
> unsigned SectionID =
> - findOrEmitSection(*Obj, *SI, IsCode, LocalSections);
> + findOrEmitSection(Obj, *SI, IsCode, LocalSections);
> LocalSymbols[Name.data()] = SymbolLoc(SectionID, SectOffset);
> DEBUG(dbgs() << "\tOffset: " << format("%p", (uintptr_t)SectOffset)
> << " flags: " << Flags << " SID: " << SectionID);
> @@ -216,11 +213,11 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> // Allocate common symbols
> if (CommonSize != 0)
> - emitCommonSymbols(*Obj, CommonSymbols, CommonSize, GlobalSymbolTable);
> + emitCommonSymbols(Obj, CommonSymbols, CommonSize, GlobalSymbolTable);
>
> // Parse and process relocations
> DEBUG(dbgs() << "Parse relocations:\n");
> - for (section_iterator SI = Obj->begin_sections(), SE = Obj->end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> unsigned SectionID = 0;
> StubMap Stubs;
> @@ -234,23 +231,25 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> bool IsCode = RelocatedSection->isText();
> SectionID =
> - findOrEmitSection(*Obj, *RelocatedSection, IsCode, LocalSections);
> + findOrEmitSection(Obj, *RelocatedSection, IsCode, LocalSections);
> DEBUG(dbgs() << "\tSectionID: " << SectionID << "\n");
>
> for (; I != E;)
> - I = processRelocationRef(SectionID, I, *Obj, LocalSections, LocalSymbols,
> + I = processRelocationRef(SectionID, I, Obj, LocalSections, LocalSymbols,
> Stubs);
>
> // If there is an attached checker, notify it about the stubs for this
> // section so that they can be verified.
> if (Checker)
> - Checker->registerStubMap(Obj->getImageName(), SectionID, Stubs);
> + Checker->registerStubMap(Obj.getFileName(), SectionID, Stubs);
> }
>
> // Give the subclasses a chance to tie-up any loose ends.
> - finalizeLoad(*Obj, LocalSections);
> + finalizeLoad(Obj, LocalSections);
>
> - return Obj;
> + unsigned SectionsAddedEndIdx = Sections.size();
> +
> + return std::make_pair(SectionsAddedBeginIdx, SectionsAddedEndIdx);
> }
>
> // A helper method for computeTotalAllocSize.
> @@ -270,7 +269,7 @@ computeAllocationSizeForSections(std::ve
>
> // Compute an upper bound of the memory size that is required to load all
> // sections
> -void RuntimeDyldImpl::computeTotalAllocSize(ObjectImage &Obj,
> +void RuntimeDyldImpl::computeTotalAllocSize(const ObjectFile &Obj,
> uint64_t &CodeSize,
> uint64_t &DataSizeRO,
> uint64_t &DataSizeRW) {
> @@ -282,7 +281,7 @@ void RuntimeDyldImpl::computeTotalAllocS
>
> // Collect sizes of all sections to be loaded;
> // also determine the max alignment of all sections
> - for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> const SectionRef &Section = *SI;
>
> @@ -328,7 +327,7 @@ void RuntimeDyldImpl::computeTotalAllocS
>
> // Compute the size of all common symbols
> uint64_t CommonSize = 0;
> - for (symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols(); I != E;
> + for (symbol_iterator I = Obj.symbol_begin(), E = Obj.symbol_end(); I != E;
> ++I) {
> uint32_t Flags = I->getFlags();
> if (Flags & SymbolRef::SF_Common) {
> @@ -353,7 +352,7 @@ void RuntimeDyldImpl::computeTotalAllocS
> }
>
> // compute stub buffer size for the given section
> -unsigned RuntimeDyldImpl::computeSectionStubBufSize(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::computeSectionStubBufSize(const ObjectFile &Obj,
> const SectionRef &Section) {
> unsigned StubSize = getMaxStubSize();
> if (StubSize == 0) {
> @@ -363,7 +362,7 @@ unsigned RuntimeDyldImpl::computeSection
> // necessary section allocation size in loadObject by walking all the sections
> // once.
> unsigned StubBufSize = 0;
> - for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> section_iterator RelSecI = SI->getRelocatedSection();
> if (!(RelSecI == Section))
> @@ -418,7 +417,7 @@ void RuntimeDyldImpl::writeBytesUnaligne
> }
> }
>
> -void RuntimeDyldImpl::emitCommonSymbols(ObjectImage &Obj,
> +void RuntimeDyldImpl::emitCommonSymbols(const ObjectFile &Obj,
> const CommonSymbolMap &CommonSymbols,
> uint64_t TotalSize,
> SymbolTableMap &SymbolTable) {
> @@ -450,14 +449,13 @@ void RuntimeDyldImpl::emitCommonSymbols(
> DEBUG(dbgs() << "Allocating common symbol " << Name << " address "
> << format("%p\n", Addr));
> }
> - Obj.updateSymbolAddress(it->first, (uint64_t)Addr);
> SymbolTable[Name.data()] = SymbolLoc(SectionID, Offset);
> Offset += Size;
> Addr += Size;
> }
> }
>
> -unsigned RuntimeDyldImpl::emitSection(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::emitSection(const ObjectFile &Obj,
> const SectionRef &Section, bool IsCode) {
>
> StringRef data;
> @@ -521,7 +519,6 @@ unsigned RuntimeDyldImpl::emitSection(Ob
> << " new addr: " << format("%p", Addr)
> << " DataSize: " << DataSize << " StubBufSize: " << StubBufSize
> << " Allocate: " << Allocate << "\n");
> - Obj.updateSectionAddress(Section, (uint64_t)Addr);
> } else {
> // Even if we didn't load the section, we need to record an entry for it
> // to handle later processing (and by 'handle' I mean don't do anything
> @@ -537,12 +534,12 @@ unsigned RuntimeDyldImpl::emitSection(Ob
> Sections.push_back(SectionEntry(Name, Addr, DataSize, (uintptr_t)pData));
>
> if (Checker)
> - Checker->registerSection(Obj.getImageName(), SectionID);
> + Checker->registerSection(Obj.getFileName(), SectionID);
>
> return SectionID;
> }
>
> -unsigned RuntimeDyldImpl::findOrEmitSection(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::findOrEmitSection(const ObjectFile &Obj,
> const SectionRef &Section,
> bool IsCode,
> ObjSectionToIDMap &LocalSections) {
> @@ -739,6 +736,16 @@ void RuntimeDyldImpl::resolveExternalSym
>
> //===----------------------------------------------------------------------===//
> // RuntimeDyld class implementation
> +
> +uint64_t RuntimeDyld::LoadedObjectInfo::getSectionLoadAddress(
> + StringRef SectionName) const {
> + for (unsigned I = BeginIdx; I != EndIdx; ++I)
> + if (RTDyld.Sections[I].Name == SectionName)
> + return RTDyld.Sections[I].LoadAddress;
> +
> + return 0;
> +}
> +
> RuntimeDyld::RuntimeDyld(RTDyldMemoryManager *mm) {
> // FIXME: There's a potential issue lurking here if a single instance of
> // RuntimeDyld is used to load multiple objects. The current implementation
> @@ -772,78 +779,23 @@ createRuntimeDyldMachO(Triple::ArchType
> return Dyld;
> }
>
> -std::unique_ptr<ObjectImage>
> -RuntimeDyld::loadObject(std::unique_ptr<ObjectFile> InputObject) {
> - std::unique_ptr<ObjectImage> InputImage;
> -
> - ObjectFile &Obj = *InputObject;
> -
> - if (InputObject->isELF()) {
> - InputImage.reset(RuntimeDyldELF::createObjectImageFromFile(std::move(InputObject)));
> - if (!Dyld)
> - Dyld = createRuntimeDyldELF(MM, ProcessAllSections, Checker);
> - } else if (InputObject->isMachO()) {
> - InputImage.reset(RuntimeDyldMachO::createObjectImageFromFile(std::move(InputObject)));
> - if (!Dyld)
> - Dyld = createRuntimeDyldMachO(
> - static_cast<Triple::ArchType>(InputImage->getArch()), MM,
> - ProcessAllSections, Checker);
> - } else
> - report_fatal_error("Incompatible object format!");
> -
> - if (!Dyld->isCompatibleFile(&Obj))
> - report_fatal_error("Incompatible object format!");
> -
> - return Dyld->loadObject(std::move(InputImage));
> -}
> -
> -std::unique_ptr<ObjectImage>
> -RuntimeDyld::loadObject(std::unique_ptr<ObjectBuffer> InputBuffer) {
> - std::unique_ptr<ObjectImage> InputImage;
> - sys::fs::file_magic Type = sys::fs::identify_magic(InputBuffer->getBuffer());
> - auto *InputBufferPtr = InputBuffer.get();
> -
> - switch (Type) {
> - case sys::fs::file_magic::elf:
> - case sys::fs::file_magic::elf_relocatable:
> - case sys::fs::file_magic::elf_executable:
> - case sys::fs::file_magic::elf_shared_object:
> - case sys::fs::file_magic::elf_core:
> - InputImage = RuntimeDyldELF::createObjectImage(std::move(InputBuffer));
> - if (!Dyld)
> +std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> +RuntimeDyld::loadObject(const ObjectFile &Obj) {
> + if (!Dyld) {
> + if (Obj.isELF())
> Dyld = createRuntimeDyldELF(MM, ProcessAllSections, Checker);
> - break;
> - case sys::fs::file_magic::macho_object:
> - case sys::fs::file_magic::macho_executable:
> - case sys::fs::file_magic::macho_fixed_virtual_memory_shared_lib:
> - case sys::fs::file_magic::macho_core:
> - case sys::fs::file_magic::macho_preload_executable:
> - case sys::fs::file_magic::macho_dynamically_linked_shared_lib:
> - case sys::fs::file_magic::macho_dynamic_linker:
> - case sys::fs::file_magic::macho_bundle:
> - case sys::fs::file_magic::macho_dynamically_linked_shared_lib_stub:
> - case sys::fs::file_magic::macho_dsym_companion:
> - InputImage = RuntimeDyldMachO::createObjectImage(std::move(InputBuffer));
> - if (!Dyld)
> + else if (Obj.isMachO())
> Dyld = createRuntimeDyldMachO(
> - static_cast<Triple::ArchType>(InputImage->getArch()), MM,
> - ProcessAllSections, Checker);
> - break;
> - case sys::fs::file_magic::unknown:
> - case sys::fs::file_magic::bitcode:
> - case sys::fs::file_magic::archive:
> - case sys::fs::file_magic::coff_object:
> - case sys::fs::file_magic::coff_import_library:
> - case sys::fs::file_magic::pecoff_executable:
> - case sys::fs::file_magic::macho_universal_binary:
> - case sys::fs::file_magic::windows_resource:
> - report_fatal_error("Incompatible object format!");
> + static_cast<Triple::ArchType>(Obj.getArch()), MM,
> + ProcessAllSections, Checker);
> + else
> + report_fatal_error("Incompatible object format!");
> }
>
> - if (!Dyld->isCompatibleFormat(InputBufferPtr))
> + if (!Dyld->isCompatibleFile(Obj))
> report_fatal_error("Incompatible object format!");
>
> - return Dyld->loadObject(std::move(InputImage));
> + return Dyld->loadObject(Obj);
> }
>
> void *RuntimeDyld::getSymbolAddress(StringRef Name) const {
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp Wed Nov 26 00:53:26 2014
> @@ -12,27 +12,23 @@
> //===----------------------------------------------------------------------===//
>
> #include "RuntimeDyldELF.h"
> -#include "JITRegistrar.h"
> -#include "ObjectImageCommon.h"
> #include "llvm/ADT/IntervalMap.h"
> #include "llvm/ADT/STLExtras.h"
> #include "llvm/ADT/StringRef.h"
> #include "llvm/ADT/Triple.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> +#include "llvm/MC/MCStreamer.h"
> #include "llvm/Object/ELFObjectFile.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/ELF.h"
> #include "llvm/Support/Endian.h"
> #include "llvm/Support/MemoryBuffer.h"
> +#include "llvm/Support/TargetRegistry.h"
>
> using namespace llvm;
> using namespace llvm::object;
>
> #define DEBUG_TYPE "dyld"
>
> -namespace {
> -
> static inline std::error_code check(std::error_code Err) {
> if (Err) {
> report_fatal_error(Err.message());
> @@ -40,6 +36,8 @@ static inline std::error_code check(std:
> return Err;
> }
>
> +namespace {
> +
> template <class ELFT> class DyldELFObject : public ELFObjectFile<ELFT> {
> LLVM_ELF_IMPORT_TYPES_ELFT(ELFT)
>
> @@ -52,16 +50,12 @@ template <class ELFT> class DyldELFObjec
>
> typedef typename ELFDataTypeTypedefHelper<ELFT>::value_type addr_type;
>
> - std::unique_ptr<ObjectFile> UnderlyingFile;
> -
> public:
> - DyldELFObject(std::unique_ptr<ObjectFile> UnderlyingFile,
> - MemoryBufferRef Wrapper, std::error_code &ec);
> -
> DyldELFObject(MemoryBufferRef Wrapper, std::error_code &ec);
>
> void updateSectionAddress(const SectionRef &Sec, uint64_t Addr);
> - void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr);
> +
> + void updateSymbolAddress(const SymbolRef &SymRef, uint64_t Addr);
>
> // Methods for type inquiry through isa, cast and dyn_cast
> static inline bool classof(const Binary *v) {
> @@ -71,42 +65,10 @@ public:
> static inline bool classof(const ELFObjectFile<ELFT> *v) {
> return v->isDyldType();
> }
> -};
> -
> -template <class ELFT> class ELFObjectImage : public ObjectImageCommon {
> - bool Registered;
>
> -public:
> - ELFObjectImage(std::unique_ptr<ObjectBuffer> Input,
> - std::unique_ptr<DyldELFObject<ELFT>> Obj)
> - : ObjectImageCommon(std::move(Input), std::move(Obj)), Registered(false) {
> - }
> -
> - virtual ~ELFObjectImage() {
> - if (Registered)
> - deregisterWithDebugger();
> - }
> +};
>
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - void updateSectionAddress(const SectionRef &Sec, uint64_t Addr) override {
> - static_cast<DyldELFObject<ELFT>*>(getObjectFile())
> - ->updateSectionAddress(Sec, Addr);
> - }
>
> - void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr) override {
> - static_cast<DyldELFObject<ELFT>*>(getObjectFile())
> - ->updateSymbolAddress(Sym, Addr);
> - }
> -
> - void registerWithDebugger() override {
> - JITRegistrar::getGDBRegistrar().registerObject(*Buffer);
> - Registered = true;
> - }
> - void deregisterWithDebugger() override {
> - JITRegistrar::getGDBRegistrar().deregisterObject(*Buffer);
> - }
> -};
>
> // The MemoryBuffer passed into this constructor is just a wrapper around the
> // actual memory. Ultimately, the Binary parent class will take ownership of
> @@ -118,14 +80,6 @@ DyldELFObject<ELFT>::DyldELFObject(Memor
> }
>
> template <class ELFT>
> -DyldELFObject<ELFT>::DyldELFObject(std::unique_ptr<ObjectFile> UnderlyingFile,
> - MemoryBufferRef Wrapper, std::error_code &EC)
> - : ELFObjectFile<ELFT>(Wrapper, EC),
> - UnderlyingFile(std::move(UnderlyingFile)) {
> - this->isDyldELFObject = true;
> -}
> -
> -template <class ELFT>
> void DyldELFObject<ELFT>::updateSectionAddress(const SectionRef &Sec,
> uint64_t Addr) {
> DataRefImpl ShdrRef = Sec.getRawDataRefImpl();
> @@ -149,10 +103,89 @@ void DyldELFObject<ELFT>::updateSymbolAd
> sym->st_value = static_cast<addr_type>(Addr);
> }
>
> +class LoadedELFObjectInfo : public RuntimeDyld::LoadedObjectInfo {
> +public:
> + LoadedELFObjectInfo(RuntimeDyldImpl &RTDyld, unsigned BeginIdx,
> + unsigned EndIdx)
> + : RuntimeDyld::LoadedObjectInfo(RTDyld, BeginIdx, EndIdx) {}
> +
> + OwningBinary<ObjectFile>
> + getObjectForDebug(const ObjectFile &Obj) const override;
> +};
> +
> +template <typename ELFT>
> +std::unique_ptr<DyldELFObject<ELFT>>
> +createRTDyldELFObject(MemoryBufferRef Buffer,
> + const LoadedELFObjectInfo &L,
> + std::error_code &ec) {
> + typedef typename ELFFile<ELFT>::Elf_Shdr Elf_Shdr;
> + typedef typename ELFDataTypeTypedefHelper<ELFT>::value_type addr_type;
> +
> + std::unique_ptr<DyldELFObject<ELFT>> Obj =
> + llvm::make_unique<DyldELFObject<ELFT>>(Buffer, ec);
> +
> + // Iterate over all sections in the object.
> + for (const auto &Sec : Obj->sections()) {
> + StringRef SectionName;
> + Sec.getName(SectionName);
> + if (SectionName != "") {
> + DataRefImpl ShdrRef = Sec.getRawDataRefImpl();
> + Elf_Shdr *shdr = const_cast<Elf_Shdr *>(
> + reinterpret_cast<const Elf_Shdr *>(ShdrRef.p));
> +
> + if (uint64_t SecLoadAddr = L.getSectionLoadAddress(SectionName)) {
> + // This assumes that the address passed in matches the target address
> + // bitness. The template-based type cast handles everything else.
> + shdr->sh_addr = static_cast<addr_type>(SecLoadAddr);
> + }
> + }
> + }
> +
> + return Obj;
> +}
> +
> +OwningBinary<ObjectFile> createELFDebugObject(const ObjectFile &Obj,
> + const LoadedELFObjectInfo &L) {
> + assert(Obj.isELF() && "Not an ELF object file.");
> +
> + std::unique_ptr<MemoryBuffer> Buffer =
> + MemoryBuffer::getMemBufferCopy(Obj.getData(), Obj.getFileName());
> +
> + std::error_code ec;
> +
> + std::unique_ptr<ObjectFile> DebugObj;
> + if (Obj.getBytesInAddress() == 4 && Obj.isLittleEndian()) {
> + typedef ELFType<support::little, 2, false> ELF32LE;
> + DebugObj = createRTDyldELFObject<ELF32LE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 4 && !Obj.isLittleEndian()) {
> + typedef ELFType<support::big, 2, false> ELF32BE;
> + DebugObj = createRTDyldELFObject<ELF32BE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 8 && !Obj.isLittleEndian()) {
> + typedef ELFType<support::big, 2, true> ELF64BE;
> + DebugObj = createRTDyldELFObject<ELF64BE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 8 && Obj.isLittleEndian()) {
> + typedef ELFType<support::little, 2, true> ELF64LE;
> + DebugObj = createRTDyldELFObject<ELF64LE>(Buffer->getMemBufferRef(), L, ec);
> + } else
> + llvm_unreachable("Unexpected ELF format");
> +
> + assert(!ec && "Could not construct copy ELF object file");
> +
> + return OwningBinary<ObjectFile>(std::move(DebugObj), std::move(Buffer));
> +}
> +
> +OwningBinary<ObjectFile>
> +LoadedELFObjectInfo::getObjectForDebug(const ObjectFile &Obj) const {
> + return createELFDebugObject(Obj, *this);
> +}
> +
> } // namespace
>
> namespace llvm {
>
> +RuntimeDyldELF::RuntimeDyldELF(RTDyldMemoryManager *mm) : RuntimeDyldImpl(mm) {}
> +RuntimeDyldELF::~RuntimeDyldELF() {}
> +
> void RuntimeDyldELF::registerEHFrames() {
> if (!MemMgr)
> return;
> @@ -180,83 +213,14 @@ void RuntimeDyldELF::deregisterEHFrames(
> RegisteredEHFrameSections.clear();
> }
>
> -ObjectImage *
> -RuntimeDyldELF::createObjectImageFromFile(std::unique_ptr<object::ObjectFile> ObjFile) {
> - if (!ObjFile)
> - return nullptr;
> -
> - std::error_code ec;
> - MemoryBufferRef Buffer = ObjFile->getMemoryBufferRef();
> -
> - if (ObjFile->getBytesInAddress() == 4 && ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 2, false>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::little, 2, false>>(
> - nullptr, std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 4 && !ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::big, 2, false>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::big, 2, false>>(nullptr, std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 8 && !ObjFile->isLittleEndian()) {
> - auto Obj = llvm::make_unique<DyldELFObject<ELFType<support::big, 2, true>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::big, 2, true>>(nullptr,
> - std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 8 && ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 2, true>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::little, 2, true>>(
> - nullptr, std::move(Obj));
> - } else
> - llvm_unreachable("Unexpected ELF format");
> -}
> -
> -std::unique_ptr<ObjectImage>
> -RuntimeDyldELF::createObjectImage(std::unique_ptr<ObjectBuffer> Buffer) {
> - if (Buffer->getBufferSize() < ELF::EI_NIDENT)
> - llvm_unreachable("Unexpected ELF object size");
> - std::pair<unsigned char, unsigned char> Ident =
> - std::make_pair((uint8_t)Buffer->getBufferStart()[ELF::EI_CLASS],
> - (uint8_t)Buffer->getBufferStart()[ELF::EI_DATA]);
> - std::error_code ec;
> -
> - MemoryBufferRef Buf = Buffer->getMemBuffer();
> -
> - if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2LSB) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 4, false>>>(
> - Buf, ec);
> - return llvm::make_unique<
> - ELFObjectImage<ELFType<support::little, 4, false>>>(std::move(Buffer),
> - std::move(Obj));
> - }
> - if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2MSB) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::big, 4, false>>>(Buf,
> - ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::big, 4, false>>>(
> - std::move(Buffer), std::move(Obj));
> - }
> - if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2MSB) {
> - auto Obj = llvm::make_unique<DyldELFObject<ELFType<support::big, 8, true>>>(
> - Buf, ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::big, 8, true>>>(
> - std::move(Buffer), std::move(Obj));
> - }
> - assert(Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2LSB &&
> - "Unexpected ELF format");
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 8, true>>>(Buf,
> - ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::little, 8, true>>>(
> - std::move(Buffer), std::move(Obj));
> +std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> +RuntimeDyldELF::loadObject(const object::ObjectFile &O) {
> + unsigned SectionStartIdx, SectionEndIdx;
> + std::tie(SectionStartIdx, SectionEndIdx) = loadObjectImpl(O);
> + return llvm::make_unique<LoadedELFObjectInfo>(*this, SectionStartIdx,
> + SectionEndIdx);
> }
>
> -RuntimeDyldELF::~RuntimeDyldELF() {}
> -
> void RuntimeDyldELF::resolveX86_64Relocation(const SectionEntry &Section,
> uint64_t Offset, uint64_t Value,
> uint32_t Type, int64_t Addend,
> @@ -615,7 +579,7 @@ void RuntimeDyldELF::resolveMIPSRelocati
> }
>
> // Return the .TOC. section and offset.
> -void RuntimeDyldELF::findPPC64TOCSection(ObjectImage &Obj,
> +void RuntimeDyldELF::findPPC64TOCSection(const ObjectFile &Obj,
> ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel) {
> // Set a default SectionID in case we do not find a TOC section below.
> @@ -628,7 +592,7 @@ void RuntimeDyldELF::findPPC64TOCSection
>
> // The TOC consists of sections .got, .toc, .tocbss, .plt in that
> // order. The TOC starts where the first of these sections starts.
> - for (section_iterator si = Obj.begin_sections(), se = Obj.end_sections();
> + for (section_iterator si = Obj.section_begin(), se = Obj.section_end();
> si != se; ++si) {
>
> StringRef SectionName;
> @@ -650,15 +614,15 @@ void RuntimeDyldELF::findPPC64TOCSection
>
> // Returns the sections and offset associated with the ODP entry referenced
> // by Symbol.
> -void RuntimeDyldELF::findOPDEntrySection(ObjectImage &Obj,
> +void RuntimeDyldELF::findOPDEntrySection(const ObjectFile &Obj,
> ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel) {
> // Get the ELF symbol value (st_value) to compare with Relocation offset in
> // .opd entries
> - for (section_iterator si = Obj.begin_sections(), se = Obj.end_sections();
> + for (section_iterator si = Obj.section_begin(), se = Obj.section_end();
> si != se; ++si) {
> section_iterator RelSecI = si->getRelocatedSection();
> - if (RelSecI == Obj.end_sections())
> + if (RelSecI == Obj.section_end())
> continue;
>
> StringRef RelSectionName;
> @@ -700,7 +664,7 @@ void RuntimeDyldELF::findOPDEntrySection
> if (Rel.Addend != (int64_t)TargetSymbolOffset)
> continue;
>
> - section_iterator tsi(Obj.end_sections());
> + section_iterator tsi(Obj.section_end());
> check(TargetSymbol->getSection(tsi));
> bool IsCode = tsi->isText();
> Rel.SectionID = findOrEmitSection(Obj, (*tsi), IsCode, LocalSections);
> @@ -935,7 +899,8 @@ void RuntimeDyldELF::resolveRelocation(c
> }
>
> relocation_iterator RuntimeDyldELF::processRelocationRef(
> - unsigned SectionID, relocation_iterator RelI, ObjectImage &Obj,
> + unsigned SectionID, relocation_iterator RelI,
> + const ObjectFile &Obj,
> ObjSectionToIDMap &ObjSectionToID, const SymbolTableMap &Symbols,
> StubMap &Stubs) {
> uint64_t RelType;
> @@ -946,7 +911,7 @@ relocation_iterator RuntimeDyldELF::proc
>
> // Obtain the symbol name which is referenced in the relocation
> StringRef TargetName;
> - if (Symbol != Obj.end_symbols())
> + if (Symbol != Obj.symbol_end())
> Symbol->getName(TargetName);
> DEBUG(dbgs() << "\t\tRelType: " << RelType << " Addend: " << Addend
> << " TargetName: " << TargetName << "\n");
> @@ -954,7 +919,7 @@ relocation_iterator RuntimeDyldELF::proc
> // First search for the symbol in the local symbol table
> SymbolTableMap::const_iterator lsi = Symbols.end();
> SymbolRef::Type SymType = SymbolRef::ST_Unknown;
> - if (Symbol != Obj.end_symbols()) {
> + if (Symbol != Obj.symbol_end()) {
> lsi = Symbols.find(TargetName.data());
> Symbol->getType(SymType);
> }
> @@ -965,7 +930,7 @@ relocation_iterator RuntimeDyldELF::proc
> } else {
> // Search for the symbol in the global symbol table
> SymbolTableMap::const_iterator gsi = GlobalSymbolTable.end();
> - if (Symbol != Obj.end_symbols())
> + if (Symbol != Obj.symbol_end())
> gsi = GlobalSymbolTable.find(TargetName.data());
> if (gsi != GlobalSymbolTable.end()) {
> Value.SectionID = gsi->second.first;
> @@ -977,9 +942,9 @@ relocation_iterator RuntimeDyldELF::proc
> // TODO: Now ELF SymbolRef::ST_Debug = STT_SECTION, it's not obviously
> // and can be changed by another developers. Maybe best way is add
> // a new symbol type ST_Section to SymbolRef and use it.
> - section_iterator si(Obj.end_sections());
> + section_iterator si(Obj.section_end());
> Symbol->getSection(si);
> - if (si == Obj.end_sections())
> + if (si == Obj.section_end())
> llvm_unreachable("Symbol section not found, bad object file format!");
> DEBUG(dbgs() << "\t\tThis is section symbol\n");
> bool isCode = si->isText();
> @@ -1135,7 +1100,7 @@ relocation_iterator RuntimeDyldELF::proc
> if (RelType == ELF::R_PPC64_REL24) {
> // Determine ABI variant in use for this object.
> unsigned AbiVariant;
> - Obj.getObjectFile()->getPlatformFlags(AbiVariant);
> + Obj.getPlatformFlags(AbiVariant);
> AbiVariant &= ELF::EF_PPC64_ABI;
> // A PPC branch relocation will need a stub function if the target is
> // an external symbol (Symbol::ST_Unknown) or if the target address
> @@ -1495,7 +1460,7 @@ uint64_t RuntimeDyldELF::findGOTEntry(ui
> return 0;
> }
>
> -void RuntimeDyldELF::finalizeLoad(ObjectImage &ObjImg,
> +void RuntimeDyldELF::finalizeLoad(const ObjectFile &Obj,
> ObjSectionToIDMap &SectionMap) {
> // If necessary, allocate the global offset table
> if (MemMgr) {
> @@ -1533,15 +1498,8 @@ void RuntimeDyldELF::finalizeLoad(Object
> }
> }
>
> -bool RuntimeDyldELF::isCompatibleFormat(const ObjectBuffer *Buffer) const {
> - if (Buffer->getBufferSize() < strlen(ELF::ElfMagic))
> - return false;
> - return (memcmp(Buffer->getBufferStart(), ELF::ElfMagic,
> - strlen(ELF::ElfMagic))) == 0;
> -}
> -
> -bool RuntimeDyldELF::isCompatibleFile(const object::ObjectFile *Obj) const {
> - return Obj->isELF();
> +bool RuntimeDyldELF::isCompatibleFile(const object::ObjectFile &Obj) const {
> + return Obj.isELF();
> }
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h Wed Nov 26 00:53:26 2014
> @@ -28,9 +28,11 @@ std::error_code Check(std::error_code Er
> }
> return Err;
> }
> +
> } // end anonymous namespace
>
> class RuntimeDyldELF : public RuntimeDyldImpl {
> +
> void resolveRelocation(const SectionEntry &Section, uint64_t Offset,
> uint64_t Value, uint32_t Type, int64_t Addend,
> uint64_t SymOffset = 0);
> @@ -81,9 +83,11 @@ class RuntimeDyldELF : public RuntimeDyl
> return 1;
> }
>
> - void findPPC64TOCSection(ObjectImage &Obj, ObjSectionToIDMap &LocalSections,
> + void findPPC64TOCSection(const ObjectFile &Obj,
> + ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel);
> - void findOPDEntrySection(ObjectImage &Obj, ObjSectionToIDMap &LocalSections,
> + void findOPDEntrySection(const ObjectFile &Obj,
> + ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel);
>
> uint64_t findGOTEntry(uint64_t LoadAddr, uint64_t Offset);
> @@ -104,24 +108,23 @@ class RuntimeDyldELF : public RuntimeDyl
> SmallVector<SID, 2> RegisteredEHFrameSections;
>
> public:
> - RuntimeDyldELF(RTDyldMemoryManager *mm) : RuntimeDyldImpl(mm) {}
> + RuntimeDyldELF(RTDyldMemoryManager *mm);
> + virtual ~RuntimeDyldELF();
> +
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> + loadObject(const object::ObjectFile &O) override;
>
> void resolveRelocation(const RelocationEntry &RE, uint64_t Value) override;
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &Obj, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &Obj,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override;
> - bool isCompatibleFormat(const ObjectBuffer *Buffer) const override;
> - bool isCompatibleFile(const object::ObjectFile *Buffer) const override;
> + bool isCompatibleFile(const object::ObjectFile &Obj) const override;
> void registerEHFrames() override;
> void deregisterEHFrames() override;
> - void finalizeLoad(ObjectImage &ObjImg,
> + void finalizeLoad(const ObjectFile &Obj,
> ObjSectionToIDMap &SectionMap) override;
> - virtual ~RuntimeDyldELF();
> -
> - static std::unique_ptr<ObjectImage>
> - createObjectImage(std::unique_ptr<ObjectBuffer> InputBuffer);
> - static ObjectImage *createObjectImageFromFile(std::unique_ptr<object::ObjectFile> Obj);
> };
>
> } // end namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h Wed Nov 26 00:53:26 2014
> @@ -18,7 +18,6 @@
> #include "llvm/ADT/SmallVector.h"
> #include "llvm/ADT/StringMap.h"
> #include "llvm/ADT/Triple.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/ExecutionEngine/RuntimeDyldChecker.h"
> #include "llvm/Object/ObjectFile.h"
> @@ -37,7 +36,6 @@ using namespace llvm::object;
>
> namespace llvm {
>
> -class ObjectBuffer;
> class Twine;
>
> /// SectionEntry - represents a section emitted into memory by the dynamic
> @@ -159,6 +157,7 @@ public:
> };
>
> class RuntimeDyldImpl {
> + friend class RuntimeDyld::LoadedObjectInfo;
> friend class RuntimeDyldCheckerImpl;
> private:
>
> @@ -296,14 +295,15 @@ protected:
> /// \brief Given the common symbols discovered in the object file, emit a
> /// new section for them and update the symbol mappings in the object and
> /// symbol table.
> - void emitCommonSymbols(ObjectImage &Obj, const CommonSymbolMap &CommonSymbols,
> + void emitCommonSymbols(const ObjectFile &Obj,
> + const CommonSymbolMap &CommonSymbols,
> uint64_t TotalSize, SymbolTableMap &SymbolTable);
>
> /// \brief Emits section data from the object file to the MemoryManager.
> /// \param IsCode if it's true then allocateCodeSection() will be
> /// used for emits, else allocateDataSection() will be used.
> /// \return SectionID.
> - unsigned emitSection(ObjectImage &Obj, const SectionRef &Section,
> + unsigned emitSection(const ObjectFile &Obj, const SectionRef &Section,
> bool IsCode);
>
> /// \brief Find Section in LocalSections. If the secton is not found - emit
> @@ -311,7 +311,7 @@ protected:
> /// \param IsCode if it's true then allocateCodeSection() will be
> /// used for emmits, else allocateDataSection() will be used.
> /// \return SectionID.
> - unsigned findOrEmitSection(ObjectImage &Obj, const SectionRef &Section,
> + unsigned findOrEmitSection(const ObjectFile &Obj, const SectionRef &Section,
> bool IsCode, ObjSectionToIDMap &LocalSections);
>
> // \brief Add a relocation entry that uses the given section.
> @@ -339,7 +339,7 @@ protected:
> /// \return Iterator to the next relocation that needs to be parsed.
> virtual relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &Obj, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &Obj, ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) = 0;
>
> /// \brief Resolve relocations to external symbols.
> @@ -351,13 +351,16 @@ protected:
>
> // \brief Compute an upper bound of the memory that is required to load all
> // sections
> - void computeTotalAllocSize(ObjectImage &Obj, uint64_t &CodeSize,
> + void computeTotalAllocSize(const ObjectFile &Obj, uint64_t &CodeSize,
> uint64_t &DataSizeRO, uint64_t &DataSizeRW);
>
> // \brief Compute the stub buffer size required for a section
> - unsigned computeSectionStubBufSize(ObjectImage &Obj,
> + unsigned computeSectionStubBufSize(const ObjectFile &Obj,
> const SectionRef &Section);
>
> + // \brief Implementation of the generic part of the loadObject algorithm.
> + std::pair<unsigned, unsigned> loadObjectImpl(const object::ObjectFile &Obj);
> +
> public:
> RuntimeDyldImpl(RTDyldMemoryManager *mm)
> : MemMgr(mm), Checker(nullptr), ProcessAllSections(false), HasError(false) {
> @@ -373,8 +376,8 @@ public:
> this->Checker = Checker;
> }
>
> - std::unique_ptr<ObjectImage>
> - loadObject(std::unique_ptr<ObjectImage> InputObject);
> + virtual std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> + loadObject(const object::ObjectFile &Obj) = 0;
>
> uint8_t* getSymbolAddress(StringRef Name) const {
> // FIXME: Just look up as a function for now. Overly simple of course.
> @@ -411,14 +414,14 @@ public:
> // Get the error message.
> StringRef getErrorString() { return ErrorStr; }
>
> - virtual bool isCompatibleFormat(const ObjectBuffer *Buffer) const = 0;
> - virtual bool isCompatibleFile(const ObjectFile *Obj) const = 0;
> + virtual bool isCompatibleFile(const ObjectFile &Obj) const = 0;
>
> virtual void registerEHFrames();
>
> virtual void deregisterEHFrames();
>
> - virtual void finalizeLoad(ObjectImage &ObjImg, ObjSectionToIDMap &SectionMap) {}
> + virtual void finalizeLoad(const ObjectFile &ObjImg,
> + ObjSectionToIDMap &SectionMap) {}
> };
>
> } // end namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp Wed Nov 26 00:53:26 2014
> @@ -25,6 +25,22 @@ using namespace llvm::object;
>
> #define DEBUG_TYPE "dyld"
>
> +namespace {
> +
> +class LoadedMachOObjectInfo : public RuntimeDyld::LoadedObjectInfo {
> +public:
> + LoadedMachOObjectInfo(RuntimeDyldImpl &RTDyld, unsigned BeginIdx,
> + unsigned EndIdx)
> + : RuntimeDyld::LoadedObjectInfo(RTDyld, BeginIdx, EndIdx) {}
> +
> + OwningBinary<ObjectFile>
> + getObjectForDebug(const ObjectFile &Obj) const override {
> + return OwningBinary<ObjectFile>();
> + }
> +};
> +
> +};
> +
> namespace llvm {
>
> int64_t RuntimeDyldMachO::memcpyAddend(const RelocationEntry &RE) const {
> @@ -35,12 +51,12 @@ int64_t RuntimeDyldMachO::memcpyAddend(c
> }
>
> RelocationValueRef RuntimeDyldMachO::getRelocationValueRef(
> - ObjectImage &ObjImg, const relocation_iterator &RI,
> + const ObjectFile &BaseTObj, const relocation_iterator &RI,
> const RelocationEntry &RE, ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols) {
>
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseTObj);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RI->getRawDataRefImpl());
> RelocationValueRef Value;
> @@ -67,7 +83,7 @@ RelocationValueRef RuntimeDyldMachO::get
> } else {
> SectionRef Sec = Obj.getRelocationSection(RelInfo);
> bool IsCode = Sec.isText();
> - Value.SectionID = findOrEmitSection(ObjImg, Sec, IsCode, ObjSectionToID);
> + Value.SectionID = findOrEmitSection(Obj, Sec, IsCode, ObjSectionToID);
> uint64_t Addr = Sec.getAddress();
> Value.Offset = RE.Addend - Addr;
> }
> @@ -76,11 +92,11 @@ RelocationValueRef RuntimeDyldMachO::get
> }
>
> void RuntimeDyldMachO::makeValueAddendPCRel(RelocationValueRef &Value,
> - ObjectImage &ObjImg,
> + const ObjectFile &BaseTObj,
> const relocation_iterator &RI,
> unsigned OffsetToNextPC) {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseTObj);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RI->getRawDataRefImpl());
>
> @@ -125,7 +141,7 @@ RuntimeDyldMachO::getSectionByAddress(co
>
> // Populate __pointers section.
> void RuntimeDyldMachO::populateIndirectSymbolPointersSection(
> - MachOObjectFile &Obj,
> + const MachOObjectFile &Obj,
> const SectionRef &PTSection,
> unsigned PTSectionID) {
> assert(!Obj.is64Bit() &&
> @@ -163,28 +179,12 @@ void RuntimeDyldMachO::populateIndirectS
> }
> }
>
> -bool
> -RuntimeDyldMachO::isCompatibleFormat(const ObjectBuffer *InputBuffer) const {
> - if (InputBuffer->getBufferSize() < 4)
> - return false;
> - StringRef Magic(InputBuffer->getBufferStart(), 4);
> - if (Magic == "\xFE\xED\xFA\xCE")
> - return true;
> - if (Magic == "\xCE\xFA\xED\xFE")
> - return true;
> - if (Magic == "\xFE\xED\xFA\xCF")
> - return true;
> - if (Magic == "\xCF\xFA\xED\xFE")
> - return true;
> - return false;
> -}
> -
> -bool RuntimeDyldMachO::isCompatibleFile(const object::ObjectFile *Obj) const {
> - return Obj->isMachO();
> +bool RuntimeDyldMachO::isCompatibleFile(const object::ObjectFile &Obj) const {
> + return Obj.isMachO();
> }
>
> template <typename Impl>
> -void RuntimeDyldMachOCRTPBase<Impl>::finalizeLoad(ObjectImage &ObjImg,
> +void RuntimeDyldMachOCRTPBase<Impl>::finalizeLoad(const ObjectFile &ObjImg,
> ObjSectionToIDMap &SectionMap) {
> unsigned EHFrameSID = RTDYLD_INVALID_SECTION_ID;
> unsigned TextSID = RTDYLD_INVALID_SECTION_ID;
> @@ -284,7 +284,7 @@ void RuntimeDyldMachOCRTPBase<Impl>::reg
> }
>
> std::unique_ptr<RuntimeDyldMachO>
> -llvm::RuntimeDyldMachO::create(Triple::ArchType Arch, RTDyldMemoryManager *MM) {
> +RuntimeDyldMachO::create(Triple::ArchType Arch, RTDyldMemoryManager *MM) {
> switch (Arch) {
> default:
> llvm_unreachable("Unsupported target for RuntimeDyldMachO.");
> @@ -296,4 +296,12 @@ llvm::RuntimeDyldMachO::create(Triple::A
> }
> }
>
> +std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> +RuntimeDyldMachO::loadObject(const object::ObjectFile &O) {
> + unsigned SectionStartIdx, SectionEndIdx;
> + std::tie(SectionStartIdx, SectionEndIdx) = loadObjectImpl(O);
> + return llvm::make_unique<LoadedMachOObjectInfo>(*this, SectionStartIdx,
> + SectionEndIdx);
> +}
> +
> } // end namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h Wed Nov 26 00:53:26 2014
> @@ -14,7 +14,6 @@
> #ifndef LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_RUNTIMEDYLDMACHO_H
> #define LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_RUNTIMEDYLDMACHO_H
>
> -#include "ObjectImageCommon.h"
> #include "RuntimeDyldImpl.h"
> #include "llvm/Object/MachO.h"
> #include "llvm/Support/Format.h"
> @@ -61,10 +60,11 @@ protected:
> /// filled in, since immediate encodings are highly target/opcode specific.
> /// For targets/opcodes with simple, contiguous immediates (e.g. X86) the
> /// memcpyAddend method can be used to read the immediate.
> - RelocationEntry getRelocationEntry(unsigned SectionID, ObjectImage &ObjImg,
> + RelocationEntry getRelocationEntry(unsigned SectionID,
> + const ObjectFile &BaseTObj,
> const relocation_iterator &RI) const {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseTObj);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RI->getRawDataRefImpl());
>
> @@ -87,14 +87,15 @@ protected:
> /// In both cases the Addend field is *NOT* fixed up to be PC-relative. That
> /// should be done by the caller where appropriate by calling makePCRel on
> /// the RelocationValueRef.
> - RelocationValueRef getRelocationValueRef(ObjectImage &ObjImg,
> + RelocationValueRef getRelocationValueRef(const ObjectFile &BaseTObj,
> const relocation_iterator &RI,
> const RelocationEntry &RE,
> ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols);
>
> /// Make the RelocationValueRef addend PC-relative.
> - void makeValueAddendPCRel(RelocationValueRef &Value, ObjectImage &ObjImg,
> + void makeValueAddendPCRel(RelocationValueRef &Value,
> + const ObjectFile &BaseTObj,
> const relocation_iterator &RI,
> unsigned OffsetToNextPC);
>
> @@ -107,31 +108,22 @@ protected:
>
>
> // Populate __pointers section.
> - void populateIndirectSymbolPointersSection(MachOObjectFile &Obj,
> + void populateIndirectSymbolPointersSection(const MachOObjectFile &Obj,
> const SectionRef &PTSection,
> unsigned PTSectionID);
>
> public:
> - /// Create an ObjectImage from the given ObjectBuffer.
> - static std::unique_ptr<ObjectImage>
> - createObjectImage(std::unique_ptr<ObjectBuffer> InputBuffer) {
> - return llvm::make_unique<ObjectImageCommon>(std::move(InputBuffer));
> - }
> -
> - /// Create an ObjectImage from the given ObjectFile.
> - static ObjectImage *
> - createObjectImageFromFile(std::unique_ptr<object::ObjectFile> InputObject) {
> - return new ObjectImageCommon(std::move(InputObject));
> - }
>
> /// Create a RuntimeDyldMachO instance for the given target architecture.
> static std::unique_ptr<RuntimeDyldMachO> create(Triple::ArchType Arch,
> RTDyldMemoryManager *mm);
>
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> + loadObject(const object::ObjectFile &O);
> +
> SectionEntry &getSection(unsigned SectionID) { return Sections[SectionID]; }
>
> - bool isCompatibleFormat(const ObjectBuffer *Buffer) const override;
> - bool isCompatibleFile(const object::ObjectFile *Obj) const override;
> + bool isCompatibleFile(const object::ObjectFile &Obj) const override;
> };
>
> /// RuntimeDyldMachOTarget - Templated base class for generic MachO linker
> @@ -153,7 +145,7 @@ private:
> public:
> RuntimeDyldMachOCRTPBase(RTDyldMemoryManager *mm) : RuntimeDyldMachO(mm) {}
>
> - void finalizeLoad(ObjectImage &ObjImg,
> + void finalizeLoad(const ObjectFile &Obj,
> ObjSectionToIDMap &SectionMap) override;
> void registerEHFrames() override;
> };
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h Wed Nov 26 00:53:26 2014
> @@ -243,10 +243,11 @@ public:
>
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &ObjImg, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &BaseObjT,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseObjT);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RelI->getRawDataRefImpl());
>
> @@ -268,10 +269,10 @@ public:
> RelInfo = Obj.getRelocation(RelI->getRawDataRefImpl());
> }
>
> - RelocationEntry RE(getRelocationEntry(SectionID, ObjImg, RelI));
> + RelocationEntry RE(getRelocationEntry(SectionID, Obj, RelI));
> RE.Addend = decodeAddend(RE);
> RelocationValueRef Value(
> - getRelocationValueRef(ObjImg, RelI, RE, ObjSectionToID, Symbols));
> + getRelocationValueRef(Obj, RelI, RE, ObjSectionToID, Symbols));
>
> assert((ExplicitAddend == 0 || RE.Addend == 0) && "Relocation has "\
> "ARM64_RELOC_ADDEND and embedded addend in the instruction.");
> @@ -282,7 +283,7 @@ public:
>
> bool IsExtern = Obj.getPlainRelocationExternal(RelInfo);
> if (!IsExtern && RE.IsPCRel)
> - makeValueAddendPCRel(Value, ObjImg, RelI, 1 << RE.Size);
> + makeValueAddendPCRel(Value, Obj, RelI, 1 << RE.Size);
>
> RE.Addend = Value.Offset;
>
> @@ -359,7 +360,7 @@ public:
> }
> }
>
> - void finalizeSection(ObjectImage &ObjImg, unsigned SectionID,
> + void finalizeSection(const ObjectFile &Obj, unsigned SectionID,
> const SectionRef &Section) {}
>
> private:
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h Wed Nov 26 00:53:26 2014
> @@ -49,29 +49,30 @@ public:
>
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &ObjImg, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &BaseObjT,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseObjT);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RelI->getRawDataRefImpl());
> uint32_t RelType = Obj.getAnyRelocationType(RelInfo);
>
> if (Obj.isRelocationScattered(RelInfo)) {
> if (RelType == MachO::ARM_RELOC_HALF_SECTDIFF)
> - return processHALFSECTDIFFRelocation(SectionID, RelI, ObjImg,
> + return processHALFSECTDIFFRelocation(SectionID, RelI, Obj,
> ObjSectionToID);
> else
> return ++++RelI;
> }
>
> - RelocationEntry RE(getRelocationEntry(SectionID, ObjImg, RelI));
> + RelocationEntry RE(getRelocationEntry(SectionID, Obj, RelI));
> RE.Addend = decodeAddend(RE);
> RelocationValueRef Value(
> - getRelocationValueRef(ObjImg, RelI, RE, ObjSectionToID, Symbols));
> + getRelocationValueRef(Obj, RelI, RE, ObjSectionToID, Symbols));
>
> if (RE.IsPCRel)
> - makeValueAddendPCRel(Value, ObjImg, RelI, 8);
> + makeValueAddendPCRel(Value, Obj, RelI, 8);
>
> if ((RE.RelType & 0xf) == MachO::ARM_RELOC_BR24)
> processBranchRelocation(RE, Value, Stubs);
> @@ -154,15 +155,14 @@ public:
> }
> }
>
> - void finalizeSection(ObjectImage &ObjImg, unsigned SectionID,
> + void finalizeSection(const ObjectFile &Obj, unsigned SectionID,
> const SectionRef &Section) {
> StringRef Name;
> Section.getName(Name);
>
> if (Name == "__nl_symbol_ptr")
> - populateIndirectSymbolPointersSection(
> - cast<MachOObjectFile>(*ObjImg.getObjectFile()),
> - Section, SectionID);
> + populateIndirectSymbolPointersSection(cast<MachOObjectFile>(Obj),
> + Section, SectionID);
> }
>
> private:
> @@ -199,25 +199,25 @@ private:
>
> relocation_iterator
> processHALFSECTDIFFRelocation(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &Obj,
> + const ObjectFile &BaseTObj,
> ObjSectionToIDMap &ObjSectionToID) {
> - const MachOObjectFile *MachO =
> - static_cast<const MachOObjectFile *>(Obj.getObjectFile());
> + const MachOObjectFile &MachO =
> + static_cast<const MachOObjectFile&>(BaseTObj);
> MachO::any_relocation_info RE =
> - MachO->getRelocation(RelI->getRawDataRefImpl());
> + MachO.getRelocation(RelI->getRawDataRefImpl());
>
>
> // For a half-diff relocation the length bits actually record whether this
> // is a movw/movt, and whether this is arm or thumb.
> // Bit 0 indicates movw (b0 == 0) or movt (b0 == 1).
> // Bit 1 indicates arm (b1 == 0) or thumb (b1 == 1).
> - unsigned HalfDiffKindBits = MachO->getAnyRelocationLength(RE);
> + unsigned HalfDiffKindBits = MachO.getAnyRelocationLength(RE);
> if (HalfDiffKindBits & 0x2)
> llvm_unreachable("Thumb not yet supported.");
>
> SectionEntry &Section = Sections[SectionID];
> - uint32_t RelocType = MachO->getAnyRelocationType(RE);
> - bool IsPCRel = MachO->getAnyRelocationPCRel(RE);
> + uint32_t RelocType = MachO.getAnyRelocationType(RE);
> + bool IsPCRel = MachO.getAnyRelocationPCRel(RE);
> uint64_t Offset;
> RelI->getOffset(Offset);
> uint8_t *LocalAddress = Section.Address + Offset;
> @@ -226,27 +226,27 @@ private:
>
> ++RelI;
> MachO::any_relocation_info RE2 =
> - MachO->getRelocation(RelI->getRawDataRefImpl());
> - uint32_t AddrA = MachO->getScatteredRelocationValue(RE);
> - section_iterator SAI = getSectionByAddress(*MachO, AddrA);
> - assert(SAI != MachO->section_end() && "Can't find section for address A");
> + MachO.getRelocation(RelI->getRawDataRefImpl());
> + uint32_t AddrA = MachO.getScatteredRelocationValue(RE);
> + section_iterator SAI = getSectionByAddress(MachO, AddrA);
> + assert(SAI != MachO.section_end() && "Can't find section for address A");
> uint64_t SectionABase = SAI->getAddress();
> uint64_t SectionAOffset = AddrA - SectionABase;
> SectionRef SectionA = *SAI;
> bool IsCode = SectionA.isText();
> uint32_t SectionAID =
> - findOrEmitSection(Obj, SectionA, IsCode, ObjSectionToID);
> + findOrEmitSection(MachO, SectionA, IsCode, ObjSectionToID);
>
> - uint32_t AddrB = MachO->getScatteredRelocationValue(RE2);
> - section_iterator SBI = getSectionByAddress(*MachO, AddrB);
> - assert(SBI != MachO->section_end() && "Can't find section for address B");
> + uint32_t AddrB = MachO.getScatteredRelocationValue(RE2);
> + section_iterator SBI = getSectionByAddress(MachO, AddrB);
> + assert(SBI != MachO.section_end() && "Can't find section for address B");
> uint64_t SectionBBase = SBI->getAddress();
> uint64_t SectionBOffset = AddrB - SectionBBase;
> SectionRef SectionB = *SBI;
> uint32_t SectionBID =
> - findOrEmitSection(Obj, SectionB, IsCode, ObjSectionToID);
> + findOrEmitSection(MachO, SectionB, IsCode, ObjSectionToID);
>
> - uint32_t OtherHalf = MachO->getAnyRelocationAddress(RE2) & 0xffff;
> + uint32_t OtherHalf = MachO.getAnyRelocationAddress(RE2) & 0xffff;
> unsigned Shift = (HalfDiffKindBits & 0x1) ? 16 : 0;
> uint32_t FullImmVal = (Immediate << Shift) | (OtherHalf << (16 - Shift));
> int64_t Addend = FullImmVal - (AddrA - AddrB);
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h Wed Nov 26 00:53:26 2014
> @@ -31,10 +31,11 @@ public:
>
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &ObjImg, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &BaseObjT,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseObjT);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RelI->getRawDataRefImpl());
> uint32_t RelType = Obj.getAnyRelocationType(RelInfo);
> @@ -42,18 +43,18 @@ public:
> if (Obj.isRelocationScattered(RelInfo)) {
> if (RelType == MachO::GENERIC_RELOC_SECTDIFF ||
> RelType == MachO::GENERIC_RELOC_LOCAL_SECTDIFF)
> - return processSECTDIFFRelocation(SectionID, RelI, ObjImg,
> + return processSECTDIFFRelocation(SectionID, RelI, Obj,
> ObjSectionToID);
> else if (RelType == MachO::GENERIC_RELOC_VANILLA)
> - return processI386ScatteredVANILLA(SectionID, RelI, ObjImg,
> + return processI386ScatteredVANILLA(SectionID, RelI, Obj,
> ObjSectionToID);
> llvm_unreachable("Unhandled scattered relocation.");
> }
>
> - RelocationEntry RE(getRelocationEntry(SectionID, ObjImg, RelI));
> + RelocationEntry RE(getRelocationEntry(SectionID, Obj, RelI));
> RE.Addend = memcpyAddend(RE);
> RelocationValueRef Value(
> - getRelocationValueRef(ObjImg, RelI, RE, ObjSectionToID, Symbols));
> + getRelocationValueRef(Obj, RelI, RE, ObjSectionToID, Symbols));
>
> // Addends for external, PC-rel relocations on i386 point back to the zero
> // offset. Calculate the final offset from the relocation target instead.
> @@ -66,7 +67,7 @@ public:
> // Value.Addend += RelocAddr + 4;
> // }
> if (RE.IsPCRel)
> - makeValueAddendPCRel(Value, ObjImg, RelI, 1 << RE.Size);
> + makeValueAddendPCRel(Value, Obj, RelI, 1 << RE.Size);
>
> RE.Addend = Value.Offset;
>
> @@ -110,34 +111,32 @@ public:
> }
> }
>
> - void finalizeSection(ObjectImage &ObjImg, unsigned SectionID,
> + void finalizeSection(const ObjectFile &Obj, unsigned SectionID,
> const SectionRef &Section) {
> StringRef Name;
> Section.getName(Name);
>
> if (Name == "__jump_table")
> - populateJumpTable(cast<MachOObjectFile>(*ObjImg.getObjectFile()), Section,
> - SectionID);
> + populateJumpTable(cast<MachOObjectFile>(Obj), Section, SectionID);
> else if (Name == "__pointers")
> - populateIndirectSymbolPointersSection(
> - cast<MachOObjectFile>(*ObjImg.getObjectFile()),
> - Section, SectionID);
> + populateIndirectSymbolPointersSection(cast<MachOObjectFile>(Obj),
> + Section, SectionID);
> }
>
> private:
> relocation_iterator
> processSECTDIFFRelocation(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &Obj,
> + const ObjectFile &BaseObjT,
> ObjSectionToIDMap &ObjSectionToID) {
> - const MachOObjectFile *MachO =
> - static_cast<const MachOObjectFile *>(Obj.getObjectFile());
> + const MachOObjectFile &Obj =
> + static_cast<const MachOObjectFile&>(BaseObjT);
> MachO::any_relocation_info RE =
> - MachO->getRelocation(RelI->getRawDataRefImpl());
> + Obj.getRelocation(RelI->getRawDataRefImpl());
>
> SectionEntry &Section = Sections[SectionID];
> - uint32_t RelocType = MachO->getAnyRelocationType(RE);
> - bool IsPCRel = MachO->getAnyRelocationPCRel(RE);
> - unsigned Size = MachO->getAnyRelocationLength(RE);
> + uint32_t RelocType = Obj.getAnyRelocationType(RE);
> + bool IsPCRel = Obj.getAnyRelocationPCRel(RE);
> + unsigned Size = Obj.getAnyRelocationLength(RE);
> uint64_t Offset;
> RelI->getOffset(Offset);
> uint8_t *LocalAddress = Section.Address + Offset;
> @@ -146,11 +145,11 @@ private:
>
> ++RelI;
> MachO::any_relocation_info RE2 =
> - MachO->getRelocation(RelI->getRawDataRefImpl());
> + Obj.getRelocation(RelI->getRawDataRefImpl());
>
> - uint32_t AddrA = MachO->getScatteredRelocationValue(RE);
> - section_iterator SAI = getSectionByAddress(*MachO, AddrA);
> - assert(SAI != MachO->section_end() && "Can't find section for address A");
> + uint32_t AddrA = Obj.getScatteredRelocationValue(RE);
> + section_iterator SAI = getSectionByAddress(Obj, AddrA);
> + assert(SAI != Obj.section_end() && "Can't find section for address A");
> uint64_t SectionABase = SAI->getAddress();
> uint64_t SectionAOffset = AddrA - SectionABase;
> SectionRef SectionA = *SAI;
> @@ -158,9 +157,9 @@ private:
> uint32_t SectionAID =
> findOrEmitSection(Obj, SectionA, IsCode, ObjSectionToID);
>
> - uint32_t AddrB = MachO->getScatteredRelocationValue(RE2);
> - section_iterator SBI = getSectionByAddress(*MachO, AddrB);
> - assert(SBI != MachO->section_end() && "Can't find section for address B");
> + uint32_t AddrB = Obj.getScatteredRelocationValue(RE2);
> + section_iterator SBI = getSectionByAddress(Obj, AddrB);
> + assert(SBI != Obj.section_end() && "Can't find section for address B");
> uint64_t SectionBBase = SBI->getAddress();
> uint64_t SectionBOffset = AddrB - SectionBBase;
> SectionRef SectionB = *SBI;
> @@ -186,26 +185,27 @@ private:
> }
>
> relocation_iterator processI386ScatteredVANILLA(
> - unsigned SectionID, relocation_iterator RelI, ObjectImage &Obj,
> + unsigned SectionID, relocation_iterator RelI,
> + const ObjectFile &BaseObjT,
> RuntimeDyldMachO::ObjSectionToIDMap &ObjSectionToID) {
> - const MachOObjectFile *MachO =
> - static_cast<const MachOObjectFile *>(Obj.getObjectFile());
> + const MachOObjectFile &Obj =
> + static_cast<const MachOObjectFile&>(BaseObjT);
> MachO::any_relocation_info RE =
> - MachO->getRelocation(RelI->getRawDataRefImpl());
> + Obj.getRelocation(RelI->getRawDataRefImpl());
>
> SectionEntry &Section = Sections[SectionID];
> - uint32_t RelocType = MachO->getAnyRelocationType(RE);
> - bool IsPCRel = MachO->getAnyRelocationPCRel(RE);
> - unsigned Size = MachO->getAnyRelocationLength(RE);
> + uint32_t RelocType = Obj.getAnyRelocationType(RE);
> + bool IsPCRel = Obj.getAnyRelocationPCRel(RE);
> + unsigned Size = Obj.getAnyRelocationLength(RE);
> uint64_t Offset;
> RelI->getOffset(Offset);
> uint8_t *LocalAddress = Section.Address + Offset;
> unsigned NumBytes = 1 << Size;
> int64_t Addend = readBytesUnaligned(LocalAddress, NumBytes);
>
> - unsigned SymbolBaseAddr = MachO->getScatteredRelocationValue(RE);
> - section_iterator TargetSI = getSectionByAddress(*MachO, SymbolBaseAddr);
> - assert(TargetSI != MachO->section_end() && "Can't find section for symbol");
> + unsigned SymbolBaseAddr = Obj.getScatteredRelocationValue(RE);
> + section_iterator TargetSI = getSectionByAddress(Obj, SymbolBaseAddr);
> + assert(TargetSI != Obj.section_end() && "Can't find section for symbol");
> uint64_t SectionBaseAddr = TargetSI->getAddress();
> SectionRef TargetSection = *TargetSI;
> bool IsCode = TargetSection.isText();
> @@ -221,7 +221,7 @@ private:
> }
>
> // Populate stubs in __jump_table section.
> - void populateJumpTable(MachOObjectFile &Obj, const SectionRef &JTSection,
> + void populateJumpTable(const MachOObjectFile &Obj, const SectionRef &JTSection,
> unsigned JTSectionID) {
> assert(!Obj.is64Bit() &&
> "__jump_table section not supported in 64-bit MachO.");
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h Wed Nov 26 00:53:26 2014
> @@ -31,24 +31,25 @@ public:
>
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &ObjImg, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &BaseObjT,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override {
> const MachOObjectFile &Obj =
> - static_cast<const MachOObjectFile &>(*ObjImg.getObjectFile());
> + static_cast<const MachOObjectFile &>(BaseObjT);
> MachO::any_relocation_info RelInfo =
> Obj.getRelocation(RelI->getRawDataRefImpl());
>
> assert(!Obj.isRelocationScattered(RelInfo) &&
> "Scattered relocations not supported on X86_64");
>
> - RelocationEntry RE(getRelocationEntry(SectionID, ObjImg, RelI));
> + RelocationEntry RE(getRelocationEntry(SectionID, Obj, RelI));
> RE.Addend = memcpyAddend(RE);
> RelocationValueRef Value(
> - getRelocationValueRef(ObjImg, RelI, RE, ObjSectionToID, Symbols));
> + getRelocationValueRef(Obj, RelI, RE, ObjSectionToID, Symbols));
>
> bool IsExtern = Obj.getPlainRelocationExternal(RelInfo);
> if (!IsExtern && RE.IsPCRel)
> - makeValueAddendPCRel(Value, ObjImg, RelI, 1 << RE.Size);
> + makeValueAddendPCRel(Value, Obj, RelI, 1 << RE.Size);
>
> if (RE.RelType == MachO::X86_64_RELOC_GOT ||
> RE.RelType == MachO::X86_64_RELOC_GOT_LOAD)
> @@ -97,7 +98,7 @@ public:
> }
> }
>
> - void finalizeSection(ObjectImage &ObjImg, unsigned SectionID,
> + void finalizeSection(const ObjectFile &Obj, unsigned SectionID,
> const SectionRef &Section) {}
>
> private:
>
> Modified: llvm/trunk/tools/lli/RemoteMemoryManager.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/lli/RemoteMemoryManager.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/tools/lli/RemoteMemoryManager.cpp (original)
> +++ llvm/trunk/tools/lli/RemoteMemoryManager.cpp Wed Nov 26 00:53:26 2014
> @@ -14,7 +14,6 @@
>
> #include "RemoteMemoryManager.h"
> #include "llvm/ExecutionEngine/ExecutionEngine.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/Support/Debug.h"
> #include "llvm/Support/Format.h"
>
> @@ -78,7 +77,7 @@ sys::MemoryBlock RemoteMemoryManager::al
> }
>
> void RemoteMemoryManager::notifyObjectLoaded(ExecutionEngine *EE,
> - const ObjectImage *Obj) {
> + const object::ObjectFile &Obj) {
> // The client should have called setRemoteTarget() before triggering any
> // code generation.
> assert(Target);
>
> Modified: llvm/trunk/tools/lli/RemoteMemoryManager.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/lli/RemoteMemoryManager.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/tools/lli/RemoteMemoryManager.h (original)
> +++ llvm/trunk/tools/lli/RemoteMemoryManager.h Wed Nov 26 00:53:26 2014
> @@ -80,7 +80,8 @@ public:
> // symbols from Modules it contains.
> uint64_t getSymbolAddress(const std::string &Name) override { return 0; }
>
> - void notifyObjectLoaded(ExecutionEngine *EE, const ObjectImage *Obj) override;
> + void notifyObjectLoaded(ExecutionEngine *EE,
> + const object::ObjectFile &Obj) override;
>
> bool finalizeMemory(std::string *ErrMsg) override;
>
>
> Modified: llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp (original)
> +++ llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp Wed Nov 26 00:53:26 2014
> @@ -19,10 +19,10 @@
> #include "llvm/ExecutionEngine/JITEventListener.h"
> #include "llvm/ExecutionEngine/SectionMemoryManager.h"
> #include "llvm/ExecutionEngine/MCJIT.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/IR/Module.h"
> #include "llvm/IRReader/IRReader.h"
> #include "llvm/Support/CommandLine.h"
> +#include "llvm/Support/Debug.h"
> #include "llvm/Support/Host.h"
> #include "llvm/Support/ManagedStatic.h"
> #include "llvm/Support/MemoryBuffer.h"
>
> 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=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp (original)
> +++ llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp Wed Nov 26 00:53:26 2014
> @@ -13,8 +13,6 @@
>
> #include "llvm/ADT/StringMap.h"
> #include "llvm/DebugInfo/DIContext.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/ExecutionEngine/RuntimeDyldChecker.h"
> #include "llvm/MC/MCAsmInfo.h"
> @@ -207,23 +205,32 @@ static int printLineInfoForInput() {
> if (std::error_code EC = InputBuffer.getError())
> return Error("unable to read input: '" + EC.message() + "'");
>
> - std::unique_ptr<ObjectImage> LoadedObject;
> + ErrorOr<std::unique_ptr<ObjectFile>> MaybeObj(
> + ObjectFile::createObjectFile((*InputBuffer)->getMemBufferRef()));
> +
> + if (std::error_code EC = MaybeObj.getError())
> + return Error("unable to create object file: '" + EC.message() + "'");
> +
> + ObjectFile &Obj = **MaybeObj;
> +
> // Load the object file
> - LoadedObject = Dyld.loadObject(
> - llvm::make_unique<ObjectBuffer>(std::move(*InputBuffer)));
> - if (!LoadedObject) {
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo> LoadedObjInfo =
> + Dyld.loadObject(Obj);
> +
> + if (Dyld.hasError())
> return Error(Dyld.getErrorString());
> - }
>
> // Resolve all the relocations we can.
> Dyld.resolveRelocations();
>
> + OwningBinary<ObjectFile> DebugObj = LoadedObjInfo->getObjectForDebug(Obj);
> +
> std::unique_ptr<DIContext> Context(
> - DIContext::getDWARFContext(*LoadedObject->getObjectFile()));
> + DIContext::getDWARFContext(*DebugObj.getBinary()));
>
> // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = LoadedObject->begin_symbols(),
> - E = LoadedObject->end_symbols();
> + for (object::symbol_iterator I = DebugObj.getBinary()->symbol_begin(),
> + E = DebugObj.getBinary()->symbol_end();
> I != E; ++I) {
> object::SymbolRef::Type SymType;
> if (I->getType(SymType)) continue;
> @@ -268,11 +275,17 @@ static int executeInput() {
> MemoryBuffer::getFileOrSTDIN(InputFileList[i]);
> if (std::error_code EC = InputBuffer.getError())
> return Error("unable to read input: '" + EC.message() + "'");
> - std::unique_ptr<ObjectImage> LoadedObject;
> + ErrorOr<std::unique_ptr<ObjectFile>> MaybeObj(
> + ObjectFile::createObjectFile((*InputBuffer)->getMemBufferRef()));
> +
> + if (std::error_code EC = MaybeObj.getError())
> + return Error("unable to create object file: '" + EC.message() + "'");
> +
> + ObjectFile &Obj = **MaybeObj;
> +
> // Load the object file
> - LoadedObject = Dyld.loadObject(
> - llvm::make_unique<ObjectBuffer>(std::move(*InputBuffer)));
> - if (!LoadedObject) {
> + Dyld.loadObject(Obj);
> + if (Dyld.hasError()) {
> return Error(Dyld.getErrorString());
> }
> }
> @@ -512,14 +525,21 @@ static int linkAndVerify() {
> // Load the input memory buffer.
> ErrorOr<std::unique_ptr<MemoryBuffer>> InputBuffer =
> MemoryBuffer::getFileOrSTDIN(InputFileList[i]);
> +
> if (std::error_code EC = InputBuffer.getError())
> return Error("unable to read input: '" + EC.message() + "'");
>
> - std::unique_ptr<ObjectImage> LoadedObject;
> + ErrorOr<std::unique_ptr<ObjectFile>> MaybeObj(
> + ObjectFile::createObjectFile((*InputBuffer)->getMemBufferRef()));
> +
> + if (std::error_code EC = MaybeObj.getError())
> + return Error("unable to create object file: '" + EC.message() + "'");
> +
> + ObjectFile &Obj = **MaybeObj;
> +
> // Load the object file
> - LoadedObject = Dyld.loadObject(
> - llvm::make_unique<ObjectBuffer>(std::move(*InputBuffer)));
> - if (!LoadedObject) {
> + Dyld.loadObject(Obj);
> + if (Dyld.hasError()) {
> return Error(Dyld.getErrorString());
> }
> }
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
On Wed, Nov 26, 2014 at 1:53 AM, Lang Hames <lhames at gmail.com> wrote:
> Author: lhames
> Date: Wed Nov 26 00:53:26 2014
> New Revision: 222810
>
> URL: http://llvm.org/viewvc/llvm-project?rev=222810&view=rev
> Log:
> [MCJIT] Clean up RuntimeDyld's quirky object-ownership/modification scheme.
>
> Previously, when loading an object file, RuntimeDyld (1) took ownership of the
> ObjectFile instance (and associated MemoryBuffer), (2) potentially modified the
> object in-place, and (3) returned an ObjectImage that managed ownership of the
> now-modified object and provided some convenience methods. This scheme accreted
> over several years as features were tacked on to RuntimeDyld, and was both
> unintuitive and unsafe (See e.g. http://llvm.org/PR20722).
>
> This patch fixes the issue by removing all ownership and in-place modification
> of object files from RuntimeDyld. Existing behavior, including debugger
> registration, is preserved.
>
> Noteworthy changes include:
>
> (1) ObjectFile instances are now passed to RuntimeDyld by const-ref.
> (2) The ObjectImage and ObjectBuffer classes have been removed entirely, they
> existed to model ownership within RuntimeDyld, and so are no longer needed.
> (3) RuntimeDyld::loadObject now returns an instance of a new class,
> RuntimeDyld::LoadedObjectInfo, which can be used to construct a modified
> object suitable for registration with the debugger, following the existing
> debugger registration scheme.
> (4) The JITRegistrar class has been removed, and the GDBRegistrar class has been
> re-written as a JITEventListener.
>
> This should fix http://llvm.org/PR20722 .
>
>
> Added:
> llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h
> - copied, changed from r222801, llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp
> - copied, changed from r222764, llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> Removed:
> llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h
> llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h
> Modified:
> llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h
> llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h
> llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h
> llvm/trunk/lib/ExecutionEngine/CMakeLists.txt
> llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp
> llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp
> llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h
> llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.cpp
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldMachO.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOAArch64.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOARM.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOI386.h
> llvm/trunk/lib/ExecutionEngine/RuntimeDyld/Targets/RuntimeDyldMachOX86_64.h
> llvm/trunk/tools/lli/RemoteMemoryManager.cpp
> llvm/trunk/tools/lli/RemoteMemoryManager.h
> llvm/trunk/tools/llvm-jitlistener/llvm-jitlistener.cpp
> llvm/trunk/tools/llvm-rtdyld/llvm-rtdyld.cpp
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/JITEventListener.h Wed Nov 26 00:53:26 2014
> @@ -15,6 +15,7 @@
> #ifndef LLVM_EXECUTIONENGINE_JITEVENTLISTENER_H
> #define LLVM_EXECUTIONENGINE_JITEVENTLISTENER_H
>
> +#include "RuntimeDyld.h"
> #include "llvm/Config/llvm-config.h"
> #include "llvm/IR/DebugLoc.h"
> #include "llvm/Support/DataTypes.h"
> @@ -25,7 +26,10 @@ class Function;
> class MachineFunction;
> class OProfileWrapper;
> class IntelJITEventsWrapper;
> -class ObjectImage;
> +
> +namespace object {
> + class ObjectFile;
> +}
>
> /// JITEvent_EmittedFunctionDetails - Helper struct for containing information
> /// about a generated machine code function.
> @@ -57,7 +61,7 @@ public:
>
> public:
> JITEventListener() {}
> - virtual ~JITEventListener();
> + virtual ~JITEventListener() {}
>
> /// NotifyObjectEmitted - Called after an object has been successfully
> /// emitted to memory. NotifyFunctionEmitted will not be called for
> @@ -67,11 +71,15 @@ public:
> /// The ObjectImage contains the generated object image
> /// with section headers updated to reflect the address at which sections
> /// were loaded and with relocations performed in-place on debug sections.
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj) {}
> + virtual void NotifyObjectEmitted(const object::ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {}
>
> /// NotifyFreeingObject - Called just before the memory associated with
> /// a previously emitted object is released.
> - virtual void NotifyFreeingObject(const ObjectImage &Obj) {}
> + virtual void NotifyFreeingObject(const object::ObjectFile &Obj) {}
> +
> + // Get a pointe to the GDB debugger registration listener.
> + static JITEventListener *createGDBRegistrationListener();
>
> #if LLVM_USE_INTEL_JITEVENTS
> // Construct an IntelJITEventListener
> @@ -105,7 +113,8 @@ public:
> return nullptr;
> }
> #endif // USE_OPROFILE
> -
> +private:
> + virtual void anchor();
> };
>
> } // end namespace llvm.
>
> Removed: llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (removed)
> @@ -1,76 +0,0 @@
> -//===---- ObjectBuffer.h - Utility class to wrap object image memory -----===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a wrapper class to hold the memory into which an
> -// object will be generated.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_EXECUTIONENGINE_OBJECTBUFFER_H
> -#define LLVM_EXECUTIONENGINE_OBJECTBUFFER_H
> -
> -#include "llvm/ADT/SmallVector.h"
> -#include "llvm/Support/MemoryBuffer.h"
> -#include "llvm/Support/raw_ostream.h"
> -
> -namespace llvm {
> -
> -/// This class acts as a container for the memory buffer used during generation
> -/// and loading of executable objects using MCJIT and RuntimeDyld. The
> -/// underlying memory for the object will be owned by the ObjectBuffer instance
> -/// throughout its lifetime.
> -class ObjectBuffer {
> - virtual void anchor();
> -public:
> - ObjectBuffer() {}
> - ObjectBuffer(std::unique_ptr<MemoryBuffer> Buf) : Buffer(std::move(Buf)) {}
> - virtual ~ObjectBuffer() {}
> -
> - MemoryBufferRef getMemBuffer() const { return Buffer->getMemBufferRef(); }
> -
> - const char *getBufferStart() const { return Buffer->getBufferStart(); }
> - size_t getBufferSize() const { return Buffer->getBufferSize(); }
> - StringRef getBuffer() const { return Buffer->getBuffer(); }
> - StringRef getBufferIdentifier() const {
> - return Buffer->getBufferIdentifier();
> - }
> -
> -protected:
> - // The memory contained in an ObjectBuffer
> - std::unique_ptr<MemoryBuffer> Buffer;
> -};
> -
> -/// This class encapsulates the SmallVector and raw_svector_ostream needed to
> -/// generate an object using MC code emission while providing a common
> -/// ObjectBuffer interface for access to the memory once the object has been
> -/// generated.
> -class ObjectBufferStream : public ObjectBuffer {
> - void anchor() override;
> -public:
> - ObjectBufferStream() : OS(SV) {}
> - virtual ~ObjectBufferStream() {}
> -
> - raw_ostream &getOStream() { return OS; }
> - void flush()
> - {
> - OS.flush();
> -
> - // Make the data accessible via the ObjectBuffer::Buffer
> - Buffer =
> - MemoryBuffer::getMemBuffer(StringRef(SV.data(), SV.size()), "", false);
> - }
> -
> -protected:
> - SmallVector<char, 4096> SV; // Working buffer into which we JIT.
> - raw_svector_ostream OS; // streaming wrapper
> -};
> -
> -} // namespace llvm
> -
> -#endif
>
> Removed: llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/ObjectImage.h (removed)
> @@ -1,76 +0,0 @@
> -//===---- ObjectImage.h - Format independent executuable object image -----===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a file format independent ObjectImage class.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
> -#define LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/Object/ObjectFile.h"
> -
> -namespace llvm {
> -
> -
> -/// ObjectImage - A container class that represents an ObjectFile that has been
> -/// or is in the process of being loaded into memory for execution.
> -class ObjectImage {
> - ObjectImage() LLVM_DELETED_FUNCTION;
> - ObjectImage(const ObjectImage &other) LLVM_DELETED_FUNCTION;
> - virtual void anchor();
> -
> -protected:
> - std::unique_ptr<ObjectBuffer> Buffer;
> -
> -public:
> - ObjectImage(std::unique_ptr<ObjectBuffer> Input) : Buffer(std::move(Input)) {}
> - virtual ~ObjectImage() {}
> -
> - virtual object::symbol_iterator begin_symbols() const = 0;
> - virtual object::symbol_iterator end_symbols() const = 0;
> - iterator_range<object::symbol_iterator> symbols() const {
> - return iterator_range<object::symbol_iterator>(begin_symbols(),
> - end_symbols());
> - }
> -
> - virtual object::section_iterator begin_sections() const = 0;
> - virtual object::section_iterator end_sections() const = 0;
> - iterator_range<object::section_iterator> sections() const {
> - return iterator_range<object::section_iterator>(begin_sections(),
> - end_sections());
> - }
> -
> - virtual /* Triple::ArchType */ unsigned getArch() const = 0;
> -
> - // Return the name associated with this ObjectImage.
> - // This is usually the name of the file or MemoryBuffer that the the
> - // ObjectBuffer was constructed from.
> - StringRef getImageName() const { return Buffer->getBufferIdentifier(); }
> -
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - virtual void updateSectionAddress(const object::SectionRef &Sec,
> - uint64_t Addr) = 0;
> - virtual void updateSymbolAddress(const object::SymbolRef &Sym,
> - uint64_t Addr) = 0;
> -
> - virtual StringRef getData() const = 0;
> -
> - virtual object::ObjectFile* getObjectFile() const = 0;
> -
> - // Subclasses can override these methods to provide JIT debugging support
> - virtual void registerWithDebugger() = 0;
> - virtual void deregisterWithDebugger() = 0;
> -};
> -
> -} // end namespace llvm
> -
> -#endif // LLVM_EXECUTIONENGINE_OBJECTIMAGE_H
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/RTDyldMemoryManager.h Wed Nov 26 00:53:26 2014
> @@ -22,7 +22,10 @@
> namespace llvm {
>
> class ExecutionEngine;
> -class ObjectImage;
> +
> + namespace object {
> + class ObjectFile;
> + }
>
> // RuntimeDyld clients often want to handle the memory management of
> // what gets placed where. For JIT clients, this is the subset of
> @@ -109,7 +112,7 @@ public:
> /// address space can use this call to remap the section addresses for the
> /// newly loaded object.
> virtual void notifyObjectLoaded(ExecutionEngine *EE,
> - const ObjectImage *) {}
> + const object::ObjectFile &) {}
>
> /// This method is called when object loading is complete and section page
> /// permissions can be applied. It is up to the memory manager implementation
>
> Modified: llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h (original)
> +++ llvm/trunk/include/llvm/ExecutionEngine/RuntimeDyld.h Wed Nov 26 00:53:26 2014
> @@ -15,19 +15,19 @@
> #define LLVM_EXECUTIONENGINE_RUNTIMEDYLD_H
>
> #include "llvm/ADT/StringRef.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> #include "llvm/ExecutionEngine/RTDyldMemoryManager.h"
> #include "llvm/Support/Memory.h"
> +#include <memory>
>
> namespace llvm {
>
> namespace object {
> class ObjectFile;
> + template <typename T> class OwningBinary;
> }
>
> class RuntimeDyldImpl;
> class RuntimeDyldCheckerImpl;
> -class ObjectImage;
>
> class RuntimeDyld {
> friend class RuntimeDyldCheckerImpl;
> @@ -46,22 +46,35 @@ protected:
> // Any relocations already associated with the symbol will be re-resolved.
> void reassignSectionAddress(unsigned SectionID, uint64_t Addr);
> public:
> +
> + /// \brief Information about the loaded object.
> + class LoadedObjectInfo {
> + friend class RuntimeDyldImpl;
> + public:
> + LoadedObjectInfo(RuntimeDyldImpl &RTDyld, unsigned BeginIdx,
> + unsigned EndIdx)
> + : RTDyld(RTDyld), BeginIdx(BeginIdx), EndIdx(EndIdx) { }
> +
> + virtual ~LoadedObjectInfo() {}
> +
> + virtual object::OwningBinary<object::ObjectFile>
> + getObjectForDebug(const object::ObjectFile &Obj) const = 0;
> +
> + uint64_t getSectionLoadAddress(StringRef Name) const;
> +
> + protected:
> + virtual void anchor();
> +
> + RuntimeDyldImpl &RTDyld;
> + unsigned BeginIdx, EndIdx;
> + };
> +
> RuntimeDyld(RTDyldMemoryManager *);
> ~RuntimeDyld();
>
> - /// Prepare the object contained in the input buffer for execution.
> - /// Ownership of the input buffer is transferred to the ObjectImage
> - /// instance returned from this function if successful. In the case of load
> - /// failure, the input buffer will be deleted.
> - std::unique_ptr<ObjectImage>
> - loadObject(std::unique_ptr<ObjectBuffer> InputBuffer);
> -
> - /// Prepare the referenced object file for execution.
> - /// Ownership of the input object is transferred to the ObjectImage
> - /// instance returned from this function if successful. In the case of load
> - /// failure, the input object will be deleted.
> - std::unique_ptr<ObjectImage>
> - loadObject(std::unique_ptr<object::ObjectFile> InputObject);
> + /// Add the referenced object file to the list of objects to be loaded and
> + /// relocated.
> + std::unique_ptr<LoadedObjectInfo> loadObject(const object::ObjectFile &O);
>
> /// Get the address of our local copy of the symbol. This may or may not
> /// be the address used for relocation (clients can copy the data around
>
> Modified: llvm/trunk/lib/ExecutionEngine/CMakeLists.txt
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/CMakeLists.txt?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/CMakeLists.txt (original)
> +++ llvm/trunk/lib/ExecutionEngine/CMakeLists.txt Wed Nov 26 00:53:26 2014
> @@ -3,7 +3,6 @@
> add_llvm_library(LLVMExecutionEngine
> ExecutionEngine.cpp
> ExecutionEngineBindings.cpp
> - JITEventListener.cpp
> RTDyldMemoryManager.cpp
> TargetSelect.cpp
> )
>
> Modified: llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/ExecutionEngine.cpp Wed Nov 26 00:53:26 2014
> @@ -16,8 +16,7 @@
> #include "llvm/ADT/SmallString.h"
> #include "llvm/ADT/Statistic.h"
> #include "llvm/ExecutionEngine/GenericValue.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectCache.h"
> +#include "llvm/ExecutionEngine/JITEventListener.h"
> #include "llvm/IR/Constants.h"
> #include "llvm/IR/DataLayout.h"
> #include "llvm/IR/DerivedTypes.h"
> @@ -43,17 +42,15 @@ using namespace llvm;
> STATISTIC(NumInitBytes, "Number of bytes of global vars initialized");
> STATISTIC(NumGlobals , "Number of global vars initialized");
>
> -// Pin the vtable to this file.
> -void ObjectCache::anchor() {}
> -void ObjectBuffer::anchor() {}
> -void ObjectBufferStream::anchor() {}
> -
> ExecutionEngine *(*ExecutionEngine::MCJITCtor)(
> std::unique_ptr<Module> M, std::string *ErrorStr,
> RTDyldMemoryManager *MCJMM, std::unique_ptr<TargetMachine> TM) = nullptr;
> ExecutionEngine *(*ExecutionEngine::InterpCtor)(std::unique_ptr<Module> M,
> std::string *ErrorStr) =nullptr;
>
> +// Anchor for the JITEventListener class.
> +void JITEventListener::anchor() {}
> +
> ExecutionEngine::ExecutionEngine(std::unique_ptr<Module> M)
> : EEState(*this),
> LazyFunctionCreator(nullptr) {
>
> Modified: llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/IntelJITEvents/IntelJITEventListener.cpp Wed Nov 26 00:53:26 2014
> @@ -21,7 +21,6 @@
> #include "llvm/ADT/DenseMap.h"
> #include "llvm/CodeGen/MachineFunction.h"
> #include "llvm/DebugInfo/DIContext.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Debug.h"
> #include "llvm/Support/raw_ostream.h"
> @@ -32,6 +31,7 @@
>
> using namespace llvm;
> using namespace llvm::jitprofiling;
> +using namespace llvm::object;
>
> #define DEBUG_TYPE "amplifier-jit-event-listener"
>
> @@ -48,6 +48,7 @@ class IntelJITEventListener : public JIT
> typedef DenseMap<const void *, MethodAddressVector> ObjectMap;
>
> ObjectMap LoadedObjectMap;
> + std::map<const char*, OwningBinary<ObjectFile>> DebugObjects;
>
> public:
> IntelJITEventListener(IntelJITEventsWrapper* libraryWrapper) {
> @@ -57,9 +58,10 @@ public:
> ~IntelJITEventListener() {
> }
>
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj);
> + void NotifyObjectEmitted(const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> - virtual void NotifyFreeingObject(const ObjectImage &Obj);
> + void NotifyFreeingObject(const ObjectFile &Obj) override;
> };
>
> static LineNumberInfo DILineInfoToIntelJITFormat(uintptr_t StartAddress,
> @@ -95,23 +97,29 @@ static iJIT_Method_Load FunctionDescToIn
> return Result;
> }
>
> -void IntelJITEventListener::NotifyObjectEmitted(const ObjectImage &Obj) {
> +void IntelJITEventListener::NotifyObjectEmitted(
> + const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> +
> + OwningBinary<ObjectFile> DebugObjOwner = L.getObjectForDebug(Obj);
> + const ObjectFile &DebugObj = *DebugObjOwner.getBinary();
> +
> // Get the address of the object image for use as a unique identifier
> - const void* ObjData = Obj.getData().data();
> - DIContext* Context = DIContext::getDWARFContext(*Obj.getObjectFile());
> + const void* ObjData = DebugObj.getData().data();
> + DIContext* Context = DIContext::getDWARFContext(DebugObj);
> MethodAddressVector Functions;
>
> // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(),
> - E = Obj.end_symbols();
> + for (symbol_iterator I = DebugObj.symbol_begin(),
> + E = DebugObj.symbol_end();
> I != E;
> ++I) {
> std::vector<LineNumberInfo> LineInfo;
> std::string SourceFileName;
>
> - object::SymbolRef::Type SymType;
> + SymbolRef::Type SymType;
> if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> + if (SymType == SymbolRef::ST_Function) {
> StringRef Name;
> uint64_t Addr;
> uint64_t Size;
> @@ -162,11 +170,18 @@ void IntelJITEventListener::NotifyObject
> // registered function addresses for each loaded object. We will
> // use the MethodIDs map to get the registered ID for each function.
> LoadedObjectMap[ObjData] = Functions;
> + DebugObjects[Obj.getData().data()] = std::move(DebugObjOwner);
> }
>
> -void IntelJITEventListener::NotifyFreeingObject(const ObjectImage &Obj) {
> +void IntelJITEventListener::NotifyFreeingObject(const ObjectFile &Obj) {
> + // This object may not have been registered with the listener. If it wasn't,
> + // bail out.
> + if (DebugObjects.find(Obj.getData().data()) == DebugObjects.end())
> + return;
> +
> // Get the address of the object image for use as a unique identifier
> - const void* ObjData = Obj.getData().data();
> + const ObjectFile &DebugObj = *DebugObjects[Obj.getData().data()].getBinary();
> + const void* ObjData = DebugObj.getData().data();
>
> // Get the object's function list from LoadedObjectMap
> ObjectMap::iterator OI = LoadedObjectMap.find(ObjData);
> @@ -190,6 +205,7 @@ void IntelJITEventListener::NotifyFreein
>
> // Erase the object from LoadedObjectMap
> LoadedObjectMap.erase(OI);
> + DebugObjects.erase(Obj.getData().data());
> }
>
> } // anonymous namespace.
>
> Removed: llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/JITEventListener.cpp (removed)
> @@ -1,15 +0,0 @@
> -//===-- JITEventListener.cpp ----------------------------------------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#include "llvm/ExecutionEngine/JITEventListener.h"
> -
> -using namespace llvm;
> -
> -// Out-of-line definition of the virtual destructor as this is the key function.
> -JITEventListener::~JITEventListener() {}
>
> Modified: llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.cpp Wed Nov 26 00:53:26 2014
> @@ -11,8 +11,6 @@
> #include "llvm/ExecutionEngine/GenericValue.h"
> #include "llvm/ExecutionEngine/JITEventListener.h"
> #include "llvm/ExecutionEngine/MCJIT.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/SectionMemoryManager.h"
> #include "llvm/IR/DataLayout.h"
> #include "llvm/IR/DerivedTypes.h"
> @@ -21,6 +19,7 @@
> #include "llvm/IR/Module.h"
> #include "llvm/MC/MCAsmInfo.h"
> #include "llvm/Object/Archive.h"
> +#include "llvm/Object/ObjectFile.h"
> #include "llvm/PassManager.h"
> #include "llvm/Support/DynamicLibrary.h"
> #include "llvm/Support/ErrorHandling.h"
> @@ -31,6 +30,8 @@
>
> using namespace llvm;
>
> +void ObjectCache::anchor() {}
> +
> namespace {
>
> static struct RegisterJIT {
> @@ -74,6 +75,7 @@ MCJIT::MCJIT(std::unique_ptr<Module> M,
>
> OwnedModules.addModule(std::move(First));
> setDataLayout(TM->getSubtargetImpl()->getDataLayout());
> + RegisterJITEventListener(JITEventListener::createGDBRegistrationListener());
> }
>
> MCJIT::~MCJIT() {
> @@ -99,13 +101,13 @@ bool MCJIT::removeModule(Module *M) {
> }
>
> void MCJIT::addObjectFile(std::unique_ptr<object::ObjectFile> Obj) {
> - std::unique_ptr<ObjectImage> LoadedObject = Dyld.loadObject(std::move(Obj));
> - if (!LoadedObject || Dyld.hasError())
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo> L = Dyld.loadObject(*Obj);
> + if (Dyld.hasError())
> report_fatal_error(Dyld.getErrorString());
>
> - NotifyObjectEmitted(*LoadedObject);
> + NotifyObjectEmitted(*Obj, *L);
>
> - LoadedObjects.push_back(std::move(LoadedObject));
> + LoadedObjects.push_back(std::move(Obj));
> }
>
> void MCJIT::addObjectFile(object::OwningBinary<object::ObjectFile> Obj) {
> @@ -125,7 +127,7 @@ void MCJIT::setObjectCache(ObjectCache*
> ObjCache = NewCache;
> }
>
> -std::unique_ptr<ObjectBufferStream> MCJIT::emitObject(Module *M) {
> +std::unique_ptr<MemoryBuffer> MCJIT::emitObject(Module *M) {
> MutexGuard locked(lock);
>
> // This must be a module which has already been added but not loaded to this
> @@ -138,30 +140,32 @@ std::unique_ptr<ObjectBufferStream> MCJI
> PM.add(new DataLayoutPass());
>
> // The RuntimeDyld will take ownership of this shortly
> - std::unique_ptr<ObjectBufferStream> CompiledObject(new ObjectBufferStream());
> + SmallVector<char, 4096> ObjBufferSV;
> + raw_svector_ostream ObjStream(ObjBufferSV);
>
> // Turn the machine code intermediate representation into bytes in memory
> // that may be executed.
> - if (TM->addPassesToEmitMC(PM, Ctx, CompiledObject->getOStream(),
> - !getVerifyModules())) {
> + if (TM->addPassesToEmitMC(PM, Ctx, ObjStream, !getVerifyModules()))
> report_fatal_error("Target does not support MC emission!");
> - }
>
> // Initialize passes.
> PM.run(*M);
> // Flush the output buffer to get the generated code into memory
> - CompiledObject->flush();
> + ObjStream.flush();
> +
> + std::unique_ptr<MemoryBuffer> CompiledObjBuffer(
> + new ObjectMemoryBuffer(std::move(ObjBufferSV)));
>
> // If we have an object cache, tell it about the new object.
> // Note that we're using the compiled image, not the loaded image (as below).
> if (ObjCache) {
> // MemoryBuffer is a thin wrapper around the actual memory, so it's OK
> // to create a temporary object here and delete it after the call.
> - MemoryBufferRef MB = CompiledObject->getMemBuffer();
> + MemoryBufferRef MB = CompiledObjBuffer->getMemBufferRef();
> ObjCache->notifyObjectCompiled(M, MB);
> }
>
> - return CompiledObject;
> + return CompiledObjBuffer;
> }
>
> void MCJIT::generateCodeForModule(Module *M) {
> @@ -176,14 +180,10 @@ void MCJIT::generateCodeForModule(Module
> if (OwnedModules.hasModuleBeenLoaded(M))
> return;
>
> - std::unique_ptr<ObjectBuffer> ObjectToLoad;
> + std::unique_ptr<MemoryBuffer> ObjectToLoad;
> // Try to load the pre-compiled object from cache if possible
> - if (ObjCache) {
> - if (std::unique_ptr<MemoryBuffer> PreCompiledObject =
> - ObjCache->getObject(M))
> - ObjectToLoad =
> - llvm::make_unique<ObjectBuffer>(std::move(PreCompiledObject));
> - }
> + if (ObjCache)
> + ObjectToLoad = ObjCache->getObject(M);
>
> // If the cache did not contain a suitable object, compile the object
> if (!ObjectToLoad) {
> @@ -193,17 +193,18 @@ void MCJIT::generateCodeForModule(Module
>
> // Load the object into the dynamic linker.
> // MCJIT now owns the ObjectImage pointer (via its LoadedObjects list).
> - std::unique_ptr<ObjectImage> LoadedObject =
> - Dyld.loadObject(std::move(ObjectToLoad));
> - if (!LoadedObject)
> - report_fatal_error(Dyld.getErrorString());
> + ErrorOr<std::unique_ptr<object::ObjectFile>> LoadedObject =
> + object::ObjectFile::createObjectFile(ObjectToLoad->getMemBufferRef());
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo> L =
> + Dyld.loadObject(*LoadedObject.get());
>
> - // FIXME: Make this optional, maybe even move it to a JIT event listener
> - LoadedObject->registerWithDebugger();
> + if (Dyld.hasError())
> + report_fatal_error(Dyld.getErrorString());
>
> - NotifyObjectEmitted(*LoadedObject);
> + NotifyObjectEmitted(*LoadedObject.get(), *L);
>
> - LoadedObjects.push_back(std::move(LoadedObject));
> + Buffers.push_back(std::move(ObjectToLoad));
> + LoadedObjects.push_back(std::move(*LoadedObject));
>
> OwnedModules.markModuleAsLoaded(M);
> }
> @@ -549,6 +550,7 @@ void MCJIT::RegisterJITEventListener(JIT
> MutexGuard locked(lock);
> EventListeners.push_back(L);
> }
> +
> void MCJIT::UnregisterJITEventListener(JITEventListener *L) {
> if (!L)
> return;
> @@ -559,14 +561,17 @@ void MCJIT::UnregisterJITEventListener(J
> EventListeners.pop_back();
> }
> }
> -void MCJIT::NotifyObjectEmitted(const ObjectImage& Obj) {
> +
> +void MCJIT::NotifyObjectEmitted(const object::ObjectFile& Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> MutexGuard locked(lock);
> - MemMgr.notifyObjectLoaded(this, &Obj);
> + MemMgr.notifyObjectLoaded(this, Obj);
> for (unsigned I = 0, S = EventListeners.size(); I < S; ++I) {
> - EventListeners[I]->NotifyObjectEmitted(Obj);
> + EventListeners[I]->NotifyObjectEmitted(Obj, L);
> }
> }
> -void MCJIT::NotifyFreeingObject(const ObjectImage& Obj) {
> +
> +void MCJIT::NotifyFreeingObject(const object::ObjectFile& Obj) {
> MutexGuard locked(lock);
> for (JITEventListener *L : EventListeners)
> L->NotifyFreeingObject(Obj);
>
> Modified: llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/MCJIT.h Wed Nov 26 00:53:26 2014
> @@ -10,12 +10,12 @@
> #ifndef LLVM_LIB_EXECUTIONENGINE_MCJIT_MCJIT_H
> #define LLVM_LIB_EXECUTIONENGINE_MCJIT_MCJIT_H
>
> +#include "ObjectBuffer.h"
> #include "llvm/ADT/DenseMap.h"
> #include "llvm/ADT/SmallPtrSet.h"
> #include "llvm/ADT/SmallVector.h"
> #include "llvm/ExecutionEngine/ExecutionEngine.h"
> #include "llvm/ExecutionEngine/ObjectCache.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/IR/Module.h"
>
> @@ -57,7 +57,7 @@ public:
> }
>
> void notifyObjectLoaded(ExecutionEngine *EE,
> - const ObjectImage *Obj) override {
> + const object::ObjectFile &Obj) override {
> ClientMM->notifyObjectLoaded(EE, Obj);
> }
>
> @@ -222,7 +222,7 @@ class MCJIT : public ExecutionEngine {
> SmallVector<object::OwningBinary<object::Archive>, 2> Archives;
> SmallVector<std::unique_ptr<MemoryBuffer>, 2> Buffers;
>
> - SmallVector<std::unique_ptr<ObjectImage>, 2> LoadedObjects;
> + SmallVector<std::unique_ptr<object::ObjectFile>, 2> LoadedObjects;
>
> // An optional ObjectCache to be notified of compiled objects and used to
> // perform lookup of pre-compiled code to avoid re-compilation.
> @@ -341,10 +341,11 @@ protected:
> /// this function call is expected to be the contained module. The module
> /// is passed as a parameter here to prepare for multiple module support in
> /// the future.
> - std::unique_ptr<ObjectBufferStream> emitObject(Module *M);
> + std::unique_ptr<MemoryBuffer> emitObject(Module *M);
>
> - void NotifyObjectEmitted(const ObjectImage& Obj);
> - void NotifyFreeingObject(const ObjectImage& Obj);
> + void NotifyObjectEmitted(const object::ObjectFile& Obj,
> + const RuntimeDyld::LoadedObjectInfo &L);
> + void NotifyFreeingObject(const object::ObjectFile& Obj);
>
> uint64_t getExistingSymbolAddress(const std::string &Name);
> Module *findModuleForSymbol(const std::string &Name,
>
> Copied: llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h (from r222801, llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h)
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h?p2=llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h&p1=llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h&r1=222801&r2=222810&rev=222810&view=diff
> ==============================================================================
> --- llvm/trunk/include/llvm/ExecutionEngine/ObjectBuffer.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/MCJIT/ObjectBuffer.h Wed Nov 26 00:53:26 2014
> @@ -1,4 +1,4 @@
> -//===---- ObjectBuffer.h - Utility class to wrap object image memory -----===//
> +//===--- ObjectBuffer.h - Utility class to wrap object memory ---*- C++ -*-===//
> //
> // The LLVM Compiler Infrastructure
> //
> @@ -21,54 +21,26 @@
>
> namespace llvm {
>
> -/// This class acts as a container for the memory buffer used during generation
> -/// and loading of executable objects using MCJIT and RuntimeDyld. The
> -/// underlying memory for the object will be owned by the ObjectBuffer instance
> -/// throughout its lifetime.
> -class ObjectBuffer {
> - virtual void anchor();
> +class ObjectMemoryBuffer : public MemoryBuffer {
> public:
> - ObjectBuffer() {}
> - ObjectBuffer(std::unique_ptr<MemoryBuffer> Buf) : Buffer(std::move(Buf)) {}
> - virtual ~ObjectBuffer() {}
> -
> - MemoryBufferRef getMemBuffer() const { return Buffer->getMemBufferRef(); }
> -
> - const char *getBufferStart() const { return Buffer->getBufferStart(); }
> - size_t getBufferSize() const { return Buffer->getBufferSize(); }
> - StringRef getBuffer() const { return Buffer->getBuffer(); }
> - StringRef getBufferIdentifier() const {
> - return Buffer->getBufferIdentifier();
> + template <unsigned N>
> + ObjectMemoryBuffer(SmallVector<char, N> SV)
> + : SV(SV), BufferName("<in-memory object>") {
> + init(this->SV.begin(), this->SV.end(), false);
> }
>
> -protected:
> - // The memory contained in an ObjectBuffer
> - std::unique_ptr<MemoryBuffer> Buffer;
> -};
> -
> -/// This class encapsulates the SmallVector and raw_svector_ostream needed to
> -/// generate an object using MC code emission while providing a common
> -/// ObjectBuffer interface for access to the memory once the object has been
> -/// generated.
> -class ObjectBufferStream : public ObjectBuffer {
> - void anchor() override;
> -public:
> - ObjectBufferStream() : OS(SV) {}
> - virtual ~ObjectBufferStream() {}
> -
> - raw_ostream &getOStream() { return OS; }
> - void flush()
> - {
> - OS.flush();
> -
> - // Make the data accessible via the ObjectBuffer::Buffer
> - Buffer =
> - MemoryBuffer::getMemBuffer(StringRef(SV.data(), SV.size()), "", false);
> + template <unsigned N>
> + ObjectMemoryBuffer(SmallVector<char, N> SV, StringRef Name)
> + : SV(SV), BufferName(Name) {
> + init(this->SV.begin(), this->SV.end(), false);
> }
> + const char* getBufferIdentifier() const override { return BufferName.c_str(); }
> +
> + BufferKind getBufferKind() const override { return MemoryBuffer_Malloc; }
>
> -protected:
> - SmallVector<char, 4096> SV; // Working buffer into which we JIT.
> - raw_svector_ostream OS; // streaming wrapper
> +private:
> + SmallVector<char, 4096> SV;
> + std::string BufferName;
> };
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/OProfileJIT/OProfileJITEventListener.cpp Wed Nov 26 00:53:26 2014
> @@ -18,8 +18,8 @@
> #include "llvm/IR/DebugInfo.h"
> #include "llvm/IR/Function.h"
> #include "llvm/CodeGen/MachineFunction.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/OProfileWrapper.h"
> +#include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Debug.h"
> #include "llvm/Support/raw_ostream.h"
> @@ -31,31 +31,34 @@
>
> using namespace llvm;
> using namespace llvm::jitprofiling;
> +using namespace llvm::object;
>
> #define DEBUG_TYPE "oprofile-jit-event-listener"
>
> namespace {
>
> class OProfileJITEventListener : public JITEventListener {
> - OProfileWrapper& Wrapper;
> + std::unique_ptr<OProfileWrapper> Wrapper;
>
> void initialize();
> + std::map<const char*, OwningBinary<ObjectFile>> DebugObjects;
>
> public:
> - OProfileJITEventListener(OProfileWrapper& LibraryWrapper)
> - : Wrapper(LibraryWrapper) {
> + OProfileJITEventListener(std::unique_ptr<OProfileWrapper> LibraryWrapper)
> + : Wrapper(std::move(LibraryWrapper)) {
> initialize();
> }
>
> ~OProfileJITEventListener();
>
> - virtual void NotifyObjectEmitted(const ObjectImage &Obj);
> + void NotifyObjectEmitted(const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> - virtual void NotifyFreeingObject(const ObjectImage &Obj);
> + void NotifyFreeingObject(const ObjectFile &Obj) override;
> };
>
> void OProfileJITEventListener::initialize() {
> - if (!Wrapper.op_open_agent()) {
> + if (!Wrapper->op_open_agent()) {
> const std::string err_str = sys::StrError();
> DEBUG(dbgs() << "Failed to connect to OProfile agent: " << err_str << "\n");
> } else {
> @@ -64,8 +67,8 @@ void OProfileJITEventListener::initializ
> }
>
> OProfileJITEventListener::~OProfileJITEventListener() {
> - if (Wrapper.isAgentAvailable()) {
> - if (Wrapper.op_close_agent() == -1) {
> + if (Wrapper->isAgentAvailable()) {
> + if (Wrapper->op_close_agent() == -1) {
> const std::string err_str = sys::StrError();
> DEBUG(dbgs() << "Failed to disconnect from OProfile agent: "
> << err_str << "\n");
> @@ -75,17 +78,22 @@ OProfileJITEventListener::~OProfileJITEv
> }
> }
>
> -void OProfileJITEventListener::NotifyObjectEmitted(const ObjectImage &Obj) {
> - if (!Wrapper.isAgentAvailable()) {
> +void OProfileJITEventListener::NotifyObjectEmitted(
> + const ObjectFile &Obj,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> + if (!Wrapper->isAgentAvailable()) {
> return;
> }
>
> + OwningBinary<ObjectFile> DebugObjOwner = L.getObjectForDebug(Obj);
> + const ObjectFile &DebugObj = *DebugObjOwner.getBinary();
> +
> // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols();
> + for (symbol_iterator I = DebugObj.symbol_begin(), E = DebugObj.symbol_end();
> I != E; ++I) {
> - object::SymbolRef::Type SymType;
> + SymbolRef::Type SymType;
> if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> + if (SymType == SymbolRef::ST_Function) {
> StringRef Name;
> uint64_t Addr;
> uint64_t Size;
> @@ -93,7 +101,7 @@ void OProfileJITEventListener::NotifyObj
> if (I->getAddress(Addr)) continue;
> if (I->getSize(Size)) continue;
>
> - if (Wrapper.op_write_native_code(Name.data(), Addr, (void*)Addr, Size)
> + if (Wrapper->op_write_native_code(Name.data(), Addr, (void*)Addr, Size)
> == -1) {
> DEBUG(dbgs() << "Failed to tell OProfile about native function "
> << Name << " at ["
> @@ -103,45 +111,48 @@ void OProfileJITEventListener::NotifyObj
> // TODO: support line number info (similar to IntelJITEventListener.cpp)
> }
> }
> -}
>
> -void OProfileJITEventListener::NotifyFreeingObject(const ObjectImage &Obj) {
> - if (!Wrapper.isAgentAvailable()) {
> - return;
> - }
> + DebugObjects[Obj.getData().data()] = std::move(DebugObjOwner);
> +}
>
> - // Use symbol info to iterate functions in the object.
> - for (object::symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols();
> - I != E; ++I) {
> - object::SymbolRef::Type SymType;
> - if (I->getType(SymType)) continue;
> - if (SymType == object::SymbolRef::ST_Function) {
> - uint64_t Addr;
> - if (I->getAddress(Addr)) continue;
> +void OProfileJITEventListener::NotifyFreeingObject(const ObjectFile &Obj) {
> + if (Wrapper->isAgentAvailable()) {
>
> - if (Wrapper.op_unload_native_code(Addr) == -1) {
> - DEBUG(dbgs()
> - << "Failed to tell OProfile about unload of native function at "
> - << (void*)Addr << "\n");
> - continue;
> + // If there was no agent registered when the original object was loaded then
> + // we won't have created a debug object for it, so bail out.
> + if (DebugObjects.find(Obj.getData().data()) == DebugObjects.end())
> + return;
> +
> + const ObjectFile &DebugObj = *DebugObjects[Obj.getData().data()].getBinary();
> +
> + // Use symbol info to iterate functions in the object.
> + for (symbol_iterator I = DebugObj.symbol_begin(),
> + E = DebugObj.symbol_end();
> + I != E; ++I) {
> + SymbolRef::Type SymType;
> + if (I->getType(SymType)) continue;
> + if (SymType == SymbolRef::ST_Function) {
> + uint64_t Addr;
> + if (I->getAddress(Addr)) continue;
> +
> + if (Wrapper->op_unload_native_code(Addr) == -1) {
> + DEBUG(dbgs()
> + << "Failed to tell OProfile about unload of native function at "
> + << (void*)Addr << "\n");
> + continue;
> + }
> }
> }
> }
> +
> + DebugObjects.erase(Obj.getData().data());
> }
>
> } // anonymous namespace.
>
> namespace llvm {
> JITEventListener *JITEventListener::createOProfileJITEventListener() {
> - static std::unique_ptr<OProfileWrapper> JITProfilingWrapper(
> - new OProfileWrapper);
> - return new OProfileJITEventListener(*JITProfilingWrapper);
> -}
> -
> -// for testing
> -JITEventListener *JITEventListener::createOProfileJITEventListener(
> - OProfileWrapper* TestImpl) {
> - return new OProfileJITEventListener(*TestImpl);
> + return new OProfileJITEventListener(llvm::make_unique<OProfileWrapper>());
> }
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/CMakeLists.txt Wed Nov 26 00:53:26 2014
> @@ -1,5 +1,5 @@
> add_llvm_library(LLVMRuntimeDyld
> - GDBRegistrar.cpp
> + GDBRegistrationListener.cpp
> RuntimeDyld.cpp
> RuntimeDyldChecker.cpp
> RuntimeDyldELF.cpp
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (removed)
> @@ -1,213 +0,0 @@
> -//===-- GDBRegistrar.cpp - Registers objects with GDB ---------------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#include "JITRegistrar.h"
> -#include "llvm/ADT/DenseMap.h"
> -#include "llvm/Support/Compiler.h"
> -#include "llvm/Support/ErrorHandling.h"
> -#include "llvm/Support/Mutex.h"
> -#include "llvm/Support/MutexGuard.h"
> -#include "llvm/Support/ManagedStatic.h"
> -
> -using namespace llvm;
> -
> -// This must be kept in sync with gdb/gdb/jit.h .
> -extern "C" {
> -
> - typedef enum {
> - JIT_NOACTION = 0,
> - JIT_REGISTER_FN,
> - JIT_UNREGISTER_FN
> - } jit_actions_t;
> -
> - struct jit_code_entry {
> - struct jit_code_entry *next_entry;
> - struct jit_code_entry *prev_entry;
> - const char *symfile_addr;
> - uint64_t symfile_size;
> - };
> -
> - struct jit_descriptor {
> - uint32_t version;
> - // This should be jit_actions_t, but we want to be specific about the
> - // bit-width.
> - uint32_t action_flag;
> - struct jit_code_entry *relevant_entry;
> - struct jit_code_entry *first_entry;
> - };
> -
> - // We put information about the JITed function in this global, which the
> - // debugger reads. Make sure to specify the version statically, because the
> - // debugger checks the version before we can set it during runtime.
> - struct jit_descriptor __jit_debug_descriptor = { 1, 0, nullptr, nullptr };
> -
> - // Debuggers puts a breakpoint in this function.
> - LLVM_ATTRIBUTE_NOINLINE void __jit_debug_register_code() {
> - // The noinline and the asm prevent calls to this function from being
> - // optimized out.
> -#if !defined(_MSC_VER)
> - asm volatile("":::"memory");
> -#endif
> - }
> -
> -}
> -
> -namespace {
> -
> -// Buffer for an in-memory object file in executable memory
> -typedef llvm::DenseMap< const char*,
> - std::pair<std::size_t, jit_code_entry*> >
> - RegisteredObjectBufferMap;
> -
> -/// Global access point for the JIT debugging interface designed for use with a
> -/// singleton toolbox. Handles thread-safe registration and deregistration of
> -/// object files that are in executable memory managed by the client of this
> -/// class.
> -class GDBJITRegistrar : public JITRegistrar {
> - /// A map of in-memory object files that have been registered with the
> - /// JIT interface.
> - RegisteredObjectBufferMap ObjectBufferMap;
> -
> -public:
> - /// Instantiates the JIT service.
> - GDBJITRegistrar() : ObjectBufferMap() {}
> -
> - /// Unregisters each object that was previously registered and releases all
> - /// internal resources.
> - virtual ~GDBJITRegistrar();
> -
> - /// Creates an entry in the JIT registry for the buffer @p Object,
> - /// which must contain an object file in executable memory with any
> - /// debug information for the debugger.
> - void registerObject(const ObjectBuffer &Object) override;
> -
> - /// Removes the internal registration of @p Object, and
> - /// frees associated resources.
> - /// Returns true if @p Object was found in ObjectBufferMap.
> - bool deregisterObject(const ObjectBuffer &Object) override;
> -
> -private:
> - /// Deregister the debug info for the given object file from the debugger
> - /// and delete any temporary copies. This private method does not remove
> - /// the function from Map so that it can be called while iterating over Map.
> - void deregisterObjectInternal(RegisteredObjectBufferMap::iterator I);
> -};
> -
> -/// Lock used to serialize all jit registration events, since they
> -/// modify global variables.
> -ManagedStatic<sys::Mutex> JITDebugLock;
> -
> -/// Do the registration.
> -void NotifyDebugger(jit_code_entry* JITCodeEntry) {
> - __jit_debug_descriptor.action_flag = JIT_REGISTER_FN;
> -
> - // Insert this entry at the head of the list.
> - JITCodeEntry->prev_entry = nullptr;
> - jit_code_entry* NextEntry = __jit_debug_descriptor.first_entry;
> - JITCodeEntry->next_entry = NextEntry;
> - if (NextEntry) {
> - NextEntry->prev_entry = JITCodeEntry;
> - }
> - __jit_debug_descriptor.first_entry = JITCodeEntry;
> - __jit_debug_descriptor.relevant_entry = JITCodeEntry;
> - __jit_debug_register_code();
> -}
> -
> -GDBJITRegistrar::~GDBJITRegistrar() {
> - // Free all registered object files.
> - llvm::MutexGuard locked(*JITDebugLock);
> - for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(), E = ObjectBufferMap.end();
> - I != E; ++I) {
> - // Call the private method that doesn't update the map so our iterator
> - // doesn't break.
> - deregisterObjectInternal(I);
> - }
> - ObjectBufferMap.clear();
> -}
> -
> -void GDBJITRegistrar::registerObject(const ObjectBuffer &Object) {
> -
> - const char *Buffer = Object.getBufferStart();
> - size_t Size = Object.getBufferSize();
> -
> - assert(Buffer && "Attempt to register a null object with a debugger.");
> - llvm::MutexGuard locked(*JITDebugLock);
> - assert(ObjectBufferMap.find(Buffer) == ObjectBufferMap.end() &&
> - "Second attempt to perform debug registration.");
> - jit_code_entry* JITCodeEntry = new jit_code_entry();
> -
> - if (!JITCodeEntry) {
> - llvm::report_fatal_error(
> - "Allocation failed when registering a JIT entry!\n");
> - } else {
> - JITCodeEntry->symfile_addr = Buffer;
> - JITCodeEntry->symfile_size = Size;
> -
> - ObjectBufferMap[Buffer] = std::make_pair(Size, JITCodeEntry);
> - NotifyDebugger(JITCodeEntry);
> - }
> -}
> -
> -bool GDBJITRegistrar::deregisterObject(const ObjectBuffer& Object) {
> - const char *Buffer = Object.getBufferStart();
> - llvm::MutexGuard locked(*JITDebugLock);
> - RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Buffer);
> -
> - if (I != ObjectBufferMap.end()) {
> - deregisterObjectInternal(I);
> - ObjectBufferMap.erase(I);
> - return true;
> - }
> - return false;
> -}
> -
> -void GDBJITRegistrar::deregisterObjectInternal(
> - RegisteredObjectBufferMap::iterator I) {
> -
> - jit_code_entry*& JITCodeEntry = I->second.second;
> -
> - // Do the unregistration.
> - {
> - __jit_debug_descriptor.action_flag = JIT_UNREGISTER_FN;
> -
> - // Remove the jit_code_entry from the linked list.
> - jit_code_entry* PrevEntry = JITCodeEntry->prev_entry;
> - jit_code_entry* NextEntry = JITCodeEntry->next_entry;
> -
> - if (NextEntry) {
> - NextEntry->prev_entry = PrevEntry;
> - }
> - if (PrevEntry) {
> - PrevEntry->next_entry = NextEntry;
> - }
> - else {
> - assert(__jit_debug_descriptor.first_entry == JITCodeEntry);
> - __jit_debug_descriptor.first_entry = NextEntry;
> - }
> -
> - // Tell the debugger which entry we removed, and unregister the code.
> - __jit_debug_descriptor.relevant_entry = JITCodeEntry;
> - __jit_debug_register_code();
> - }
> -
> - delete JITCodeEntry;
> - JITCodeEntry = nullptr;
> -}
> -
> -llvm::ManagedStatic<GDBJITRegistrar> TheRegistrar;
> -
> -} // end namespace
> -
> -namespace llvm {
> -
> -JITRegistrar& JITRegistrar::getGDBRegistrar() {
> - return *TheRegistrar;
> -}
> -
> -} // namespace llvm
>
> Copied: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp (from r222764, llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp)
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp?p2=llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp&p1=llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp&r1=222764&r2=222810&rev=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrar.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/GDBRegistrationListener.cpp Wed Nov 26 00:53:26 2014
> @@ -1,4 +1,4 @@
> -//===-- GDBRegistrar.cpp - Registers objects with GDB ---------------------===//
> +//===----- GDBRegistrationListener.cpp - Registers objects with GDB -------===//
> //
> // The LLVM Compiler Infrastructure
> //
> @@ -7,8 +7,9 @@
> //
> //===----------------------------------------------------------------------===//
>
> -#include "JITRegistrar.h"
> #include "llvm/ADT/DenseMap.h"
> +#include "llvm/ExecutionEngine/JITEventListener.h"
> +#include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/Compiler.h"
> #include "llvm/Support/ErrorHandling.h"
> #include "llvm/Support/Mutex.h"
> @@ -16,6 +17,7 @@
> #include "llvm/Support/ManagedStatic.h"
>
> using namespace llvm;
> +using namespace llvm::object;
>
> // This must be kept in sync with gdb/gdb/jit.h .
> extern "C" {
> @@ -60,37 +62,49 @@ extern "C" {
>
> namespace {
>
> +struct RegisteredObjectInfo {
> + RegisteredObjectInfo() {}
> +
> + RegisteredObjectInfo(std::size_t Size, jit_code_entry *Entry,
> + OwningBinary<ObjectFile> Obj)
> + : Size(Size), Entry(Entry), Obj(std::move(Obj)) {}
> +
> + std::size_t Size;
> + jit_code_entry *Entry;
> + OwningBinary<ObjectFile> Obj;
> +};
> +
> // Buffer for an in-memory object file in executable memory
> -typedef llvm::DenseMap< const char*,
> - std::pair<std::size_t, jit_code_entry*> >
> +typedef llvm::DenseMap< const char*, RegisteredObjectInfo>
> RegisteredObjectBufferMap;
>
> /// Global access point for the JIT debugging interface designed for use with a
> /// singleton toolbox. Handles thread-safe registration and deregistration of
> /// object files that are in executable memory managed by the client of this
> /// class.
> -class GDBJITRegistrar : public JITRegistrar {
> +class GDBJITRegistrationListener : public JITEventListener {
> /// A map of in-memory object files that have been registered with the
> /// JIT interface.
> RegisteredObjectBufferMap ObjectBufferMap;
>
> public:
> /// Instantiates the JIT service.
> - GDBJITRegistrar() : ObjectBufferMap() {}
> + GDBJITRegistrationListener() : ObjectBufferMap() {}
>
> /// Unregisters each object that was previously registered and releases all
> /// internal resources.
> - virtual ~GDBJITRegistrar();
> + virtual ~GDBJITRegistrationListener();
>
> /// Creates an entry in the JIT registry for the buffer @p Object,
> /// which must contain an object file in executable memory with any
> /// debug information for the debugger.
> - void registerObject(const ObjectBuffer &Object) override;
> + void NotifyObjectEmitted(const ObjectFile &Object,
> + const RuntimeDyld::LoadedObjectInfo &L) override;
>
> /// Removes the internal registration of @p Object, and
> /// frees associated resources.
> /// Returns true if @p Object was found in ObjectBufferMap.
> - bool deregisterObject(const ObjectBuffer &Object) override;
> + void NotifyFreeingObject(const ObjectFile &Object) override;
>
> private:
> /// Deregister the debug info for the given object file from the debugger
> @@ -119,10 +133,11 @@ void NotifyDebugger(jit_code_entry* JITC
> __jit_debug_register_code();
> }
>
> -GDBJITRegistrar::~GDBJITRegistrar() {
> +GDBJITRegistrationListener::~GDBJITRegistrationListener() {
> // Free all registered object files.
> llvm::MutexGuard locked(*JITDebugLock);
> - for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(), E = ObjectBufferMap.end();
> + for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(),
> + E = ObjectBufferMap.end();
> I != E; ++I) {
> // Call the private method that doesn't update the map so our iterator
> // doesn't break.
> @@ -131,14 +146,19 @@ GDBJITRegistrar::~GDBJITRegistrar() {
> ObjectBufferMap.clear();
> }
>
> -void GDBJITRegistrar::registerObject(const ObjectBuffer &Object) {
> +void GDBJITRegistrationListener::NotifyObjectEmitted(
> + const ObjectFile &Object,
> + const RuntimeDyld::LoadedObjectInfo &L) {
> +
> + OwningBinary<ObjectFile> DebugObj = L.getObjectForDebug(Object);
> + const char *Buffer = DebugObj.getBinary()->getMemoryBufferRef().getBufferStart();
> + size_t Size = DebugObj.getBinary()->getMemoryBufferRef().getBufferSize();
>
> - const char *Buffer = Object.getBufferStart();
> - size_t Size = Object.getBufferSize();
> + const char *Key = Object.getMemoryBufferRef().getBufferStart();
>
> - assert(Buffer && "Attempt to register a null object with a debugger.");
> + assert(Key && "Attempt to register a null object with a debugger.");
> llvm::MutexGuard locked(*JITDebugLock);
> - assert(ObjectBufferMap.find(Buffer) == ObjectBufferMap.end() &&
> + assert(ObjectBufferMap.find(Key) == ObjectBufferMap.end() &&
> "Second attempt to perform debug registration.");
> jit_code_entry* JITCodeEntry = new jit_code_entry();
>
> @@ -149,28 +169,27 @@ void GDBJITRegistrar::registerObject(con
> JITCodeEntry->symfile_addr = Buffer;
> JITCodeEntry->symfile_size = Size;
>
> - ObjectBufferMap[Buffer] = std::make_pair(Size, JITCodeEntry);
> + ObjectBufferMap[Key] = RegisteredObjectInfo(Size, JITCodeEntry,
> + std::move(DebugObj));
> NotifyDebugger(JITCodeEntry);
> }
> }
>
> -bool GDBJITRegistrar::deregisterObject(const ObjectBuffer& Object) {
> - const char *Buffer = Object.getBufferStart();
> +void GDBJITRegistrationListener::NotifyFreeingObject(const ObjectFile& Object) {
> + const char *Key = Object.getMemoryBufferRef().getBufferStart();
> llvm::MutexGuard locked(*JITDebugLock);
> - RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Buffer);
> + RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(Key);
>
> if (I != ObjectBufferMap.end()) {
> deregisterObjectInternal(I);
> ObjectBufferMap.erase(I);
> - return true;
> }
> - return false;
> }
>
> -void GDBJITRegistrar::deregisterObjectInternal(
> +void GDBJITRegistrationListener::deregisterObjectInternal(
> RegisteredObjectBufferMap::iterator I) {
>
> - jit_code_entry*& JITCodeEntry = I->second.second;
> + jit_code_entry*& JITCodeEntry = I->second.Entry;
>
> // Do the unregistration.
> {
> @@ -200,14 +219,14 @@ void GDBJITRegistrar::deregisterObjectIn
> JITCodeEntry = nullptr;
> }
>
> -llvm::ManagedStatic<GDBJITRegistrar> TheRegistrar;
> +llvm::ManagedStatic<GDBJITRegistrationListener> GDBRegListener;
>
> } // end namespace
>
> namespace llvm {
>
> -JITRegistrar& JITRegistrar::getGDBRegistrar() {
> - return *TheRegistrar;
> +JITEventListener* JITEventListener::createGDBRegistrationListener() {
> + return &*GDBRegListener;
> }
>
> } // namespace llvm
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/JITRegistrar.h (removed)
> @@ -1,44 +0,0 @@
> -//===-- JITRegistrar.h - Registers objects with a debugger ----------------===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_JITREGISTRAR_H
> -#define LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_JITREGISTRAR_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -
> -namespace llvm {
> -
> -/// Global access point for the JIT debugging interface.
> -class JITRegistrar {
> - virtual void anchor();
> -public:
> - /// Instantiates the JIT service.
> - JITRegistrar() {}
> -
> - /// Unregisters each object that was previously registered and releases all
> - /// internal resources.
> - virtual ~JITRegistrar() {}
> -
> - /// Creates an entry in the JIT registry for the buffer @p Object,
> - /// which must contain an object file in executable memory with any
> - /// debug information for the debugger.
> - virtual void registerObject(const ObjectBuffer &Object) = 0;
> -
> - /// Removes the internal registration of @p Object, and
> - /// frees associated resources.
> - /// Returns true if @p Object was previously registered.
> - virtual bool deregisterObject(const ObjectBuffer &Object) = 0;
> -
> - /// Returns a reference to a GDB JIT registrar singleton
> - static JITRegistrar& getGDBRegistrar();
> -};
> -
> -} // end namespace llvm
> -
> -#endif
>
> Removed: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h?rev=222809&view=auto
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/ObjectImageCommon.h (removed)
> @@ -1,86 +0,0 @@
> -//===-- ObjectImageCommon.h - Format independent executuable object image -===//
> -//
> -// The LLVM Compiler Infrastructure
> -//
> -// This file is distributed under the University of Illinois Open Source
> -// License. See LICENSE.TXT for details.
> -//
> -//===----------------------------------------------------------------------===//
> -//
> -// This file declares a file format independent ObjectImage class.
> -//
> -//===----------------------------------------------------------------------===//
> -
> -#ifndef LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_OBJECTIMAGECOMMON_H
> -#define LLVM_LIB_EXECUTIONENGINE_RUNTIMEDYLD_OBJECTIMAGECOMMON_H
> -
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> -#include "llvm/Object/ObjectFile.h"
> -
> -#include <memory>
> -
> -namespace llvm {
> -
> -namespace object {
> - class ObjectFile;
> -}
> -
> -class ObjectImageCommon : public ObjectImage {
> - ObjectImageCommon(); // = delete
> - ObjectImageCommon(const ObjectImageCommon &other); // = delete
> - void anchor() override;
> -
> -protected:
> - std::unique_ptr<object::ObjectFile> ObjFile;
> -
> - // This form of the constructor allows subclasses to use
> - // format-specific subclasses of ObjectFile directly
> - ObjectImageCommon(std::unique_ptr<ObjectBuffer> Input,
> - std::unique_ptr<object::ObjectFile> Obj)
> - : ObjectImage(std::move(Input)), ObjFile(std::move(Obj)) {}
> -
> -public:
> - ObjectImageCommon(std::unique_ptr<ObjectBuffer> Input)
> - : ObjectImage(std::move(Input)) {
> - // FIXME: error checking? createObjectFile returns an ErrorOr<ObjectFile*>
> - // and should probably be checked for failure.
> - MemoryBufferRef Buf = Buffer->getMemBuffer();
> - ObjFile = std::move(object::ObjectFile::createObjectFile(Buf).get());
> - }
> - ObjectImageCommon(std::unique_ptr<object::ObjectFile> Input)
> - : ObjectImage(nullptr), ObjFile(std::move(Input)) {}
> - virtual ~ObjectImageCommon() { }
> -
> - object::symbol_iterator begin_symbols() const override
> - { return ObjFile->symbol_begin(); }
> - object::symbol_iterator end_symbols() const override
> - { return ObjFile->symbol_end(); }
> -
> - object::section_iterator begin_sections() const override
> - { return ObjFile->section_begin(); }
> - object::section_iterator end_sections() const override
> - { return ObjFile->section_end(); }
> -
> - /* Triple::ArchType */ unsigned getArch() const override
> - { return ObjFile->getArch(); }
> -
> - StringRef getData() const override { return ObjFile->getData(); }
> -
> - object::ObjectFile* getObjectFile() const override { return ObjFile.get(); }
> -
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - void updateSectionAddress(const object::SectionRef &Sec,
> - uint64_t Addr) override {}
> - void updateSymbolAddress(const object::SymbolRef &Sym,
> - uint64_t Addr) override {}
> -
> - // Subclasses can override these methods to provide JIT debugging support
> - void registerWithDebugger() override {}
> - void deregisterWithDebugger() override {}
> -};
> -
> -} // end namespace llvm
> -
> -#endif
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyld.cpp Wed Nov 26 00:53:26 2014
> @@ -12,8 +12,6 @@
> //===----------------------------------------------------------------------===//
>
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> -#include "JITRegistrar.h"
> -#include "ObjectImageCommon.h"
> #include "RuntimeDyldCheckerImpl.h"
> #include "RuntimeDyldELF.h"
> #include "RuntimeDyldImpl.h"
> @@ -30,10 +28,8 @@ using namespace llvm::object;
> // Empty out-of-line virtual destructor as the key function.
> RuntimeDyldImpl::~RuntimeDyldImpl() {}
>
> -// Pin the JITRegistrar's and ObjectImage*'s vtables to this file.
> -void JITRegistrar::anchor() {}
> -void ObjectImage::anchor() {}
> -void ObjectImageCommon::anchor() {}
> +// Pin LoadedObjectInfo's vtables to this file.
> +void RuntimeDyld::LoadedObjectInfo::anchor() {}
>
> namespace llvm {
>
> @@ -139,22 +135,23 @@ static std::error_code getOffset(const S
> return object_error::success;
> }
>
> -std::unique_ptr<ObjectImage>
> -RuntimeDyldImpl::loadObject(std::unique_ptr<ObjectImage> Obj) {
> +std::pair<unsigned, unsigned>
> +RuntimeDyldImpl::loadObjectImpl(const object::ObjectFile &Obj) {
> MutexGuard locked(lock);
>
> - if (!Obj)
> - return nullptr;
> + // Grab the first Section ID. We'll use this later to construct the underlying
> + // range for the returned LoadedObjectInfo.
> + unsigned SectionsAddedBeginIdx = Sections.size();
>
> // Save information about our target
> - Arch = (Triple::ArchType)Obj->getArch();
> - IsTargetLittleEndian = Obj->getObjectFile()->isLittleEndian();
> + Arch = (Triple::ArchType)Obj.getArch();
> + IsTargetLittleEndian = Obj.isLittleEndian();
>
> // Compute the memory size required to load all sections to be loaded
> // and pass this information to the memory manager
> if (MemMgr->needsToReserveAllocationSpace()) {
> uint64_t CodeSize = 0, DataSizeRO = 0, DataSizeRW = 0;
> - computeTotalAllocSize(*Obj, CodeSize, DataSizeRO, DataSizeRW);
> + computeTotalAllocSize(Obj, CodeSize, DataSizeRO, DataSizeRW);
> MemMgr->reserveAllocationSpace(CodeSize, DataSizeRO, DataSizeRW);
> }
>
> @@ -170,7 +167,7 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> // Parse symbols
> DEBUG(dbgs() << "Parse symbols:\n");
> - for (symbol_iterator I = Obj->begin_symbols(), E = Obj->end_symbols(); I != E;
> + for (symbol_iterator I = Obj.symbol_begin(), E = Obj.symbol_end(); I != E;
> ++I) {
> object::SymbolRef::Type SymType;
> StringRef Name;
> @@ -196,15 +193,15 @@ RuntimeDyldImpl::loadObject(std::unique_
> SymType == object::SymbolRef::ST_Unknown) {
> uint64_t SectOffset;
> StringRef SectionData;
> - section_iterator SI = Obj->end_sections();
> + section_iterator SI = Obj.section_end();
> Check(getOffset(*I, SectOffset));
> Check(I->getSection(SI));
> - if (SI == Obj->end_sections())
> + if (SI == Obj.section_end())
> continue;
> Check(SI->getContents(SectionData));
> bool IsCode = SI->isText();
> unsigned SectionID =
> - findOrEmitSection(*Obj, *SI, IsCode, LocalSections);
> + findOrEmitSection(Obj, *SI, IsCode, LocalSections);
> LocalSymbols[Name.data()] = SymbolLoc(SectionID, SectOffset);
> DEBUG(dbgs() << "\tOffset: " << format("%p", (uintptr_t)SectOffset)
> << " flags: " << Flags << " SID: " << SectionID);
> @@ -216,11 +213,11 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> // Allocate common symbols
> if (CommonSize != 0)
> - emitCommonSymbols(*Obj, CommonSymbols, CommonSize, GlobalSymbolTable);
> + emitCommonSymbols(Obj, CommonSymbols, CommonSize, GlobalSymbolTable);
>
> // Parse and process relocations
> DEBUG(dbgs() << "Parse relocations:\n");
> - for (section_iterator SI = Obj->begin_sections(), SE = Obj->end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> unsigned SectionID = 0;
> StubMap Stubs;
> @@ -234,23 +231,25 @@ RuntimeDyldImpl::loadObject(std::unique_
>
> bool IsCode = RelocatedSection->isText();
> SectionID =
> - findOrEmitSection(*Obj, *RelocatedSection, IsCode, LocalSections);
> + findOrEmitSection(Obj, *RelocatedSection, IsCode, LocalSections);
> DEBUG(dbgs() << "\tSectionID: " << SectionID << "\n");
>
> for (; I != E;)
> - I = processRelocationRef(SectionID, I, *Obj, LocalSections, LocalSymbols,
> + I = processRelocationRef(SectionID, I, Obj, LocalSections, LocalSymbols,
> Stubs);
>
> // If there is an attached checker, notify it about the stubs for this
> // section so that they can be verified.
> if (Checker)
> - Checker->registerStubMap(Obj->getImageName(), SectionID, Stubs);
> + Checker->registerStubMap(Obj.getFileName(), SectionID, Stubs);
> }
>
> // Give the subclasses a chance to tie-up any loose ends.
> - finalizeLoad(*Obj, LocalSections);
> + finalizeLoad(Obj, LocalSections);
>
> - return Obj;
> + unsigned SectionsAddedEndIdx = Sections.size();
> +
> + return std::make_pair(SectionsAddedBeginIdx, SectionsAddedEndIdx);
> }
>
> // A helper method for computeTotalAllocSize.
> @@ -270,7 +269,7 @@ computeAllocationSizeForSections(std::ve
>
> // Compute an upper bound of the memory size that is required to load all
> // sections
> -void RuntimeDyldImpl::computeTotalAllocSize(ObjectImage &Obj,
> +void RuntimeDyldImpl::computeTotalAllocSize(const ObjectFile &Obj,
> uint64_t &CodeSize,
> uint64_t &DataSizeRO,
> uint64_t &DataSizeRW) {
> @@ -282,7 +281,7 @@ void RuntimeDyldImpl::computeTotalAllocS
>
> // Collect sizes of all sections to be loaded;
> // also determine the max alignment of all sections
> - for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> const SectionRef &Section = *SI;
>
> @@ -328,7 +327,7 @@ void RuntimeDyldImpl::computeTotalAllocS
>
> // Compute the size of all common symbols
> uint64_t CommonSize = 0;
> - for (symbol_iterator I = Obj.begin_symbols(), E = Obj.end_symbols(); I != E;
> + for (symbol_iterator I = Obj.symbol_begin(), E = Obj.symbol_end(); I != E;
> ++I) {
> uint32_t Flags = I->getFlags();
> if (Flags & SymbolRef::SF_Common) {
> @@ -353,7 +352,7 @@ void RuntimeDyldImpl::computeTotalAllocS
> }
>
> // compute stub buffer size for the given section
> -unsigned RuntimeDyldImpl::computeSectionStubBufSize(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::computeSectionStubBufSize(const ObjectFile &Obj,
> const SectionRef &Section) {
> unsigned StubSize = getMaxStubSize();
> if (StubSize == 0) {
> @@ -363,7 +362,7 @@ unsigned RuntimeDyldImpl::computeSection
> // necessary section allocation size in loadObject by walking all the sections
> // once.
> unsigned StubBufSize = 0;
> - for (section_iterator SI = Obj.begin_sections(), SE = Obj.end_sections();
> + for (section_iterator SI = Obj.section_begin(), SE = Obj.section_end();
> SI != SE; ++SI) {
> section_iterator RelSecI = SI->getRelocatedSection();
> if (!(RelSecI == Section))
> @@ -418,7 +417,7 @@ void RuntimeDyldImpl::writeBytesUnaligne
> }
> }
>
> -void RuntimeDyldImpl::emitCommonSymbols(ObjectImage &Obj,
> +void RuntimeDyldImpl::emitCommonSymbols(const ObjectFile &Obj,
> const CommonSymbolMap &CommonSymbols,
> uint64_t TotalSize,
> SymbolTableMap &SymbolTable) {
> @@ -450,14 +449,13 @@ void RuntimeDyldImpl::emitCommonSymbols(
> DEBUG(dbgs() << "Allocating common symbol " << Name << " address "
> << format("%p\n", Addr));
> }
> - Obj.updateSymbolAddress(it->first, (uint64_t)Addr);
> SymbolTable[Name.data()] = SymbolLoc(SectionID, Offset);
> Offset += Size;
> Addr += Size;
> }
> }
>
> -unsigned RuntimeDyldImpl::emitSection(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::emitSection(const ObjectFile &Obj,
> const SectionRef &Section, bool IsCode) {
>
> StringRef data;
> @@ -521,7 +519,6 @@ unsigned RuntimeDyldImpl::emitSection(Ob
> << " new addr: " << format("%p", Addr)
> << " DataSize: " << DataSize << " StubBufSize: " << StubBufSize
> << " Allocate: " << Allocate << "\n");
> - Obj.updateSectionAddress(Section, (uint64_t)Addr);
> } else {
> // Even if we didn't load the section, we need to record an entry for it
> // to handle later processing (and by 'handle' I mean don't do anything
> @@ -537,12 +534,12 @@ unsigned RuntimeDyldImpl::emitSection(Ob
> Sections.push_back(SectionEntry(Name, Addr, DataSize, (uintptr_t)pData));
>
> if (Checker)
> - Checker->registerSection(Obj.getImageName(), SectionID);
> + Checker->registerSection(Obj.getFileName(), SectionID);
>
> return SectionID;
> }
>
> -unsigned RuntimeDyldImpl::findOrEmitSection(ObjectImage &Obj,
> +unsigned RuntimeDyldImpl::findOrEmitSection(const ObjectFile &Obj,
> const SectionRef &Section,
> bool IsCode,
> ObjSectionToIDMap &LocalSections) {
> @@ -739,6 +736,16 @@ void RuntimeDyldImpl::resolveExternalSym
>
> //===----------------------------------------------------------------------===//
> // RuntimeDyld class implementation
> +
> +uint64_t RuntimeDyld::LoadedObjectInfo::getSectionLoadAddress(
> + StringRef SectionName) const {
> + for (unsigned I = BeginIdx; I != EndIdx; ++I)
> + if (RTDyld.Sections[I].Name == SectionName)
> + return RTDyld.Sections[I].LoadAddress;
> +
> + return 0;
> +}
> +
> RuntimeDyld::RuntimeDyld(RTDyldMemoryManager *mm) {
> // FIXME: There's a potential issue lurking here if a single instance of
> // RuntimeDyld is used to load multiple objects. The current implementation
> @@ -772,78 +779,23 @@ createRuntimeDyldMachO(Triple::ArchType
> return Dyld;
> }
>
> -std::unique_ptr<ObjectImage>
> -RuntimeDyld::loadObject(std::unique_ptr<ObjectFile> InputObject) {
> - std::unique_ptr<ObjectImage> InputImage;
> -
> - ObjectFile &Obj = *InputObject;
> -
> - if (InputObject->isELF()) {
> - InputImage.reset(RuntimeDyldELF::createObjectImageFromFile(std::move(InputObject)));
> - if (!Dyld)
> - Dyld = createRuntimeDyldELF(MM, ProcessAllSections, Checker);
> - } else if (InputObject->isMachO()) {
> - InputImage.reset(RuntimeDyldMachO::createObjectImageFromFile(std::move(InputObject)));
> - if (!Dyld)
> - Dyld = createRuntimeDyldMachO(
> - static_cast<Triple::ArchType>(InputImage->getArch()), MM,
> - ProcessAllSections, Checker);
> - } else
> - report_fatal_error("Incompatible object format!");
> -
> - if (!Dyld->isCompatibleFile(&Obj))
> - report_fatal_error("Incompatible object format!");
> -
> - return Dyld->loadObject(std::move(InputImage));
> -}
> -
> -std::unique_ptr<ObjectImage>
> -RuntimeDyld::loadObject(std::unique_ptr<ObjectBuffer> InputBuffer) {
> - std::unique_ptr<ObjectImage> InputImage;
> - sys::fs::file_magic Type = sys::fs::identify_magic(InputBuffer->getBuffer());
> - auto *InputBufferPtr = InputBuffer.get();
> -
> - switch (Type) {
> - case sys::fs::file_magic::elf:
> - case sys::fs::file_magic::elf_relocatable:
> - case sys::fs::file_magic::elf_executable:
> - case sys::fs::file_magic::elf_shared_object:
> - case sys::fs::file_magic::elf_core:
> - InputImage = RuntimeDyldELF::createObjectImage(std::move(InputBuffer));
> - if (!Dyld)
> +std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> +RuntimeDyld::loadObject(const ObjectFile &Obj) {
> + if (!Dyld) {
> + if (Obj.isELF())
> Dyld = createRuntimeDyldELF(MM, ProcessAllSections, Checker);
> - break;
> - case sys::fs::file_magic::macho_object:
> - case sys::fs::file_magic::macho_executable:
> - case sys::fs::file_magic::macho_fixed_virtual_memory_shared_lib:
> - case sys::fs::file_magic::macho_core:
> - case sys::fs::file_magic::macho_preload_executable:
> - case sys::fs::file_magic::macho_dynamically_linked_shared_lib:
> - case sys::fs::file_magic::macho_dynamic_linker:
> - case sys::fs::file_magic::macho_bundle:
> - case sys::fs::file_magic::macho_dynamically_linked_shared_lib_stub:
> - case sys::fs::file_magic::macho_dsym_companion:
> - InputImage = RuntimeDyldMachO::createObjectImage(std::move(InputBuffer));
> - if (!Dyld)
> + else if (Obj.isMachO())
> Dyld = createRuntimeDyldMachO(
> - static_cast<Triple::ArchType>(InputImage->getArch()), MM,
> - ProcessAllSections, Checker);
> - break;
> - case sys::fs::file_magic::unknown:
> - case sys::fs::file_magic::bitcode:
> - case sys::fs::file_magic::archive:
> - case sys::fs::file_magic::coff_object:
> - case sys::fs::file_magic::coff_import_library:
> - case sys::fs::file_magic::pecoff_executable:
> - case sys::fs::file_magic::macho_universal_binary:
> - case sys::fs::file_magic::windows_resource:
> - report_fatal_error("Incompatible object format!");
> + static_cast<Triple::ArchType>(Obj.getArch()), MM,
> + ProcessAllSections, Checker);
> + else
> + report_fatal_error("Incompatible object format!");
> }
>
> - if (!Dyld->isCompatibleFormat(InputBufferPtr))
> + if (!Dyld->isCompatibleFile(Obj))
> report_fatal_error("Incompatible object format!");
>
> - return Dyld->loadObject(std::move(InputImage));
> + return Dyld->loadObject(Obj);
> }
>
> void *RuntimeDyld::getSymbolAddress(StringRef Name) const {
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.cpp Wed Nov 26 00:53:26 2014
> @@ -12,27 +12,23 @@
> //===----------------------------------------------------------------------===//
>
> #include "RuntimeDyldELF.h"
> -#include "JITRegistrar.h"
> -#include "ObjectImageCommon.h"
> #include "llvm/ADT/IntervalMap.h"
> #include "llvm/ADT/STLExtras.h"
> #include "llvm/ADT/StringRef.h"
> #include "llvm/ADT/Triple.h"
> -#include "llvm/ExecutionEngine/ObjectBuffer.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> +#include "llvm/MC/MCStreamer.h"
> #include "llvm/Object/ELFObjectFile.h"
> #include "llvm/Object/ObjectFile.h"
> #include "llvm/Support/ELF.h"
> #include "llvm/Support/Endian.h"
> #include "llvm/Support/MemoryBuffer.h"
> +#include "llvm/Support/TargetRegistry.h"
>
> using namespace llvm;
> using namespace llvm::object;
>
> #define DEBUG_TYPE "dyld"
>
> -namespace {
> -
> static inline std::error_code check(std::error_code Err) {
> if (Err) {
> report_fatal_error(Err.message());
> @@ -40,6 +36,8 @@ static inline std::error_code check(std:
> return Err;
> }
>
> +namespace {
> +
> template <class ELFT> class DyldELFObject : public ELFObjectFile<ELFT> {
> LLVM_ELF_IMPORT_TYPES_ELFT(ELFT)
>
> @@ -52,16 +50,12 @@ template <class ELFT> class DyldELFObjec
>
> typedef typename ELFDataTypeTypedefHelper<ELFT>::value_type addr_type;
>
> - std::unique_ptr<ObjectFile> UnderlyingFile;
> -
> public:
> - DyldELFObject(std::unique_ptr<ObjectFile> UnderlyingFile,
> - MemoryBufferRef Wrapper, std::error_code &ec);
> -
> DyldELFObject(MemoryBufferRef Wrapper, std::error_code &ec);
>
> void updateSectionAddress(const SectionRef &Sec, uint64_t Addr);
> - void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr);
> +
> + void updateSymbolAddress(const SymbolRef &SymRef, uint64_t Addr);
>
> // Methods for type inquiry through isa, cast and dyn_cast
> static inline bool classof(const Binary *v) {
> @@ -71,42 +65,10 @@ public:
> static inline bool classof(const ELFObjectFile<ELFT> *v) {
> return v->isDyldType();
> }
> -};
> -
> -template <class ELFT> class ELFObjectImage : public ObjectImageCommon {
> - bool Registered;
>
> -public:
> - ELFObjectImage(std::unique_ptr<ObjectBuffer> Input,
> - std::unique_ptr<DyldELFObject<ELFT>> Obj)
> - : ObjectImageCommon(std::move(Input), std::move(Obj)), Registered(false) {
> - }
> -
> - virtual ~ELFObjectImage() {
> - if (Registered)
> - deregisterWithDebugger();
> - }
> +};
>
> - // Subclasses can override these methods to update the image with loaded
> - // addresses for sections and common symbols
> - void updateSectionAddress(const SectionRef &Sec, uint64_t Addr) override {
> - static_cast<DyldELFObject<ELFT>*>(getObjectFile())
> - ->updateSectionAddress(Sec, Addr);
> - }
>
> - void updateSymbolAddress(const SymbolRef &Sym, uint64_t Addr) override {
> - static_cast<DyldELFObject<ELFT>*>(getObjectFile())
> - ->updateSymbolAddress(Sym, Addr);
> - }
> -
> - void registerWithDebugger() override {
> - JITRegistrar::getGDBRegistrar().registerObject(*Buffer);
> - Registered = true;
> - }
> - void deregisterWithDebugger() override {
> - JITRegistrar::getGDBRegistrar().deregisterObject(*Buffer);
> - }
> -};
>
> // The MemoryBuffer passed into this constructor is just a wrapper around the
> // actual memory. Ultimately, the Binary parent class will take ownership of
> @@ -118,14 +80,6 @@ DyldELFObject<ELFT>::DyldELFObject(Memor
> }
>
> template <class ELFT>
> -DyldELFObject<ELFT>::DyldELFObject(std::unique_ptr<ObjectFile> UnderlyingFile,
> - MemoryBufferRef Wrapper, std::error_code &EC)
> - : ELFObjectFile<ELFT>(Wrapper, EC),
> - UnderlyingFile(std::move(UnderlyingFile)) {
> - this->isDyldELFObject = true;
> -}
> -
> -template <class ELFT>
> void DyldELFObject<ELFT>::updateSectionAddress(const SectionRef &Sec,
> uint64_t Addr) {
> DataRefImpl ShdrRef = Sec.getRawDataRefImpl();
> @@ -149,10 +103,89 @@ void DyldELFObject<ELFT>::updateSymbolAd
> sym->st_value = static_cast<addr_type>(Addr);
> }
>
> +class LoadedELFObjectInfo : public RuntimeDyld::LoadedObjectInfo {
> +public:
> + LoadedELFObjectInfo(RuntimeDyldImpl &RTDyld, unsigned BeginIdx,
> + unsigned EndIdx)
> + : RuntimeDyld::LoadedObjectInfo(RTDyld, BeginIdx, EndIdx) {}
> +
> + OwningBinary<ObjectFile>
> + getObjectForDebug(const ObjectFile &Obj) const override;
> +};
> +
> +template <typename ELFT>
> +std::unique_ptr<DyldELFObject<ELFT>>
> +createRTDyldELFObject(MemoryBufferRef Buffer,
> + const LoadedELFObjectInfo &L,
> + std::error_code &ec) {
> + typedef typename ELFFile<ELFT>::Elf_Shdr Elf_Shdr;
> + typedef typename ELFDataTypeTypedefHelper<ELFT>::value_type addr_type;
> +
> + std::unique_ptr<DyldELFObject<ELFT>> Obj =
> + llvm::make_unique<DyldELFObject<ELFT>>(Buffer, ec);
> +
> + // Iterate over all sections in the object.
> + for (const auto &Sec : Obj->sections()) {
> + StringRef SectionName;
> + Sec.getName(SectionName);
> + if (SectionName != "") {
> + DataRefImpl ShdrRef = Sec.getRawDataRefImpl();
> + Elf_Shdr *shdr = const_cast<Elf_Shdr *>(
> + reinterpret_cast<const Elf_Shdr *>(ShdrRef.p));
> +
> + if (uint64_t SecLoadAddr = L.getSectionLoadAddress(SectionName)) {
> + // This assumes that the address passed in matches the target address
> + // bitness. The template-based type cast handles everything else.
> + shdr->sh_addr = static_cast<addr_type>(SecLoadAddr);
> + }
> + }
> + }
> +
> + return Obj;
> +}
> +
> +OwningBinary<ObjectFile> createELFDebugObject(const ObjectFile &Obj,
> + const LoadedELFObjectInfo &L) {
> + assert(Obj.isELF() && "Not an ELF object file.");
> +
> + std::unique_ptr<MemoryBuffer> Buffer =
> + MemoryBuffer::getMemBufferCopy(Obj.getData(), Obj.getFileName());
> +
> + std::error_code ec;
> +
> + std::unique_ptr<ObjectFile> DebugObj;
> + if (Obj.getBytesInAddress() == 4 && Obj.isLittleEndian()) {
> + typedef ELFType<support::little, 2, false> ELF32LE;
> + DebugObj = createRTDyldELFObject<ELF32LE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 4 && !Obj.isLittleEndian()) {
> + typedef ELFType<support::big, 2, false> ELF32BE;
> + DebugObj = createRTDyldELFObject<ELF32BE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 8 && !Obj.isLittleEndian()) {
> + typedef ELFType<support::big, 2, true> ELF64BE;
> + DebugObj = createRTDyldELFObject<ELF64BE>(Buffer->getMemBufferRef(), L, ec);
> + } else if (Obj.getBytesInAddress() == 8 && Obj.isLittleEndian()) {
> + typedef ELFType<support::little, 2, true> ELF64LE;
> + DebugObj = createRTDyldELFObject<ELF64LE>(Buffer->getMemBufferRef(), L, ec);
> + } else
> + llvm_unreachable("Unexpected ELF format");
> +
> + assert(!ec && "Could not construct copy ELF object file");
> +
> + return OwningBinary<ObjectFile>(std::move(DebugObj), std::move(Buffer));
> +}
> +
> +OwningBinary<ObjectFile>
> +LoadedELFObjectInfo::getObjectForDebug(const ObjectFile &Obj) const {
> + return createELFDebugObject(Obj, *this);
> +}
> +
> } // namespace
>
> namespace llvm {
>
> +RuntimeDyldELF::RuntimeDyldELF(RTDyldMemoryManager *mm) : RuntimeDyldImpl(mm) {}
> +RuntimeDyldELF::~RuntimeDyldELF() {}
> +
> void RuntimeDyldELF::registerEHFrames() {
> if (!MemMgr)
> return;
> @@ -180,83 +213,14 @@ void RuntimeDyldELF::deregisterEHFrames(
> RegisteredEHFrameSections.clear();
> }
>
> -ObjectImage *
> -RuntimeDyldELF::createObjectImageFromFile(std::unique_ptr<object::ObjectFile> ObjFile) {
> - if (!ObjFile)
> - return nullptr;
> -
> - std::error_code ec;
> - MemoryBufferRef Buffer = ObjFile->getMemoryBufferRef();
> -
> - if (ObjFile->getBytesInAddress() == 4 && ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 2, false>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::little, 2, false>>(
> - nullptr, std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 4 && !ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::big, 2, false>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::big, 2, false>>(nullptr, std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 8 && !ObjFile->isLittleEndian()) {
> - auto Obj = llvm::make_unique<DyldELFObject<ELFType<support::big, 2, true>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::big, 2, true>>(nullptr,
> - std::move(Obj));
> - } else if (ObjFile->getBytesInAddress() == 8 && ObjFile->isLittleEndian()) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 2, true>>>(
> - std::move(ObjFile), Buffer, ec);
> - return new ELFObjectImage<ELFType<support::little, 2, true>>(
> - nullptr, std::move(Obj));
> - } else
> - llvm_unreachable("Unexpected ELF format");
> -}
> -
> -std::unique_ptr<ObjectImage>
> -RuntimeDyldELF::createObjectImage(std::unique_ptr<ObjectBuffer> Buffer) {
> - if (Buffer->getBufferSize() < ELF::EI_NIDENT)
> - llvm_unreachable("Unexpected ELF object size");
> - std::pair<unsigned char, unsigned char> Ident =
> - std::make_pair((uint8_t)Buffer->getBufferStart()[ELF::EI_CLASS],
> - (uint8_t)Buffer->getBufferStart()[ELF::EI_DATA]);
> - std::error_code ec;
> -
> - MemoryBufferRef Buf = Buffer->getMemBuffer();
> -
> - if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2LSB) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 4, false>>>(
> - Buf, ec);
> - return llvm::make_unique<
> - ELFObjectImage<ELFType<support::little, 4, false>>>(std::move(Buffer),
> - std::move(Obj));
> - }
> - if (Ident.first == ELF::ELFCLASS32 && Ident.second == ELF::ELFDATA2MSB) {
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::big, 4, false>>>(Buf,
> - ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::big, 4, false>>>(
> - std::move(Buffer), std::move(Obj));
> - }
> - if (Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2MSB) {
> - auto Obj = llvm::make_unique<DyldELFObject<ELFType<support::big, 8, true>>>(
> - Buf, ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::big, 8, true>>>(
> - std::move(Buffer), std::move(Obj));
> - }
> - assert(Ident.first == ELF::ELFCLASS64 && Ident.second == ELF::ELFDATA2LSB &&
> - "Unexpected ELF format");
> - auto Obj =
> - llvm::make_unique<DyldELFObject<ELFType<support::little, 8, true>>>(Buf,
> - ec);
> - return llvm::make_unique<ELFObjectImage<ELFType<support::little, 8, true>>>(
> - std::move(Buffer), std::move(Obj));
> +std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> +RuntimeDyldELF::loadObject(const object::ObjectFile &O) {
> + unsigned SectionStartIdx, SectionEndIdx;
> + std::tie(SectionStartIdx, SectionEndIdx) = loadObjectImpl(O);
> + return llvm::make_unique<LoadedELFObjectInfo>(*this, SectionStartIdx,
> + SectionEndIdx);
> }
>
> -RuntimeDyldELF::~RuntimeDyldELF() {}
> -
> void RuntimeDyldELF::resolveX86_64Relocation(const SectionEntry &Section,
> uint64_t Offset, uint64_t Value,
> uint32_t Type, int64_t Addend,
> @@ -615,7 +579,7 @@ void RuntimeDyldELF::resolveMIPSRelocati
> }
>
> // Return the .TOC. section and offset.
> -void RuntimeDyldELF::findPPC64TOCSection(ObjectImage &Obj,
> +void RuntimeDyldELF::findPPC64TOCSection(const ObjectFile &Obj,
> ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel) {
> // Set a default SectionID in case we do not find a TOC section below.
> @@ -628,7 +592,7 @@ void RuntimeDyldELF::findPPC64TOCSection
>
> // The TOC consists of sections .got, .toc, .tocbss, .plt in that
> // order. The TOC starts where the first of these sections starts.
> - for (section_iterator si = Obj.begin_sections(), se = Obj.end_sections();
> + for (section_iterator si = Obj.section_begin(), se = Obj.section_end();
> si != se; ++si) {
>
> StringRef SectionName;
> @@ -650,15 +614,15 @@ void RuntimeDyldELF::findPPC64TOCSection
>
> // Returns the sections and offset associated with the ODP entry referenced
> // by Symbol.
> -void RuntimeDyldELF::findOPDEntrySection(ObjectImage &Obj,
> +void RuntimeDyldELF::findOPDEntrySection(const ObjectFile &Obj,
> ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel) {
> // Get the ELF symbol value (st_value) to compare with Relocation offset in
> // .opd entries
> - for (section_iterator si = Obj.begin_sections(), se = Obj.end_sections();
> + for (section_iterator si = Obj.section_begin(), se = Obj.section_end();
> si != se; ++si) {
> section_iterator RelSecI = si->getRelocatedSection();
> - if (RelSecI == Obj.end_sections())
> + if (RelSecI == Obj.section_end())
> continue;
>
> StringRef RelSectionName;
> @@ -700,7 +664,7 @@ void RuntimeDyldELF::findOPDEntrySection
> if (Rel.Addend != (int64_t)TargetSymbolOffset)
> continue;
>
> - section_iterator tsi(Obj.end_sections());
> + section_iterator tsi(Obj.section_end());
> check(TargetSymbol->getSection(tsi));
> bool IsCode = tsi->isText();
> Rel.SectionID = findOrEmitSection(Obj, (*tsi), IsCode, LocalSections);
> @@ -935,7 +899,8 @@ void RuntimeDyldELF::resolveRelocation(c
> }
>
> relocation_iterator RuntimeDyldELF::processRelocationRef(
> - unsigned SectionID, relocation_iterator RelI, ObjectImage &Obj,
> + unsigned SectionID, relocation_iterator RelI,
> + const ObjectFile &Obj,
> ObjSectionToIDMap &ObjSectionToID, const SymbolTableMap &Symbols,
> StubMap &Stubs) {
> uint64_t RelType;
> @@ -946,7 +911,7 @@ relocation_iterator RuntimeDyldELF::proc
>
> // Obtain the symbol name which is referenced in the relocation
> StringRef TargetName;
> - if (Symbol != Obj.end_symbols())
> + if (Symbol != Obj.symbol_end())
> Symbol->getName(TargetName);
> DEBUG(dbgs() << "\t\tRelType: " << RelType << " Addend: " << Addend
> << " TargetName: " << TargetName << "\n");
> @@ -954,7 +919,7 @@ relocation_iterator RuntimeDyldELF::proc
> // First search for the symbol in the local symbol table
> SymbolTableMap::const_iterator lsi = Symbols.end();
> SymbolRef::Type SymType = SymbolRef::ST_Unknown;
> - if (Symbol != Obj.end_symbols()) {
> + if (Symbol != Obj.symbol_end()) {
> lsi = Symbols.find(TargetName.data());
> Symbol->getType(SymType);
> }
> @@ -965,7 +930,7 @@ relocation_iterator RuntimeDyldELF::proc
> } else {
> // Search for the symbol in the global symbol table
> SymbolTableMap::const_iterator gsi = GlobalSymbolTable.end();
> - if (Symbol != Obj.end_symbols())
> + if (Symbol != Obj.symbol_end())
> gsi = GlobalSymbolTable.find(TargetName.data());
> if (gsi != GlobalSymbolTable.end()) {
> Value.SectionID = gsi->second.first;
> @@ -977,9 +942,9 @@ relocation_iterator RuntimeDyldELF::proc
> // TODO: Now ELF SymbolRef::ST_Debug = STT_SECTION, it's not obviously
> // and can be changed by another developers. Maybe best way is add
> // a new symbol type ST_Section to SymbolRef and use it.
> - section_iterator si(Obj.end_sections());
> + section_iterator si(Obj.section_end());
> Symbol->getSection(si);
> - if (si == Obj.end_sections())
> + if (si == Obj.section_end())
> llvm_unreachable("Symbol section not found, bad object file format!");
> DEBUG(dbgs() << "\t\tThis is section symbol\n");
> bool isCode = si->isText();
> @@ -1135,7 +1100,7 @@ relocation_iterator RuntimeDyldELF::proc
> if (RelType == ELF::R_PPC64_REL24) {
> // Determine ABI variant in use for this object.
> unsigned AbiVariant;
> - Obj.getObjectFile()->getPlatformFlags(AbiVariant);
> + Obj.getPlatformFlags(AbiVariant);
> AbiVariant &= ELF::EF_PPC64_ABI;
> // A PPC branch relocation will need a stub function if the target is
> // an external symbol (Symbol::ST_Unknown) or if the target address
> @@ -1495,7 +1460,7 @@ uint64_t RuntimeDyldELF::findGOTEntry(ui
> return 0;
> }
>
> -void RuntimeDyldELF::finalizeLoad(ObjectImage &ObjImg,
> +void RuntimeDyldELF::finalizeLoad(const ObjectFile &Obj,
> ObjSectionToIDMap &SectionMap) {
> // If necessary, allocate the global offset table
> if (MemMgr) {
> @@ -1533,15 +1498,8 @@ void RuntimeDyldELF::finalizeLoad(Object
> }
> }
>
> -bool RuntimeDyldELF::isCompatibleFormat(const ObjectBuffer *Buffer) const {
> - if (Buffer->getBufferSize() < strlen(ELF::ElfMagic))
> - return false;
> - return (memcmp(Buffer->getBufferStart(), ELF::ElfMagic,
> - strlen(ELF::ElfMagic))) == 0;
> -}
> -
> -bool RuntimeDyldELF::isCompatibleFile(const object::ObjectFile *Obj) const {
> - return Obj->isELF();
> +bool RuntimeDyldELF::isCompatibleFile(const object::ObjectFile &Obj) const {
> + return Obj.isELF();
> }
>
> } // namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldELF.h Wed Nov 26 00:53:26 2014
> @@ -28,9 +28,11 @@ std::error_code Check(std::error_code Er
> }
> return Err;
> }
> +
> } // end anonymous namespace
>
> class RuntimeDyldELF : public RuntimeDyldImpl {
> +
> void resolveRelocation(const SectionEntry &Section, uint64_t Offset,
> uint64_t Value, uint32_t Type, int64_t Addend,
> uint64_t SymOffset = 0);
> @@ -81,9 +83,11 @@ class RuntimeDyldELF : public RuntimeDyl
> return 1;
> }
>
> - void findPPC64TOCSection(ObjectImage &Obj, ObjSectionToIDMap &LocalSections,
> + void findPPC64TOCSection(const ObjectFile &Obj,
> + ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel);
> - void findOPDEntrySection(ObjectImage &Obj, ObjSectionToIDMap &LocalSections,
> + void findOPDEntrySection(const ObjectFile &Obj,
> + ObjSectionToIDMap &LocalSections,
> RelocationValueRef &Rel);
>
> uint64_t findGOTEntry(uint64_t LoadAddr, uint64_t Offset);
> @@ -104,24 +108,23 @@ class RuntimeDyldELF : public RuntimeDyl
> SmallVector<SID, 2> RegisteredEHFrameSections;
>
> public:
> - RuntimeDyldELF(RTDyldMemoryManager *mm) : RuntimeDyldImpl(mm) {}
> + RuntimeDyldELF(RTDyldMemoryManager *mm);
> + virtual ~RuntimeDyldELF();
> +
> + std::unique_ptr<RuntimeDyld::LoadedObjectInfo>
> + loadObject(const object::ObjectFile &O) override;
>
> void resolveRelocation(const RelocationEntry &RE, uint64_t Value) override;
> relocation_iterator
> processRelocationRef(unsigned SectionID, relocation_iterator RelI,
> - ObjectImage &Obj, ObjSectionToIDMap &ObjSectionToID,
> + const ObjectFile &Obj,
> + ObjSectionToIDMap &ObjSectionToID,
> const SymbolTableMap &Symbols, StubMap &Stubs) override;
> - bool isCompatibleFormat(const ObjectBuffer *Buffer) const override;
> - bool isCompatibleFile(const object::ObjectFile *Buffer) const override;
> + bool isCompatibleFile(const object::ObjectFile &Obj) const override;
> void registerEHFrames() override;
> void deregisterEHFrames() override;
> - void finalizeLoad(ObjectImage &ObjImg,
> + void finalizeLoad(const ObjectFile &Obj,
> ObjSectionToIDMap &SectionMap) override;
> - virtual ~RuntimeDyldELF();
> -
> - static std::unique_ptr<ObjectImage>
> - createObjectImage(std::unique_ptr<ObjectBuffer> InputBuffer);
> - static ObjectImage *createObjectImageFromFile(std::unique_ptr<object::ObjectFile> Obj);
> };
>
> } // end namespace llvm
>
> Modified: llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h?rev=222810&r1=222809&r2=222810&view=diff
> ==============================================================================
> --- llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h (original)
> +++ llvm/trunk/lib/ExecutionEngine/RuntimeDyld/RuntimeDyldImpl.h Wed Nov 26 00:53:26 2014
> @@ -18,7 +18,6 @@
> #include "llvm/ADT/SmallVector.h"
> #include "llvm/ADT/StringMap.h"
> #include "llvm/ADT/Triple.h"
> -#include "llvm/ExecutionEngine/ObjectImage.h"
> #include "llvm/ExecutionEngine/RuntimeDyld.h"
> #include "llvm/ExecutionEngine/RuntimeDyldChecker.h"
> #include "llvm/Object/ObjectFile.h"
> @@ -37,7 +36,6 @@ using namespace llvm::object;
>
> namespace llvm {
>
> -class ObjectBuffer;
> class Twine;
>
> /// SectionEntry - represents a section emitted into memory by the dynamic
> @@ -159,6 +157,7 @@ public:
> };
>
> class RuntimeDyldImpl {
> + friend class RuntimeDyld::LoadedObjectInfo;
> friend class RuntimeDyldCheckerImpl;
> private:
>
> @@ -296,14 +295,15 @@ protected:
> /// \brief Given the common symb...
>
> [Message clipped]
More information about the llvm-commits
mailing list