From 8f358a20881b61cf3256fa1e404b86d5f104932d Mon Sep 17 00:00:00 2001 From: Alex Dvornikov Date: Thu, 11 Jan 2018 14:11:00 -0800 Subject: [PATCH] Report module id as string and as double, in case of invalid values are passed to nativeRequire Differential Revision: D6695769 fbshipit-source-id: b578b9d52ed711fb5a3e51717ac555fa8a232d7a --- ReactCommon/cxxreact/JSCUtils.cpp | 24 +++++++++--------------- ReactCommon/jschelpers/Value.cpp | 9 +++++++++ ReactCommon/jschelpers/Value.h | 9 +++++++++ 3 files changed, 27 insertions(+), 15 deletions(-) diff --git a/ReactCommon/cxxreact/JSCUtils.cpp b/ReactCommon/cxxreact/JSCUtils.cpp index 96ede8f6ae7a06..74942bc629b3d6 100644 --- a/ReactCommon/cxxreact/JSCUtils.cpp +++ b/ReactCommon/cxxreact/JSCUtils.cpp @@ -2,6 +2,8 @@ #include "JSCUtils.h" +#include + namespace facebook { namespace react { @@ -17,28 +19,20 @@ std::pair parseNativeRequireParameters( const JSGlobalContextRef& context, const JSValueRef arguments[], size_t argumentCount) { - double moduleId = 0, bundleId = 0; + uint32_t moduleId = 0, bundleId = 0; + // use "getNumber" & "folly::to" to throw explicitely in case of an overflow + // error during conversion if (argumentCount == 1) { - moduleId = Value(context, arguments[0]).asNumber(); + moduleId = folly::to(Value(context, arguments[0]).getNumberOrThrow()); } else if (argumentCount == 2) { - moduleId = Value(context, arguments[0]).asNumber(); - bundleId = Value(context, arguments[1]).asNumber(); + moduleId = folly::to(Value(context, arguments[0]).getNumberOrThrow()); + bundleId = folly::to(Value(context, arguments[1]).getNumberOrThrow()); } else { throw std::invalid_argument("Got wrong number of args"); } - if (moduleId < 0) { - throw std::invalid_argument(folly::to("Received invalid module ID: ", - Value(context, arguments[0]).toString().str())); - } - - if (bundleId < 0) { - throw std::invalid_argument(folly::to("Received invalid bundle ID: ", - Value(context, arguments[1]).toString().str())); - } - - return std::make_pair(static_cast(bundleId), static_cast(moduleId)); + return std::make_pair(bundleId, moduleId); } } diff --git a/ReactCommon/jschelpers/Value.cpp b/ReactCommon/jschelpers/Value.cpp index f084335f3032c1..72e303b18a152d 100644 --- a/ReactCommon/jschelpers/Value.cpp +++ b/ReactCommon/jschelpers/Value.cpp @@ -191,6 +191,15 @@ Value Value::makeError(JSContextRef ctx, const char *error, const char *stack) } } +void Value::throwTypeException(const std::string &expectedType) const { + std::string wat("TypeError: Expected "); + wat += expectedType; + wat += ", instead got '"; + wat += toString().str(); + wat += "'"; + throw JSException(wat.c_str()); +} + Object::operator Value() const { return Value(m_context, m_obj); } diff --git a/ReactCommon/jschelpers/Value.h b/ReactCommon/jschelpers/Value.h index d78103a8418482..e7df097096fd40 100644 --- a/ReactCommon/jschelpers/Value.h +++ b/ReactCommon/jschelpers/Value.h @@ -302,6 +302,13 @@ class Value : public noncopyable { } } + double getNumberOrThrow() const { + if (!isNumber()) { + throwTypeException("Number"); + } + return JSC_JSValueToNumber(context(), m_value, nullptr); + } + int32_t asInteger() const { return static_cast(asNumber()); } @@ -355,7 +362,9 @@ class Value : public noncopyable { JSContextRef m_context; JSValueRef m_value; + void throwTypeException(const std::string &expectedType) const; static JSValueRef fromDynamicInner(JSContextRef ctx, const folly::dynamic& obj); + }; } }