summaryrefslogtreecommitdiffstats
path: root/widget/gonk/WidgetTraceEvent.cpp
blob: 558d9313e3dd4f0450aa7f1c95596b19845182e1 (plain)
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
/* 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/. */

#include "mozilla/WidgetTraceEvent.h"
#include "mozilla/StaticPtr.h"
#include "nsThreadUtils.h"
#include <mozilla/CondVar.h>
#include <mozilla/Mutex.h>

using mozilla::CondVar;
using mozilla::Mutex;
using mozilla::MutexAutoLock;

namespace mozilla {
  class TracerRunnable : public Runnable {
    public:
      TracerRunnable() {
        mTracerLock = new Mutex("TracerRunnable");
        mTracerCondVar = new CondVar(*mTracerLock, "TracerRunnable");
        mMainThread = do_GetMainThread();
      }

      ~TracerRunnable() {
        delete mTracerCondVar;
        delete mTracerLock;
        mTracerLock = nullptr;
        mTracerCondVar = nullptr;
      }

      virtual nsresult Run() {
        MutexAutoLock lock(*mTracerLock);
        mHasRun = true;
        mTracerCondVar->Notify();
        return NS_OK;
      }

      bool Fire() {
        if (!mTracerLock || !mTracerCondVar) {
          return false;
        }

        MutexAutoLock lock(*mTracerLock);
        mHasRun = false;
        mMainThread->Dispatch(this, NS_DISPATCH_NORMAL);
        while (!mHasRun) {
          mTracerCondVar->Wait();
        }
        return true;
      }

      void Signal() {
        MutexAutoLock lock(*mTracerLock);
        mHasRun = true;
        mTracerCondVar->Notify();
      }

    private:
      Mutex* mTracerLock;
      CondVar* mTracerCondVar;
      bool mHasRun;
      nsCOMPtr<nsIThread> mMainThread;
  };

  StaticRefPtr<TracerRunnable> sTracerRunnable;

  bool InitWidgetTracing()
  {
    if (!sTracerRunnable) {
      sTracerRunnable = new TracerRunnable();
    }
    return true;
  }

  void CleanUpWidgetTracing()
  {
    sTracerRunnable = nullptr;
  }

  bool FireAndWaitForTracerEvent()
  {
    if (sTracerRunnable) {
      return sTracerRunnable->Fire();
    }

    return false;
  }

  void SignalTracerThread()
  {
    if (sTracerRunnable) {
      return sTracerRunnable->Signal();
    }
  }
} // namespace mozilla