Bug 1366511: Part 2 - Allow autoconverting Err(nsresult) to nsresult. r?ehsan,nbp draft
authorKris Maglione <maglione.k@gmail.com>
Tue, 29 Aug 2017 21:28:22 -0700
changeset 655536 bdf69e6d9837c52fbe532cb7e0ac0b054eb94dad
parent 655535 291191cde633995e98c165cc4631d097e947be16
child 655537 ddfd7a72397055fdf38c1b00755a9cad7a9fea92
push id76906
push usermaglione.k@gmail.com
push dateWed, 30 Aug 2017 04:49:23 +0000
reviewersehsan, nbp
bugs1366511
milestone57.0a1
Bug 1366511: Part 2 - Allow autoconverting Err(nsresult) to nsresult. r?ehsan,nbp This allows MOZ_TRY and MOZ_TRY_VAR to be transparently used in XPCOM methods when compatible Result types are used. Also removes a compatibility macro in SimpleChannel.cpp, and an identical specialization in AddonManagerStartup, which are no longer necessary after this change. MozReview-Commit-ID: 94iNrPDJEnN
js/xpconnect/loader/ScriptPreloader-inl.h
js/xpconnect/loader/ScriptPreloader.cpp
mfbt/ResultExtensions.h
mfbt/moz.build
netwerk/base/SimpleChannel.cpp
netwerk/base/SimpleChannel.h
netwerk/protocol/res/ExtensionProtocolHandler.cpp
netwerk/protocol/res/ExtensionProtocolHandler.h
toolkit/components/extensions/WebExtensionPolicy.cpp
toolkit/mozapps/extensions/AddonManagerStartup.cpp
xpcom/base/nscore.h
--- a/js/xpconnect/loader/ScriptPreloader-inl.h
+++ b/js/xpconnect/loader/ScriptPreloader-inl.h
@@ -6,41 +6,26 @@
 #ifndef ScriptPreloader_inl_h
 #define ScriptPreloader_inl_h
 
 #include "mozilla/Attributes.h"
 #include "mozilla/Assertions.h"
 #include "mozilla/CheckedInt.h"
 #include "mozilla/EnumSet.h"
 #include "mozilla/Range.h"
-#include "mozilla/Result.h"
+#include "mozilla/ResultExtensions.h"
 #include "mozilla/Unused.h"
 #include "mozilla/dom/ScriptSettings.h"
 #include "nsString.h"
 #include "nsTArray.h"
 
 #include <prio.h>
 
 namespace mozilla {
 
-// A specialization of GenericErrorResult which auto-converts to a nsresult.
-// This should be removed when bug 1366511 is fixed.
-template <>
-class MOZ_MUST_USE_TYPE GenericErrorResult<nsresult>
-{
-  nsresult mErrorValue;
-
-  template<typename V, typename E2> friend class Result;
-
-public:
-  explicit GenericErrorResult(nsresult aErrorValue) : mErrorValue(aErrorValue) {}
-
-  operator nsresult() { return mErrorValue; }
-};
-
 namespace loader {
 
 using mozilla::dom::AutoJSAPI;
 
 struct MOZ_RAII AutoSafeJSAPI : public AutoJSAPI
 {
     AutoSafeJSAPI() { Init(); }
 };
--- a/js/xpconnect/loader/ScriptPreloader.cpp
+++ b/js/xpconnect/loader/ScriptPreloader.cpp
@@ -1,16 +1,16 @@
 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
 /* vim: set ts=8 sts=4 et sw=4 tw=99: */
 /* 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 "ScriptPreloader-inl.h"
 #include "mozilla/ScriptPreloader.h"
-#include "ScriptPreloader-inl.h"
 #include "mozilla/loader/ScriptCacheActors.h"
 
 #include "mozilla/ArrayUtils.h"
 #include "mozilla/ClearOnShutdown.h"
 #include "mozilla/FileUtils.h"
 #include "mozilla/Logging.h"
 #include "mozilla/ScopeExit.h"
 #include "mozilla/Services.h"
new file mode 100644
--- /dev/null
+++ b/mfbt/ResultExtensions.h
@@ -0,0 +1,37 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
+ * vim: set ts=8 sts=4 et sw=4 tw=99:
+ * 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/. */
+
+/* Extensions to the Result type to enable simpler handling of XPCOM/NSPR results. */
+
+#ifndef mozilla_ResultExtensions_h
+#define mozilla_ResultExtensions_h
+
+#include "mozilla/Assertions.h"
+#include "nscore.h"
+
+namespace mozilla {
+
+// Allow nsresult errors to automatically convert to nsresult values, so MOZ_TRY
+// can be used in XPCOM methods with Result<T, nserror> results.
+template <>
+class MOZ_MUST_USE_TYPE GenericErrorResult<nsresult>
+{
+  nsresult mErrorValue;
+
+  template<typename V, typename E2> friend class Result;
+
+public:
+  explicit GenericErrorResult(nsresult aErrorValue) : mErrorValue(aErrorValue)
+  {
+    MOZ_ASSERT(NS_FAILED(aErrorValue));
+  }
+
+  operator nsresult() { return mErrorValue; }
+};
+
+} // namespace mozilla
+
+#endif // mozilla_ResultExtensions_h
--- a/mfbt/moz.build
+++ b/mfbt/moz.build
@@ -71,16 +71,17 @@ EXPORTS.mozilla = [
     'Range.h',
     'RangedArray.h',
     'RangedPtr.h',
     'ReentrancyGuard.h',
     'RefCounted.h',
     'RefCountType.h',
     'RefPtr.h',
     'Result.h',
+    'ResultExtensions.h',
     'ReverseIterator.h',
     'RollingMean.h',
     'Saturate.h',
     'Scoped.h',
     'ScopeExit.h',
     'SegmentedVector.h',
     'SHA1.h',
     'SmallPointerArray.h',
--- a/netwerk/base/SimpleChannel.cpp
+++ b/netwerk/base/SimpleChannel.cpp
@@ -16,28 +16,16 @@
 #include "mozilla/Unused.h"
 #include "mozilla/dom/ContentChild.h"
 #include "mozilla/net/NeckoChild.h"
 #include "mozilla/net/PSimpleChannelChild.h"
 
 namespace mozilla {
 namespace net {
 
-// Like MOZ_TRY, but returns the unwrapped error value rather than a
-// GenericErrorResult on failure.
-#define TRY_VAR(target, expr) \
-  do { \
-    auto result = (expr); \
-    if (result.isErr()) { \
-      return result.unwrapErr(); \
-    } \
-    (target) = result.unwrap(); \
-  } while (0)
-
-
 class SimpleChannel : public nsBaseChannel
 {
 public:
   explicit SimpleChannel(UniquePtr<SimpleChannelCallbacks>&& aCallbacks);
 
 protected:
   virtual ~SimpleChannel() {}
 
@@ -58,42 +46,40 @@ SimpleChannel::SimpleChannel(UniquePtr<S
 }
 
 nsresult
 SimpleChannel::OpenContentStream(bool async, nsIInputStream **streamOut, nsIChannel** channel)
 {
   NS_ENSURE_TRUE(mCallbacks, NS_ERROR_UNEXPECTED);
 
   nsCOMPtr<nsIInputStream> stream;
-  TRY_VAR(stream, mCallbacks->OpenContentStream(async, this));
+  MOZ_TRY_VAR(stream, mCallbacks->OpenContentStream(async, this));
   MOZ_ASSERT(stream);
 
   mCallbacks = nullptr;
 
   *channel = nullptr;
   stream.forget(streamOut);
   return NS_OK;
 }
 
 nsresult
 SimpleChannel::BeginAsyncRead(nsIStreamListener* listener, nsIRequest** request)
 {
   NS_ENSURE_TRUE(mCallbacks, NS_ERROR_UNEXPECTED);
 
   nsCOMPtr<nsIRequest> req;
-  TRY_VAR(req, mCallbacks->StartAsyncRead(listener, this));
+  MOZ_TRY_VAR(req, mCallbacks->StartAsyncRead(listener, this));
 
   mCallbacks = nullptr;
 
   req.forget(request);
   return NS_OK;
 }
 
-#undef TRY_VAR
-
 class SimpleChannelChild final : public SimpleChannel
                                , public nsIChildChannel
                                , public PSimpleChannelChild
 {
 public:
   explicit SimpleChannelChild(UniquePtr<SimpleChannelCallbacks>&& aCallbacks);
 
   NS_DECL_ISUPPORTS_INHERITED
--- a/netwerk/base/SimpleChannel.h
+++ b/netwerk/base/SimpleChannel.h
@@ -1,17 +1,17 @@
 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
 /* 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/. */
 
 #ifndef SimpleChannel_h
 #define SimpleChannel_h
 
-#include "mozilla/Result.h"
+#include "mozilla/ResultExtensions.h"
 #include "mozilla/UniquePtr.h"
 #include "nsCOMPtr.h"
 
 class nsIChannel;
 class nsIInputStream;
 class nsILoadInfo;
 class nsIRequest;
 class nsIStreamListener;
--- a/netwerk/protocol/res/ExtensionProtocolHandler.cpp
+++ b/netwerk/protocol/res/ExtensionProtocolHandler.cpp
@@ -47,29 +47,16 @@
 #endif
 
 #define EXTENSION_SCHEME "moz-extension"
 using mozilla::ipc::FileDescriptor;
 using OptionalIPCStream = mozilla::ipc::OptionalIPCStream;
 
 namespace mozilla {
 
-template <>
-class MOZ_MUST_USE_TYPE GenericErrorResult<nsresult>
-{
-  nsresult mErrorValue;
-
-  template<typename V, typename E2> friend class Result;
-
-public:
-  explicit GenericErrorResult(nsresult aErrorValue) : mErrorValue(aErrorValue) {}
-
-  operator nsresult() { return mErrorValue; }
-};
-
 namespace net {
 
 using extensions::URLInfo;
 
 LazyLogModule gExtProtocolLog("ExtProtocol");
 #undef LOG
 #define LOG(...) MOZ_LOG(gExtProtocolLog, LogLevel::Debug, (__VA_ARGS__))
 
--- a/netwerk/protocol/res/ExtensionProtocolHandler.h
+++ b/netwerk/protocol/res/ExtensionProtocolHandler.h
@@ -3,16 +3,17 @@
  * 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/. */
 
 #ifndef ExtensionProtocolHandler_h___
 #define ExtensionProtocolHandler_h___
 
 #include "mozilla/net/NeckoParent.h"
 #include "mozilla/LazyIdleThread.h"
+#include "mozilla/Result.h"
 #include "SubstitutingProtocolHandler.h"
 
 namespace mozilla {
 namespace net {
 
 class ExtensionProtocolHandler final : public nsISubstitutingProtocolHandler,
                                        public nsIProtocolHandlerWithDynamicFlags,
                                        public SubstitutingProtocolHandler,
--- a/toolkit/components/extensions/WebExtensionPolicy.cpp
+++ b/toolkit/components/extensions/WebExtensionPolicy.cpp
@@ -3,16 +3,17 @@
  * 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/ExtensionPolicyService.h"
 #include "mozilla/extensions/WebExtensionContentScript.h"
 #include "mozilla/extensions/WebExtensionPolicy.h"
 
 #include "mozilla/AddonManagerWebAPI.h"
+#include "mozilla/ResultExtensions.h"
 #include "nsEscape.h"
 #include "nsISubstitutingProtocolHandler.h"
 #include "nsNetUtil.h"
 #include "nsPrintfCString.h"
 
 namespace mozilla {
 namespace extensions {
 
--- a/toolkit/mozapps/extensions/AddonManagerStartup.cpp
+++ b/toolkit/mozapps/extensions/AddonManagerStartup.cpp
@@ -11,16 +11,17 @@
 #include "js/TracingAPI.h"
 #include "xpcpublic.h"
 
 #include "mozilla/ClearOnShutdown.h"
 #include "mozilla/EndianUtils.h"
 #include "mozilla/Compression.h"
 #include "mozilla/LinkedList.h"
 #include "mozilla/Preferences.h"
+#include "mozilla/ResultExtensions.h"
 #include "mozilla/ScopeExit.h"
 #include "mozilla/Services.h"
 #include "mozilla/Unused.h"
 #include "mozilla/ErrorResult.h"
 #include "mozilla/dom/ipc/StructuredCloneData.h"
 
 #include "nsAppDirectoryServiceDefs.h"
 #include "nsAppRunner.h"
@@ -37,29 +38,16 @@
 #include "nsJSUtils.h"
 #include "nsReadableUtils.h"
 #include "nsXULAppAPI.h"
 
 #include <stdlib.h>
 
 namespace mozilla {
 
-template <>
-class MOZ_MUST_USE_TYPE GenericErrorResult<nsresult>
-{
-  nsresult mErrorValue;
-
-  template<typename V, typename E2> friend class Result;
-
-public:
-  explicit GenericErrorResult(nsresult aErrorValue) : mErrorValue(aErrorValue) {}
-
-  operator nsresult() { return mErrorValue; }
-};
-
 static inline Result<Ok, nsresult>
 WrapNSResult(PRStatus aRv)
 {
     if (aRv != PR_SUCCESS) {
         return Err(NS_ERROR_FAILURE);
     }
     return Ok();
 }
--- a/xpcom/base/nscore.h
+++ b/xpcom/base/nscore.h
@@ -207,16 +207,19 @@ namespace detail {
 // nsresult-sized value.
 template<typename T> struct UnusedZero;
 template<>
 struct UnusedZero<nsresult>
 {
   static const bool value = true;
 };
 } // namespace detail
+
+template <typename T> class MOZ_MUST_USE_TYPE GenericErrorResult;
+template <> class MOZ_MUST_USE_TYPE GenericErrorResult<nsresult>;
 } // namespace mozilla
 
 /*
  * Use these macros to do 64bit safe pointer conversions.
  */
 
 #define NS_PTR_TO_INT32(x) ((int32_t)(intptr_t)(x))
 #define NS_PTR_TO_UINT32(x) ((uint32_t)(intptr_t)(x))