[llvm] c4ccf60 - ManagedStatic: remove from GDBRegistrationListener

Nicolai Hähnle via llvm-commits llvm-commits at lists.llvm.org
Sun Jul 10 05:13:40 PDT 2022


Author: Nicolai Hähnle
Date: 2022-07-10T14:13:16+02:00
New Revision: c4ccf608c2380796d64db108eed3b24c1b0140ef

URL: https://github.com/llvm/llvm-project/commit/c4ccf608c2380796d64db108eed3b24c1b0140ef
DIFF: https://github.com/llvm/llvm-project/commit/c4ccf608c2380796d64db108eed3b24c1b0140ef.diff

LOG: ManagedStatic: remove from GDBRegistrationListener

An earlier version of this change originally landed as part of
e6f1f062457c928c18a88c612f39d9e168f65a85 (D129120), which caused a
Fuchsia buildbot regression in ExecutionEngine tests.

Careful review suggests that the issue was that in the earlier version,
the destructor of the JITDebugLock was run before the destructor of
GDBJITRegistrationListener. The new version of the change moves the lock
to a member variable of the (singleton!) GDBJITRegistartionListener so
that destructors are run in the right order.

Added: 
    

Modified: 
    llvm/lib/ExecutionEngine/GDBRegistrationListener.cpp

Removed: 
    


################################################################################
diff  --git a/llvm/lib/ExecutionEngine/GDBRegistrationListener.cpp b/llvm/lib/ExecutionEngine/GDBRegistrationListener.cpp
index 29a623ebe449..f1eeee3b3599 100644
--- a/llvm/lib/ExecutionEngine/GDBRegistrationListener.cpp
+++ b/llvm/lib/ExecutionEngine/GDBRegistrationListener.cpp
@@ -12,7 +12,6 @@
 #include "llvm/Object/ObjectFile.h"
 #include "llvm/Support/Compiler.h"
 #include "llvm/Support/ErrorHandling.h"
-#include "llvm/Support/ManagedStatic.h"
 #include "llvm/Support/MemoryBuffer.h"
 #include "llvm/Support/Mutex.h"
 #include <mutex>
@@ -91,11 +90,18 @@ typedef llvm::DenseMap<JITEventListener::ObjectKey, RegisteredObjectInfo>
 /// object files that are in executable memory managed by the client of this
 /// class.
 class GDBJITRegistrationListener : public JITEventListener {
+  /// Lock used to serialize all jit registration events, since they
+  /// modify global variables.
+  ///
+  /// Only a single instance of GDBJITRegistrationListener is ever created,
+  /// and so the lock can be a member variable of that instance. This ensures
+  /// destructors are run in the correct order.
+  sys::Mutex JITDebugLock;
+
   /// A map of in-memory object files that have been registered with the
   /// JIT interface.
   RegisteredObjectBufferMap ObjectBufferMap;
 
-public:
   /// Instantiates the JIT service.
   GDBJITRegistrationListener() = default;
 
@@ -103,6 +109,12 @@ class GDBJITRegistrationListener : public JITEventListener {
   /// internal resources.
   ~GDBJITRegistrationListener() override;
 
+public:
+  static GDBJITRegistrationListener &instance() {
+    static GDBJITRegistrationListener Instance;
+    return Instance;
+  }
+
   /// 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.
@@ -121,10 +133,6 @@ class GDBJITRegistrationListener : public JITEventListener {
   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;
@@ -143,7 +151,7 @@ void NotifyDebugger(jit_code_entry* JITCodeEntry) {
 
 GDBJITRegistrationListener::~GDBJITRegistrationListener() {
   // Free all registered object files.
-  std::lock_guard<llvm::sys::Mutex> locked(*JITDebugLock);
+  std::lock_guard<llvm::sys::Mutex> locked(JITDebugLock);
   for (RegisteredObjectBufferMap::iterator I = ObjectBufferMap.begin(),
                                            E = ObjectBufferMap.end();
        I != E; ++I) {
@@ -167,7 +175,7 @@ void GDBJITRegistrationListener::notifyObjectLoaded(
   const char *Buffer = DebugObj.getBinary()->getMemoryBufferRef().getBufferStart();
   size_t      Size = DebugObj.getBinary()->getMemoryBufferRef().getBufferSize();
 
-  std::lock_guard<llvm::sys::Mutex> locked(*JITDebugLock);
+  std::lock_guard<llvm::sys::Mutex> locked(JITDebugLock);
   assert(ObjectBufferMap.find(K) == ObjectBufferMap.end() &&
          "Second attempt to perform debug registration.");
   jit_code_entry* JITCodeEntry = new jit_code_entry();
@@ -186,7 +194,7 @@ void GDBJITRegistrationListener::notifyObjectLoaded(
 }
 
 void GDBJITRegistrationListener::notifyFreeingObject(ObjectKey K) {
-  std::lock_guard<llvm::sys::Mutex> locked(*JITDebugLock);
+  std::lock_guard<llvm::sys::Mutex> locked(JITDebugLock);
   RegisteredObjectBufferMap::iterator I = ObjectBufferMap.find(K);
 
   if (I != ObjectBufferMap.end()) {
@@ -228,14 +236,12 @@ void GDBJITRegistrationListener::deregisterObjectInternal(
   JITCodeEntry = nullptr;
 }
 
-llvm::ManagedStatic<GDBJITRegistrationListener> GDBRegListener;
-
 } // end namespace
 
 namespace llvm {
 
 JITEventListener* JITEventListener::createGDBRegistrationListener() {
-  return &*GDBRegListener;
+  return &GDBJITRegistrationListener::instance();
 }
 
 } // namespace llvm


        


More information about the llvm-commits mailing list