DXR is a code search and navigation tool aimed at making sense of large projects. It supports full-text and regex searches as well as structural queries.

Implementation

Mercurial (c68fe15a81fc)

VCS Links

Line Code
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

// A lock that can be acquired multiple times on the same thread.
// A lock that can be acquired multiple times on the same thread.

#ifndef mozilla_RecursiveMutex_h
#define mozilla_RecursiveMutex_h

#include "mozilla/BlockingResourceBase.h"
#include "mozilla/BlockingResourceBase.h"
#include "mozilla/GuardObjects.h"

#ifndef XP_WIN
#  include <pthread.h>
#endif
#endif

namespace mozilla {

class RecursiveMutex : public BlockingResourceBase {
 public:
 public:
  explicit RecursiveMutex(const char* aName MOZ_GUARD_OBJECT_NOTIFIER_PARAM);
  ~RecursiveMutex();

#ifdef DEBUG
  void Lock();
  void Lock();
  void Unlock();
#else
  void Lock() { LockInternal(); }
  void Unlock() { UnlockInternal(); }
#endif
#endif

#ifdef DEBUG
  /**
   * AssertCurrentThreadIn
   **/
  void AssertCurrentThreadIn();
  /**
  /**
   * AssertNotCurrentThreadIn
   **/
  void AssertNotCurrentThreadIn() {
    // Not currently implemented. See bug 476536 for discussion.
  }
  }
#else
  void AssertCurrentThreadIn() {}
  void AssertNotCurrentThreadIn() {}
#endif


 private:
  RecursiveMutex() = delete;
  RecursiveMutex(const RecursiveMutex&) = delete;
  RecursiveMutex& operator=(const RecursiveMutex&) = delete;


  void LockInternal();
  void UnlockInternal();

#ifdef DEBUG
  PRThread* mOwningThread;
  size_t mEntryCount;
#endif
#endif

#if !defined(XP_WIN)
  pthread_mutex_t mMutex;
#else
  // We eschew including windows.h and using CRITICAL_SECTION here so that files
  // We eschew including windows.h and using CRITICAL_SECTION here so that files
  // including us don't also pull in windows.h.  Just use a type that's big
  // enough for CRITICAL_SECTION, and we'll fix it up later.
  void* mMutex[6];
#endif
  MOZ_DECL_USE_GUARD_OBJECT_NOTIFIER
  MOZ_DECL_USE_GUARD_OBJECT_NOTIFIER
};

class MOZ_RAII RecursiveMutexAutoLock {
 public:
  explicit RecursiveMutexAutoLock(
  explicit RecursiveMutexAutoLock(
      RecursiveMutex& aRecursiveMutex MOZ_GUARD_OBJECT_NOTIFIER_PARAM)
      : mRecursiveMutex(&aRecursiveMutex) {
    MOZ_GUARD_OBJECT_NOTIFIER_INIT;
    NS_ASSERTION(mRecursiveMutex, "null mutex");
    NS_ASSERTION(mRecursiveMutex, "null mutex");
    mRecursiveMutex->Lock();
  }

  ~RecursiveMutexAutoLock(void) { mRecursiveMutex->Unlock(); }


 private:
  RecursiveMutexAutoLock() = delete;
  RecursiveMutexAutoLock(const RecursiveMutexAutoLock&) = delete;
  RecursiveMutexAutoLock& operator=(const RecursiveMutexAutoLock&) = delete;
  static void* operator new(size_t) noexcept(true);

  mozilla::RecursiveMutex* mRecursiveMutex;
  MOZ_DECL_USE_GUARD_OBJECT_NOTIFIER
};


class MOZ_RAII RecursiveMutexAutoUnlock {
 public:
  explicit RecursiveMutexAutoUnlock(
      RecursiveMutex& aRecursiveMutex MOZ_GUARD_OBJECT_NOTIFIER_PARAM)
      : mRecursiveMutex(&aRecursiveMutex) {
      : mRecursiveMutex(&aRecursiveMutex) {
    MOZ_GUARD_OBJECT_NOTIFIER_INIT;
    NS_ASSERTION(mRecursiveMutex, "null mutex");
    mRecursiveMutex->Unlock();
  }


  ~RecursiveMutexAutoUnlock(void) { mRecursiveMutex->Lock(); }

 private:
  RecursiveMutexAutoUnlock() = delete;
  RecursiveMutexAutoUnlock(const RecursiveMutexAutoUnlock&) = delete;
  RecursiveMutexAutoUnlock(const RecursiveMutexAutoUnlock&) = delete;
  RecursiveMutexAutoUnlock& operator=(const RecursiveMutexAutoUnlock&) = delete;
  static void* operator new(size_t) noexcept(true);

  mozilla::RecursiveMutex* mRecursiveMutex;
  MOZ_DECL_USE_GUARD_OBJECT_NOTIFIER
  MOZ_DECL_USE_GUARD_OBJECT_NOTIFIER
};

}  // namespace mozilla

#endif  // mozilla_RecursiveMutex_h
#endif  // mozilla_RecursiveMutex_h