Bug 1632128 - Use mozilla::Variant for ResultHelper. r=dom-workers-and-storage-reviewers,janv
authorSimon Giesecke <sgiesecke@mozilla.com>
Thu, 14 May 2020 09:42:13 +0000
changeset 593594 7e01603c26005b763f0596ecba7c6993ec84a2da
parent 593593 fddd01727ad2f5c097b4d750bba958d0cdfc1340
child 593595 e4f2bb3f46359552fae16d0d836f4b9a27541d9a
push id13186
push userffxbld-merge
push dateMon, 01 Jun 2020 09:52:46 +0000
treeherdermozilla-beta@3e7c70a1e4a1 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersdom-workers-and-storage-reviewers, janv
bugs1632128
milestone78.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1632128 - Use mozilla::Variant for ResultHelper. r=dom-workers-and-storage-reviewers,janv Differential Revision: https://phabricator.services.mozilla.com/D71936
dom/indexedDB/ActorsChild.cpp
--- a/dom/indexedDB/ActorsChild.cpp
+++ b/dom/indexedDB/ActorsChild.cpp
@@ -194,243 +194,117 @@ class MOZ_STACK_CLASS AutoSetCurrentTran
   }
 };
 
 class MOZ_STACK_CLASS ResultHelper final : public IDBRequest::ResultCallback {
   const RefPtr<IDBRequest> mRequest;
   const AutoSetCurrentTransaction mAutoTransaction;
   const SafeRefPtr<IDBTransaction> mTransaction;
 
-  union {
-    IDBDatabase* mDatabase;
-    IDBCursor* mCursor;
-    IDBMutableFile* mMutableFile;
-    StructuredCloneReadInfoChild* mStructuredClone;
-    nsTArray<StructuredCloneReadInfoChild>* mStructuredCloneArray;
-    const Key* mKey;
-    const nsTArray<Key>* mKeyArray;
-    uint64_t mUInt64Value;
-    const JS::Handle<JS::Value>* mJSValHandle;
-  } mResult;
-
-  enum {
-    ResultTypeDatabase,
-    ResultTypeCursor,
-    ResultTypeMutableFile,
-    ResultTypeStructuredClone,
-    ResultTypeStructuredCloneArray,
-    ResultTypeKey,
-    ResultTypeKeyArray,
-    ResultTypeUInt64,
-    ResultTypeJSValHandle,
-  } mResultType;
+  mozilla::Variant<
+      IDBDatabase*, IDBCursor*, IDBMutableFile*, StructuredCloneReadInfoChild*,
+      nsTArray<StructuredCloneReadInfoChild>*, const Key*, const nsTArray<Key>*,
+      const uint64_t*, const JS::Handle<JS::Value>*>
+      mResult;
 
  public:
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               IDBDatabase* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeDatabase) {
-    MOZ_ASSERT(aRequest);
-    MOZ_ASSERT(aResult);
-
-    mResult.mDatabase = aResult;
-  }
-
+  template <typename T>
   ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               IDBCursor* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeCursor) {
-    MOZ_ASSERT(aRequest);
-
-    mResult.mCursor = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               IDBMutableFile* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeMutableFile) {
-    MOZ_ASSERT(aRequest);
-
-    mResult.mMutableFile = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               StructuredCloneReadInfoChild* aResult)
+               T* aResult)
       : mRequest(aRequest),
         mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
         mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeStructuredClone) {
-    MOZ_ASSERT(aRequest);
-    MOZ_ASSERT(aResult);
-
-    mResult.mStructuredClone = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               nsTArray<StructuredCloneReadInfoChild>* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeStructuredCloneArray) {
-    MOZ_ASSERT(aRequest);
-    MOZ_ASSERT(aResult);
-
-    mResult.mStructuredCloneArray = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               const Key* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeKey) {
+        mResult(aResult) {
     MOZ_ASSERT(aRequest);
     MOZ_ASSERT(aResult);
-
-    mResult.mKey = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               const nsTArray<Key>* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeKeyArray) {
-    MOZ_ASSERT(aRequest);
-    MOZ_ASSERT(aResult);
-
-    mResult.mKeyArray = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               const uint64_t aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeUInt64) {
-    MOZ_ASSERT(aRequest);
-
-    mResult.mUInt64Value = aResult;
-  }
-
-  ResultHelper(IDBRequest* aRequest, SafeRefPtr<IDBTransaction> aTransaction,
-               const JS::Handle<JS::Value>* aResult)
-      : mRequest(aRequest),
-        mAutoTransaction(aTransaction ? SomeRef(*aTransaction) : Nothing()),
-        mTransaction(std::move(aTransaction)),
-        mResultType(ResultTypeJSValHandle) {
-    MOZ_ASSERT(aRequest);
-
-    mResult.mJSValHandle = aResult;
   }
 
   virtual nsresult GetResult(JSContext* aCx,
                              JS::MutableHandle<JS::Value> aResult) override {
     MOZ_ASSERT(aCx);
     MOZ_ASSERT(mRequest);
 
-    switch (mResultType) {
-      case ResultTypeDatabase:
-        return GetResult(aCx, mResult.mDatabase, aResult);
-
-      case ResultTypeCursor:
-        return GetResult(aCx, mResult.mCursor, aResult);
-
-      case ResultTypeMutableFile:
-        return GetResult(aCx, mResult.mMutableFile, aResult);
-
-      case ResultTypeStructuredClone:
-        return GetResult(aCx, std::move(*mResult.mStructuredClone), aResult);
-
-      case ResultTypeStructuredCloneArray:
-        return GetResult(aCx, std::move(*mResult.mStructuredCloneArray),
-                         aResult);
-
-      case ResultTypeKey:
-        return GetResult(aCx, mResult.mKey, aResult);
-
-      case ResultTypeKeyArray:
-        return GetResult(aCx, mResult.mKeyArray, aResult);
-
-      case ResultTypeUInt64:
-        aResult.set(JS::NumberValue(mResult.mUInt64Value));
-        return NS_OK;
-
-      case ResultTypeJSValHandle:
-        aResult.set(*mResult.mJSValHandle);
-        return NS_OK;
-
-      default:
-        MOZ_CRASH("Unknown result type!");
-    }
-
-    MOZ_CRASH("Should never get here!");
+    return mResult.match(
+        [aCx, aResult](auto* aPtr) { return GetResult(aCx, aPtr, aResult); });
   }
 
   void DispatchSuccessEvent(RefPtr<Event> aEvent = nullptr);
 
  private:
   template <class T>
-  std::enable_if_t<std::is_same_v<T, IDBDatabase> ||
-                       std::is_same_v<T, IDBCursor> ||
-                       std::is_same_v<T, IDBMutableFile>,
-                   nsresult>
+  static std::enable_if_t<std::is_same_v<T, IDBDatabase> ||
+                              std::is_same_v<T, IDBCursor> ||
+                              std::is_same_v<T, IDBMutableFile>,
+                          nsresult>
   GetResult(JSContext* aCx, T* aDOMObject,
             JS::MutableHandle<JS::Value> aResult) {
     if (!aDOMObject) {
       aResult.setNull();
       return NS_OK;
     }
 
     const bool ok = GetOrCreateDOMReflector(aCx, aDOMObject, aResult);
     if (NS_WARN_IF(!ok)) {
       IDB_REPORT_INTERNAL_ERR();
       return NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
     }
 
     return NS_OK;
   }
 
-  nsresult GetResult(JSContext* aCx, StructuredCloneReadInfoChild&& aCloneInfo,
-                     JS::MutableHandle<JS::Value> aResult) {
+  static nsresult GetResult(JSContext* aCx, const JS::Handle<JS::Value>* aValue,
+                            JS::MutableHandle<JS::Value> aResult) {
+    aResult.set(*aValue);
+    return NS_OK;
+  }
+
+  static nsresult GetResult(JSContext* aCx, const uint64_t* aValue,
+                            JS::MutableHandle<JS::Value> aResult) {
+    aResult.set(JS::NumberValue(*aValue));
+    return NS_OK;
+  }
+
+  static nsresult GetResult(JSContext* aCx,
+                            StructuredCloneReadInfoChild* aCloneInfo,
+                            JS::MutableHandle<JS::Value> aResult) {
+    return GetResult(aCx, std::move(*aCloneInfo), aResult);
+  }
+
+  static nsresult GetResult(JSContext* aCx,
+                            StructuredCloneReadInfoChild&& aCloneInfo,
+                            JS::MutableHandle<JS::Value> aResult) {
     const bool ok =
         IDBObjectStore::DeserializeValue(aCx, std::move(aCloneInfo), aResult);
 
     if (NS_WARN_IF(!ok)) {
       return NS_ERROR_DOM_DATA_CLONE_ERR;
     }
 
     return NS_OK;
   }
 
-  nsresult GetResult(JSContext* aCx,
-                     nsTArray<StructuredCloneReadInfoChild>&& aCloneInfos,
-                     JS::MutableHandle<JS::Value> aResult) {
+  static nsresult GetResult(JSContext* aCx,
+                            nsTArray<StructuredCloneReadInfoChild>* aCloneInfos,
+                            JS::MutableHandle<JS::Value> aResult) {
     JS::Rooted<JSObject*> array(aCx, JS::NewArrayObject(aCx, 0));
     if (NS_WARN_IF(!array)) {
       IDB_REPORT_INTERNAL_ERR();
       return NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
     }
 
-    if (!aCloneInfos.IsEmpty()) {
-      const uint32_t count = aCloneInfos.Length();
+    if (!aCloneInfos->IsEmpty()) {
+      const uint32_t count = aCloneInfos->Length();
 
       if (NS_WARN_IF(!JS::SetArrayLength(aCx, array, count))) {
         IDB_REPORT_INTERNAL_ERR();
         return NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
       }
 
       for (uint32_t index = 0; index < count; index++) {
-        auto& cloneInfo = aCloneInfos.ElementAt(index);
+        auto& cloneInfo = aCloneInfos->ElementAt(index);
 
         JS::Rooted<JS::Value> value(aCx);
 
         const nsresult rv = GetResult(aCx, std::move(cloneInfo), &value);
         if (NS_WARN_IF(NS_FAILED(rv))) {
           return rv;
         }
 
@@ -441,27 +315,27 @@ class MOZ_STACK_CLASS ResultHelper final
         }
       }
     }
 
     aResult.setObject(*array);
     return NS_OK;
   }
 
-  nsresult GetResult(JSContext* aCx, const Key* aKey,
-                     JS::MutableHandle<JS::Value> aResult) {
+  static nsresult GetResult(JSContext* aCx, const Key* aKey,
+                            JS::MutableHandle<JS::Value> aResult) {
     const nsresult rv = aKey->ToJSVal(aCx, aResult);
     if (NS_WARN_IF(NS_FAILED(rv))) {
       return rv;
     }
     return NS_OK;
   }
 
-  nsresult GetResult(JSContext* aCx, const nsTArray<Key>* aKeys,
-                     JS::MutableHandle<JS::Value> aResult) {
+  static nsresult GetResult(JSContext* aCx, const nsTArray<Key>* aKeys,
+                            JS::MutableHandle<JS::Value> aResult) {
     JS::Rooted<JSObject*> array(aCx, JS::NewArrayObject(aCx, 0));
     if (NS_WARN_IF(!array)) {
       IDB_REPORT_INTERNAL_ERR();
       return NS_ERROR_DOM_INDEXEDDB_UNKNOWN_ERR;
     }
 
     if (!aKeys->IsEmpty()) {
       const uint32_t count = aKeys->Length();
@@ -2667,25 +2541,26 @@ void BackgroundRequestChild::HandleRespo
   ResultHelper helper(mRequest, AcquireTransaction(), &cloneReadInfos);
 
   helper.DispatchSuccessEvent();
 }
 
 void BackgroundRequestChild::HandleResponse(JS::Handle<JS::Value> aResponse) {
   AssertIsOnOwningThread();
 
-  ResultHelper helper(mRequest, AcquireTransaction(), &aResponse);
+  ResultHelper helper(mRequest, AcquireTransaction(),
+                      const_cast<const JS::Handle<JS::Value>*>(&aResponse));
 
   helper.DispatchSuccessEvent();
 }
 
-void BackgroundRequestChild::HandleResponse(uint64_t aResponse) {
+void BackgroundRequestChild::HandleResponse(const uint64_t aResponse) {
   AssertIsOnOwningThread();
 
-  ResultHelper helper(mRequest, AcquireTransaction(), aResponse);
+  ResultHelper helper(mRequest, AcquireTransaction(), &aResponse);
 
   helper.DispatchSuccessEvent();
 }
 
 nsresult BackgroundRequestChild::HandlePreprocess(
     const PreprocessInfo& aPreprocessInfo) {
   return HandlePreprocessInternal(
       AutoTArray<PreprocessInfo, 1>{aPreprocessInfo});
@@ -3360,17 +3235,17 @@ void BackgroundCursorChild<CursorType>::
       "Consumed cached response", mTransaction->LoggingSerialNumber(),
       GetRequest()->LoggingSerialNumber(),
       mDelayedResponses.size() + mCachedResponses.size());
 
   ResultHelper helper(GetRequest(),
                       mTransaction ? SafeRefPtr{&mTransaction.ref(),
                                                 AcquireStrongRefFromRawPtr{}}
                                    : nullptr,
-                      cursor);
+                      cursor.get());
   helper.DispatchSuccessEvent();
 
   mTransaction->OnRequestFinished(/* aRequestCompletedSuccessfully */ true);
 }
 
 template <IDBCursorType CursorType>
 void BackgroundCursorChild<CursorType>::SendDeleteMeInternal() {
   AssertIsOnOwningThread();
@@ -3559,17 +3434,17 @@ void BackgroundCursorChild<CursorType>::
       break;
     }
   }
 
   ResultHelper helper(GetRequest(),
                       mTransaction ? SafeRefPtr{&mTransaction.ref(),
                                                 AcquireStrongRefFromRawPtr{}}
                                    : nullptr,
-                      mCursor);
+                      static_cast<IDBCursor*>(mCursor));
   helper.DispatchSuccessEvent();
 }
 
 template <IDBCursorType CursorType>
 void BackgroundCursorChild<CursorType>::HandleResponse(
     nsTArray<ResponseType>&& aResponses) {
   AssertIsOnOwningThread();