diff --git a/libcxxabi/src/fallback_malloc.cpp b/libcxxabi/src/fallback_malloc.cpp
--- a/libcxxabi/src/fallback_malloc.cpp
+++ b/libcxxabi/src/fallback_malloc.cpp
@@ -41,14 +41,28 @@
 
 class mutexor {
 public:
-#ifndef _LIBCXXABI_HAS_NO_THREADS
-  mutexor(std::__libcpp_mutex_t* m) : mtx_(m) {
-    std::__libcpp_mutex_lock(mtx_);
-  }
-  ~mutexor() { std::__libcpp_mutex_unlock(mtx_); }
-#else
+#ifdef _LIBCXXABI_HAS_NO_THREADS
   mutexor(void*) {}
   ~mutexor() {}
+#else
+  mutexor(std::__libcpp_mutex_t* m) {
+    // Neither fallback_malloc nor fallback_free spawn new threads. Thus, there
+    // is no danger of one thread entering them without aquiring the mutex,
+    // followed by another thread entering (and aquiring the mutex) before the
+    // first thread leaves.
+    // We can't acquire the mutex with threads disabled, but since we don't
+    // need to unless there is more than one thread anyways, we only bother to
+    // aquire the mutex when multi-threaded.
+    if (std::__libcpp_has_spawned_other_threads()) {
+      mtx_ = m;
+      std::__libcpp_mutex_lock(mtx_);
+    } else
+      mtx_ = nullptr;
+  }
+  ~mutexor() {
+    if (mtx_ != nullptr)
+      std::__libcpp_mutex_unlock(mtx_);
+  }
 #endif
 private:
   mutexor(const mutexor& rhs);