Revert of Modernize SkMutex and SkSemaphore. (patchset #2 id:20001 of https://codereview.chromium.org/1947153002/ )

Reason for revert:
This CL seems to have broken the Linux x64 and Mac
bots, e.g.

https://build.chromium.org/p/chromium/builders/Linux%20x64/builds/19052
https://build.chromium.org/p/chromium/builders/Mac/builds/15151

The error appears to have something to do with new static initializers being
added.

Original issue's description:
> Modernize SkMutex and SkSemaphore.
>
>    - use <atomic>
>    - fuse SkMutex and SkBaseMutex
>    - fuse SkSemaphore and SkBaseSemaphore
>
> Still TODO:
>    - replace SK_DECLARE_STATIC_MUTEX(name) with static SkMutex name
>
> I just didn't want to bother fixing all that up until I know this CL sticks.
>
> BUG=skia:
> GOLD_TRYBOT_URL= https://gold.skia.org/search2?unt=true&query=source_type%3Dgm&master=false&issue=1947153002
>
> No public API changes.
> TBR=reed@google.com
>
> Committed: https://skia.googlesource.com/skia/+/427c2819d9237d7d7729c59238036cfc73c072ea

TBR=herb@google.com,mtklein@chromium.org,reed@google.com,bsalomon@google.com
# Skipping CQ checks because original CL landed less than 1 days ago.
NOPRESUBMIT=true
NOTREECHECKS=true
NOTRY=true
BUG=609340

Review-Url: https://codereview.chromium.org/1945343003
diff --git a/src/core/SkSemaphore.cpp b/src/core/SkSemaphore.cpp
index 0646b15..da422e2 100644
--- a/src/core/SkSemaphore.cpp
+++ b/src/core/SkSemaphore.cpp
@@ -9,7 +9,7 @@
 
 #if defined(SK_BUILD_FOR_MAC) || defined(SK_BUILD_FOR_IOS)
     #include <mach/mach.h>
-    struct SkSemaphore::OSSemaphore {
+    struct SkBaseSemaphore::OSSemaphore {
         semaphore_t fSemaphore;
 
         OSSemaphore()  {
@@ -21,7 +21,7 @@
         void wait() { semaphore_wait(fSemaphore); }
     };
 #elif defined(SK_BUILD_FOR_WIN32)
-    struct SkSemaphore::OSSemaphore {
+    struct SkBaseSemaphore::OSSemaphore {
         HANDLE fSemaphore;
 
         OSSemaphore()  {
@@ -41,7 +41,7 @@
     // It's important we test for Mach before this.  This code will compile but not work there.
     #include <errno.h>
     #include <semaphore.h>
-    struct SkSemaphore::OSSemaphore {
+    struct SkBaseSemaphore::OSSemaphore {
         sem_t fSemaphore;
 
         OSSemaphore()  { sem_init(&fSemaphore, 0/*cross process?*/, 0/*initial count*/); }
@@ -57,16 +57,43 @@
 
 ///////////////////////////////////////////////////////////////////////////////
 
-void SkSemaphore::osSignal(int n) {
-    fOSSemaphoreOnce([this] { fOSSemaphore = new OSSemaphore; });
-    fOSSemaphore->signal(n);
+void SkBaseSemaphore::signal(int n) {
+    SkASSERT(n >= 0);
+
+    // We only want to call the OS semaphore when our logical count crosses
+    // from <= 0 to >0 (when we need to wake sleeping threads).
+    //
+    // This is easiest to think about with specific examples of prev and n.
+    // If n == 5 and prev == -3, there are 3 threads sleeping and we signal
+    // SkTMin(-(-3), 5) == 3 times on the OS semaphore, leaving the count at 2.
+    //
+    // If prev >= 0, no threads are waiting, SkTMin(-prev, n) is always <= 0,
+    // so we don't call the OS semaphore, leaving the count at (prev + n).
+    int prev = sk_atomic_fetch_add(&fCount, n, sk_memory_order_release);
+    int toSignal = SkTMin(-prev, n);
+    if (toSignal > 0) {
+        this->osSignal(toSignal);
+    }
 }
 
-void SkSemaphore::osWait() {
-    fOSSemaphoreOnce([this] { fOSSemaphore = new OSSemaphore; });
-    fOSSemaphore->wait();
+static SkBaseSemaphore::OSSemaphore* semaphore(SkBaseSemaphore* semaphore) {
+    return semaphore->fOSSemaphore.get([](){ return new SkBaseSemaphore::OSSemaphore(); });
 }
 
-SkSemaphore::~SkSemaphore() {
-    delete fOSSemaphore;
+void SkBaseSemaphore::osSignal(int n) { semaphore(this)->signal(n); }
+
+void SkBaseSemaphore::osWait() { semaphore(this)->wait(); }
+
+void SkBaseSemaphore::deleteSemaphore() {
+    delete (OSSemaphore*) fOSSemaphore;
 }
+
+///////////////////////////////////////////////////////////////////////////////
+
+SkSemaphore::SkSemaphore(){ fBaseSemaphore = {0, {0}}; }
+
+SkSemaphore::~SkSemaphore() { fBaseSemaphore.deleteSemaphore(); }
+
+void SkSemaphore::wait() { fBaseSemaphore.wait(); }
+
+void SkSemaphore::signal(int n) {fBaseSemaphore.signal(n); }
diff --git a/src/lazy/SkDiscardableMemoryPool.cpp b/src/lazy/SkDiscardableMemoryPool.cpp
index 2be4c75..1f3bcf9 100644
--- a/src/lazy/SkDiscardableMemoryPool.cpp
+++ b/src/lazy/SkDiscardableMemoryPool.cpp
@@ -29,7 +29,7 @@
     /**
      *  Without mutex, will be not be thread safe.
      */
-    DiscardableMemoryPool(size_t budget, SkMutex* mutex = nullptr);
+    DiscardableMemoryPool(size_t budget, SkBaseMutex* mutex = nullptr);
     virtual ~DiscardableMemoryPool();
 
     SkDiscardableMemory* create(size_t bytes) override;
@@ -52,9 +52,9 @@
     #endif  // SK_LAZY_CACHE_STATS
 
 private:
-    SkMutex* fMutex;
-    size_t   fBudget;
-    size_t   fUsed;
+    SkBaseMutex* fMutex;
+    size_t       fBudget;
+    size_t       fUsed;
     SkTInternalLList<PoolDiscardableMemory> fList;
 
     /** Function called to free memory if needed */
@@ -128,7 +128,8 @@
 
 ////////////////////////////////////////////////////////////////////////////////
 
-DiscardableMemoryPool::DiscardableMemoryPool(size_t budget, SkMutex* mutex)
+DiscardableMemoryPool::DiscardableMemoryPool(size_t budget,
+                                             SkBaseMutex* mutex)
     : fMutex(mutex)
     , fBudget(budget)
     , fUsed(0) {
@@ -240,7 +241,7 @@
 
 }  // namespace
 
-SkDiscardableMemoryPool* SkDiscardableMemoryPool::Create(size_t size, SkMutex* mutex) {
+SkDiscardableMemoryPool* SkDiscardableMemoryPool::Create(size_t size, SkBaseMutex* mutex) {
     return new DiscardableMemoryPool(size, mutex);
 }
 
diff --git a/src/lazy/SkDiscardableMemoryPool.h b/src/lazy/SkDiscardableMemoryPool.h
index ad8d796..92ba48b 100644
--- a/src/lazy/SkDiscardableMemoryPool.h
+++ b/src/lazy/SkDiscardableMemoryPool.h
@@ -52,7 +52,8 @@
      *  the pool works.
      *  Without mutex, will be not be thread safe.
      */
-    static SkDiscardableMemoryPool* Create(size_t size, SkMutex* mutex = nullptr);
+    static SkDiscardableMemoryPool* Create(
+            size_t size, SkBaseMutex* mutex = nullptr);
 };
 
 /**