Esempio n. 1
0
bool
WrapperAnswer::RecvObjectClassIs(const ObjectId &objId, const uint32_t &classValue,
                                 bool *result)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext *cx = jsapi.cx();

    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj) {
        // This is very unfortunate, but we have no choice.
        *result = false;
        return true;
    }

    LOG("%s.objectClassIs()", ReceiverObj(objId));

    *result = js_ObjectClassIs(cx, obj, (js::ESClassValue)classValue);
    return true;
}
Esempio n. 2
0
  NS_IMETHOD
  OnUnsubscribe(nsresult aStatus, bool aSuccess) override
  {
    AssertIsOnMainThread();
    MOZ_ASSERT(mProxy, "OnUnsubscribe() called twice?");

    nsRefPtr<PromiseWorkerProxy> proxy = mProxy.forget();

    MutexAutoLock lock(proxy->Lock());
    if (proxy->CleanedUp()) {
      return NS_OK;
    }

    AutoJSAPI jsapi;
    jsapi.Init();

    nsRefPtr<UnsubscribeResultRunnable> r =
      new UnsubscribeResultRunnable(proxy, aStatus, aSuccess);
    r->Dispatch(jsapi.cx());
    return NS_OK;
  }
Esempio n. 3
0
bool
WrapperAnswer::RecvPreventExtensions(const ObjectId &objId, ReturnStatus *rs,
                                     bool *succeeded)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext *cx = jsapi.cx();

    *succeeded = false;
    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj)
        return fail(cx, rs);

    if (!JS_PreventExtensions(cx, obj, succeeded))
        return fail(cx, rs);

    LOG("%s.preventExtensions()", ReceiverObj(objId));

    return ok(rs);
}
Esempio n. 4
0
  NS_IMETHOD
  OnPushEndpoint(nsresult aStatus, const nsAString& aEndpoint) override
  {
    AssertIsOnMainThread();
    MOZ_ASSERT(mProxy, "OnPushEndpoint() called twice?");

    nsRefPtr<PromiseWorkerProxy> proxy = mProxy.forget();

    MutexAutoLock lock(proxy->Lock());
    if (proxy->CleanedUp()) {
      return NS_OK;
    }

    AutoJSAPI jsapi;
    jsapi.Init();

    nsRefPtr<GetSubscriptionResultRunnable> r =
      new GetSubscriptionResultRunnable(proxy, aStatus, aEndpoint, mScope);
    r->Dispatch(jsapi.cx());
    return NS_OK;
  }
Esempio n. 5
0
void
TCPServerSocket::FireEvent(const nsAString& aType, TCPSocket* aSocket)
{
  AutoJSAPI api;
  api.Init(GetOwnerGlobal());

  TCPServerSocketEventInit init;
  init.mBubbles = false;
  init.mCancelable = false;
  init.mSocket = aSocket;

  RefPtr<TCPServerSocketEvent> event =
      TCPServerSocketEvent::Constructor(this, aType, init);
  event->SetTrusted(true);
  bool dummy;
  DispatchEvent(event, &dummy);

  if (mServerBridgeParent) {
    mServerBridgeParent->OnConnect(event);
  }
}
Esempio n. 6
0
void
FetchStream::Close()
{
  AssertIsOnOwningThread();

  MutexAutoLock lock(mMutex);

  if (mState == eClosed) {
    return;
  }

  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(mGlobal))) {
    ReleaseObjects(lock);
    return;
  }

  JSContext* cx = jsapi.cx();
  JS::Rooted<JSObject*> stream(cx, mStreamHolder->ReadableStreamBody());
  CloseAndReleaseObjects(cx, lock, stream);
}
NS_IMETHODIMP
MobileConnectionCallback::NotifyGetClirStatusSuccess(uint16_t aN, uint16_t aM)
{
    MozClirStatus result;
    result.mN.Construct(aN);
    result.mM.Construct(aM);

    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(mWindow))) {
        return NS_ERROR_FAILURE;
    }

    JSContext* cx = jsapi.cx();
    JS::Rooted<JS::Value> jsResult(cx);
    if (!ToJSValue(cx, result, &jsResult)) {
        JS_ClearPendingException(cx);
        return NS_ERROR_TYPE_ERR;
    }

    return NotifySuccess(jsResult);
};
Esempio n. 8
0
void
MessagePort::DispatchError()
{
  nsCOMPtr<nsIGlobalObject> globalObject = GetParentObject();

  AutoJSAPI jsapi;
  if (!globalObject || !jsapi.Init(globalObject)) {
    NS_WARNING("Failed to initialize AutoJSAPI object.");
    return;
  }

  RootedDictionary<MessageEventInit> init(jsapi.cx());
  init.mBubbles = false;
  init.mCancelable = false;

  RefPtr<Event> event =
    MessageEvent::Constructor(this, NS_LITERAL_STRING("messageerror"), init);
  event->SetTrusted(true);

  bool dummy;
  DispatchEvent(event, &dummy);
}
Esempio n. 9
0
already_AddRefed<InternalRequest>
TypeUtils::ToInternalRequest(const nsAString& aIn, ErrorResult& aRv)
{
  RequestOrUSVString requestOrString;
  requestOrString.SetAsUSVString().Rebind(aIn.Data(), aIn.Length());

  // Re-create a GlobalObject stack object so we can use webidl Constructors.
  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(GetGlobalObject()))) {
    aRv.Throw(NS_ERROR_UNEXPECTED);
    return nullptr;
  }
  JSContext* cx = jsapi.cx();
  GlobalObject global(cx, GetGlobalObject()->GetGlobalJSObject());
  MOZ_ASSERT(!global.Failed());

  nsRefPtr<Request> request = Request::Constructor(global, requestOrString,
                                                   RequestInit(), aRv);
  if (NS_WARN_IF(aRv.Failed())) { return nullptr; }

  return request->GetInternalRequest();
}
Esempio n. 10
0
void
BluetoothDevice::SetPropertyByValue(const BluetoothNamedValue& aValue)
{
  const nsString& name = aValue.name();
  const BluetoothValue& value = aValue.value();
  if (name.EqualsLiteral("Name")) {
    mName = value.get_nsString();
  } else if (name.EqualsLiteral("Path")) {
    MOZ_ASSERT(value.get_nsString().Length() > 0);
    mPath = value.get_nsString();
  } else if (name.EqualsLiteral("Address")) {
    mAddress = value.get_nsString();
  } else if (name.EqualsLiteral("Class")) {
    mClass = value.get_uint32_t();
  } else if (name.EqualsLiteral("Icon")) {
    mIcon = value.get_nsString();
  } else if (name.EqualsLiteral("Connected")) {
    mConnected = value.get_bool();
  } else if (name.EqualsLiteral("Paired")) {
    mPaired = value.get_bool();
  } else if (name.EqualsLiteral("UUIDs")) {
    mUuids = value.get_ArrayOfnsString();

    AutoJSAPI jsapi;
    if (!jsapi.Init(GetOwner())) {
      BT_WARNING("Failed to initialise AutoJSAPI!");
      return;
    }
    JSContext* cx = jsapi.cx();
    JS::Rooted<JSObject*> uuids(cx);
    if (NS_FAILED(nsTArrayToJSArray(cx, mUuids, &uuids))) {
      BT_WARNING("Cannot set JS UUIDs object!");
      return;
    }
    mJsUuids = uuids;
    Root();
  } else if (name.EqualsLiteral("Services")) {
    mServices = value.get_ArrayOfnsString();

    AutoJSAPI jsapi;
    if (!jsapi.Init(GetOwner())) {
      BT_WARNING("Failed to initialise AutoJSAPI!");
      return;
    }
    JSContext* cx = jsapi.cx();
    JS::Rooted<JSObject*> services(cx);
    if (NS_FAILED(nsTArrayToJSArray(cx, mServices, &services))) {
      BT_WARNING("Cannot set JS Services object!");
      return;
    }
    mJsServices = services;
    Root();
  } else {
    nsCString warningMsg;
    warningMsg.AssignLiteral("Not handling device property: ");
    warningMsg.Append(NS_ConvertUTF16toUTF8(name));
    BT_WARNING(warningMsg.get());
  }
}
Esempio n. 11
0
    // This is called on main thread.
    nsresult ReceiveBlob(already_AddRefed<File> aBlob)
    {
      nsRefPtr<File> blob = aBlob;
      uint64_t size;
      nsresult rv = blob->GetSize(&size);
      if (NS_SUCCEEDED(rv)) {
        AutoJSAPI jsapi;
        if (jsapi.Init(mGlobal)) {
          JS_updateMallocCounter(jsapi.cx(), size);
        }
      }

      nsRefPtr<File> newBlob = new File(mGlobal, blob->Impl());

      mozilla::ErrorResult error;
      mFileCallback->Call(*newBlob, error);

      mGlobal = nullptr;
      mFileCallback = nullptr;

      return error.StealNSResult();
    }
Esempio n. 12
0
bool
WrapperAnswer::RecvIsExtensible(const ObjectId &objId, ReturnStatus *rs, bool *result)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext *cx = jsapi.cx();
    *result = false;

    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj)
        return fail(cx, rs);

    LOG("%s.isExtensible()", ReceiverObj(objId));

    bool extensible;
    if (!JS_IsExtensible(cx, obj, &extensible))
        return fail(cx, rs);

    *result = !!extensible;
    return ok(rs);
}
Esempio n. 13
0
nsresult
nsJSUtils::CompileFunction(AutoJSAPI& jsapi,
                           JS::AutoObjectVector& aScopeChain,
                           JS::CompileOptions& aOptions,
                           const nsACString& aName,
                           uint32_t aArgCount,
                           const char** aArgArray,
                           const nsAString& aBody,
                           JSObject** aFunctionObject)
{
  MOZ_ASSERT(jsapi.OwnsErrorReporting());
  JSContext* cx = jsapi.cx();
  MOZ_ASSERT(js::GetEnterCompartmentDepth(cx) > 0);
  MOZ_ASSERT_IF(aScopeChain.length() != 0,
                js::IsObjectInContextCompartment(aScopeChain[0], cx));
  MOZ_ASSERT_IF(aOptions.versionSet, aOptions.version != JSVERSION_UNKNOWN);
  mozilla::DebugOnly<nsIScriptContext*> ctx = GetScriptContextFromJSContext(cx);
  MOZ_ASSERT_IF(ctx, ctx->IsContextInitialized());

  // Do the junk Gecko is supposed to do before calling into JSAPI.
  for (size_t i = 0; i < aScopeChain.length(); ++i) {
    JS::ExposeObjectToActiveJS(aScopeChain[i]);
  }

  // Compile.
  JS::Rooted<JSFunction*> fun(cx);
  if (!JS::CompileFunction(cx, aScopeChain, aOptions,
                           PromiseFlatCString(aName).get(),
                           aArgCount, aArgArray,
                           PromiseFlatString(aBody).get(),
                           aBody.Length(), &fun))
  {
    return NS_ERROR_FAILURE;
  }

  *aFunctionObject = JS_GetFunctionObject(fun);
  return NS_OK;
}
    nsresult
    Initialize(nsIPrincipal* aPrincipal, const nsAString& aURL,
               const nsAString& aCacheName, nsILoadGroup* aLoadGroup)
    {
        AssertIsOnMainThread();
        MOZ_ASSERT(aPrincipal);

        mURL = aURL;

        // Always create a CacheStorage since we want to write the network entry to
        // the cache even if there isn't an existing one.
        AutoJSAPI jsapi;
        jsapi.Init();
        ErrorResult result;
        mSandbox.init(jsapi.cx());
        mCacheStorage = CreateCacheStorage(jsapi.cx(), aPrincipal, result, &mSandbox);
        if (NS_WARN_IF(result.Failed())) {
            MOZ_ASSERT(!result.IsErrorWithMessage());
            return result.StealNSResult();
        }

        mCN = new CompareNetwork(this);
        nsresult rv = mCN->Initialize(aPrincipal, aURL, aLoadGroup);
        if (NS_WARN_IF(NS_FAILED(rv))) {
            return rv;
        }

        if (!aCacheName.IsEmpty()) {
            mCC = new CompareCache(this);
            rv = mCC->Initialize(aPrincipal, aURL, aCacheName);
            if (NS_WARN_IF(NS_FAILED(rv))) {
                mCN->Abort();
                return rv;
            }
        }

        return NS_OK;
    }
Esempio n. 15
0
bool
WrapperAnswer::RecvDelete(const ObjectId& objId, const JSIDVariant& idVar, ReturnStatus* rs)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext* cx = jsapi.cx();

    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj)
        return fail(cx, rs);

    LOG("delete %s[%s]", ReceiverObj(objId), Identifier(idVar));

    RootedId id(cx);
    if (!fromJSIDVariant(cx, idVar, &id))
        return fail(cx, rs);

    ObjectOpResult success;
    if (!JS_DeletePropertyById(cx, obj, id, success))
        return fail(cx, rs);
    return ok(rs, success);
}
NS_IMETHODIMP
MobileMessageCallback::NotifyMessageDeleted(bool *aDeleted, uint32_t aSize)
{
  if (aSize == 1) {
    AutoJSContext cx;
    JS::Rooted<JS::Value> val(cx, JS::BooleanValue(*aDeleted));
    return NotifySuccess(val);
  }

  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(mDOMRequest->GetOwner()))) {
    return NS_ERROR_FAILURE;
  }
  JSContext* cx = jsapi.cx();

  JS::Rooted<JSObject*> deleteArrayObj(cx, JS_NewArrayObject(cx, aSize));
  for (uint32_t i = 0; i < aSize; i++) {
    JS_DefineElement(cx, deleteArrayObj, i, aDeleted[i], JSPROP_ENUMERATE);
  }

  JS::Rooted<JS::Value> deleteArrayVal(cx, JS::ObjectValue(*deleteArrayObj));
  return NotifySuccess(deleteArrayVal);
}
Esempio n. 17
0
bool
WrapperAnswer::RecvDOMInstanceOf(const ObjectId &objId, const int &prototypeID,
                                 const int &depth, ReturnStatus *rs, bool *instanceof)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext *cx = jsapi.cx();
    *instanceof = false;

    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj)
        return fail(cx, rs);

    LOG("%s.domInstanceOf()", ReceiverObj(objId));

    bool tmp;
    if (!mozilla::dom::InterfaceHasInstance(cx, prototypeID, depth, obj, &tmp))
        return fail(cx, rs);
    *instanceof = tmp;

    return ok(rs);
}
Esempio n. 18
0
bool
WrapperAnswer::RecvHasInstance(const ObjectId &objId, const JSVariant &vVar, ReturnStatus *rs, bool *bp)
{
    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(scopeForTargetObjects())))
        return false;
    JSContext *cx = jsapi.cx();

    RootedObject obj(cx, findObjectById(cx, objId));
    if (!obj)
        return fail(cx, rs);

    LOG("%s.hasInstance(%s)", ReceiverObj(objId), InVariant(vVar));

    RootedValue val(cx);
    if (!fromVariant(cx, vVar, &val))
        return fail(cx, rs);

    if (!JS_HasInstance(cx, obj, val, bp))
        return fail(cx, rs);

    return ok(rs);
}
Esempio n. 19
0
already_AddRefed<DOMRequest>
nsBrowserElement::ExecuteScript(const nsAString& aScript,
                                const BrowserElementExecuteScriptOptions& aOptions,
                                ErrorResult& aRv)
{
  NS_ENSURE_TRUE(IsBrowserElementOrThrow(aRv), nullptr);

  RefPtr<DOMRequest> req;
  nsCOMPtr<nsIXPConnectWrappedJS> wrappedObj = do_QueryInterface(mBrowserElementAPI);
  MOZ_ASSERT(wrappedObj, "Failed to get wrapped JS from XPCOM component.");
  MOZ_RELEASE_ASSERT(!js::IsWrapper(wrappedObj->GetJSObject()));
  AutoJSAPI jsapi;
  if (!jsapi.Init(wrappedObj->GetJSObject())) {
    aRv.Throw(NS_ERROR_UNEXPECTED);
    return nullptr;
  }
  JSContext* cx = jsapi.cx();
  JS::Rooted<JS::Value> options(cx);
  aRv.MightThrowJSException();
  if (!ToJSValue(cx, aOptions, &options)) {
    aRv.StealExceptionFromJSContext(cx);
    return nullptr;
  }

  nsresult rv = mBrowserElementAPI->ExecuteScript(aScript, options, getter_AddRefs(req));

  if (NS_FAILED(rv)) {
    if (rv == NS_ERROR_INVALID_ARG) {
      aRv.Throw(NS_ERROR_DOM_INVALID_ACCESS_ERR);
    } else {
      aRv.Throw(NS_ERROR_DOM_INVALID_STATE_ERR);
    }
    return nullptr;
  }

  return req.forget();
}
Esempio n. 20
0
void
Promise::AppendNativeHandler(PromiseNativeHandler* aRunnable)
{
  NS_ASSERT_OWNINGTHREAD(Promise);

  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(mGlobal))) {
    // Our API doesn't allow us to return a useful error.  Not like this should
    // happen anyway.
    return;
  }

  // The self-hosted promise js may keep the object we pass to it alive
  // for quite a while depending on when GC runs.  Therefore, pass a shim
  // object instead.  The shim will free its inner PromiseNativeHandler
  // after the promise has settled just like our previous c++ promises did.
  RefPtr<PromiseNativeHandlerShim> shim =
    new PromiseNativeHandlerShim(aRunnable);

  JSContext* cx = jsapi.cx();
  JS::Rooted<JSObject*> handlerWrapper(cx);
  // Note: PromiseNativeHandler is NOT wrappercached.  So we can't use
  // ToJSValue here, because it will try to do XPConnect wrapping on it, sadly.
  if (NS_WARN_IF(!shim->WrapObject(cx, nullptr, &handlerWrapper))) {
    // Again, no way to report errors.
    jsapi.ClearException();
    return;
  }

  JS::Rooted<JSObject*> resolveFunc(cx);
  resolveFunc =
    CreateNativeHandlerFunction(cx, handlerWrapper, NativeHandlerTask::Resolve);
  if (NS_WARN_IF(!resolveFunc)) {
    jsapi.ClearException();
    return;
  }

  JS::Rooted<JSObject*> rejectFunc(cx);
  rejectFunc =
    CreateNativeHandlerFunction(cx, handlerWrapper, NativeHandlerTask::Reject);
  if (NS_WARN_IF(!rejectFunc)) {
    jsapi.ClearException();
    return;
  }

  JS::Rooted<JSObject*> promiseObj(cx, PromiseObj());
  if (NS_WARN_IF(!JS::AddPromiseReactions(cx, promiseObj, resolveFunc,
                                          rejectFunc))) {
    jsapi.ClearException();
    return;
  }
}
    // This is called on main thread.
    nsresult ReceiveBlob(already_AddRefed<Blob> aBlob)
    {
      RefPtr<Blob> blob = aBlob;

      ErrorResult rv;
      uint64_t size = blob->GetSize(rv);
      if (rv.Failed()) {
        rv.SuppressException();
      } else {
        AutoJSAPI jsapi;
        if (jsapi.Init(mGlobal)) {
          JS_updateMallocCounter(jsapi.cx(), size);
        }
      }

      RefPtr<Blob> newBlob = Blob::Create(mGlobal, blob->Impl());

      mFileCallback->Call(*newBlob, rv);

      mGlobal = nullptr;
      mFileCallback = nullptr;

      return rv.StealNSResult();
    }
Esempio n. 22
0
static void GetPropertyBagFromEvent(Event* aEvent,
                                    nsIPropertyBag2** aPropertyBag) {
  *aPropertyBag = nullptr;

  CustomEvent* customEvent = aEvent->AsCustomEvent();
  if (!customEvent) return;

  AutoJSAPI jsapi;
  if (!jsapi.Init(customEvent->GetParentObject())) return;

  JSContext* cx = jsapi.cx();
  JS::Rooted<JS::Value> detail(cx);
  customEvent->GetDetail(cx, &detail);
  if (!detail.isObject()) return;

  JS::Rooted<JSObject*> detailObj(cx, &detail.toObject());

  nsresult rv;
  nsCOMPtr<nsIPropertyBag2> propBag;
  rv = UnwrapArg<nsIPropertyBag2>(cx, detailObj, getter_AddRefs(propBag));
  if (NS_FAILED(rv)) return;

  propBag.forget(aPropertyBag);
}
NS_IMETHODIMP
MobileConnectionCallback::NotifyGetCallBarringSuccess(uint16_t aProgram,
        bool aEnabled,
        uint16_t aServiceClass)
{
    MozCallBarringOptions result;
    result.mProgram.Construct().SetValue(aProgram);
    result.mEnabled.Construct().SetValue(aEnabled);
    result.mServiceClass.Construct().SetValue(aServiceClass);

    AutoJSAPI jsapi;
    if (NS_WARN_IF(!jsapi.Init(mWindow))) {
        return NS_ERROR_FAILURE;
    }

    JSContext* cx = jsapi.cx();
    JS::Rooted<JS::Value> jsResult(cx);
    if (!ToJSValue(cx, result, &jsResult)) {
        JS_ClearPendingException(cx);
        return NS_ERROR_TYPE_ERR;
    }

    return NotifySuccess(jsResult);
}
Esempio n. 24
0
  bool
  ParseSuccessfulReply(JS::MutableHandle<JS::Value> aValue)
  {
    aValue.setUndefined();

    AutoJSAPI jsapi;
    NS_ENSURE_TRUE(jsapi.Init(mAdapter->GetParentObject()), false);
    JSContext* cx = jsapi.cx();

    /**
     * Create a new discovery handle and wrap it to return. Each
     * discovery handle is one-time-use only.
     */
    nsRefPtr<BluetoothDiscoveryHandle> discoveryHandle =
      BluetoothDiscoveryHandle::Create(mAdapter->GetParentObject());
    if (!ToJSValue(cx, discoveryHandle, aValue)) {
      JS_ClearPendingException(cx);
      return false;
    }

    // Set the created discovery handle as the one in use.
    mAdapter->SetDiscoveryHandleInUse(discoveryHandle);
    return true;
  }
NS_IMETHODIMP
MobileMessageCallback::NotifySegmentInfoForTextGot(int32_t aSegments,
                                                   int32_t aCharsPerSegment,
                                                   int32_t aCharsAvailableInLastSegment)
{
  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(mDOMRequest->GetOwner()))) {
    return NotifyError(nsIMobileMessageCallback::INTERNAL_ERROR);
  }

  SmsSegmentInfo info;
  info.mSegments = aSegments;
  info.mCharsPerSegment = aCharsPerSegment;
  info.mCharsAvailableInLastSegment = aCharsAvailableInLastSegment;

  JSContext* cx = jsapi.cx();
  JS::Rooted<JS::Value> val(cx);
  if (!ToJSValue(cx, info, &val)) {
    JS_ClearPendingException(cx);
    return NotifyError(nsIMobileMessageCallback::INTERNAL_ERROR);
  }

  return NotifySuccess(val, true);
}
Esempio n. 26
0
already_AddRefed<nsISupports>
CallbackObjectHolderBase::ToXPCOMCallback(CallbackObject* aCallback,
                                          const nsIID& aIID) const
{
  MOZ_ASSERT(NS_IsMainThread());
  if (!aCallback) {
    return nullptr;
  }

  // We don't init the AutoJSAPI with our callback because we don't want it
  // reporting errors to its global's onerror handlers.
  AutoJSAPI jsapi;
  jsapi.Init();
  JSContext* cx = jsapi.cx();

  JS::Rooted<JSObject*> callback(cx, aCallback->CallbackOrNull());
  if (!callback) {
    return nullptr;
  }

  JSAutoCompartment ac(cx, callback);
  RefPtr<nsXPCWrappedJS> wrappedJS;
  nsresult rv =
    nsXPCWrappedJS::GetNewOrUsed(callback, aIID, getter_AddRefs(wrappedJS));
  if (NS_FAILED(rv) || !wrappedJS) {
    return nullptr;
  }

  nsCOMPtr<nsISupports> retval;
  rv = wrappedJS->QueryInterface(aIID, getter_AddRefs(retval));
  if (NS_FAILED(rv)) {
    return nullptr;
  }

  return retval.forget();
}
Esempio n. 27
0
void
ProfileGatherer::Finish()
{
  MOZ_ASSERT(NS_IsMainThread());

  if (!mTicker) {
    // We somehow got called after we were cancelled! This shouldn't
    // be possible, but doing a belt-and-suspenders check to be sure.
    return;
  }

  UniquePtr<char[]> buf = mTicker->ToJSON(mSinceTime);

  nsCOMPtr<nsIObserverService> os = mozilla::services::GetObserverService();
  if (os) {
    DebugOnly<nsresult> rv = os->RemoveObserver(this, "profiler-subprocess");
    NS_WARNING_ASSERTION(NS_SUCCEEDED(rv), "RemoveObserver failed");
  }

  AutoJSAPI jsapi;
  if (NS_WARN_IF(!jsapi.Init(mPromise->GlobalJSObject()))) {
    // We're really hosed if we can't get a JS context for some reason.
    Reset();
    return;
  }

  JSContext* cx = jsapi.cx();

  // Now parse the JSON so that we resolve with a JS Object.
  JS::RootedValue val(cx);
  {
    NS_ConvertUTF8toUTF16 js_string(nsDependentCString(buf.get()));
    if (!JS_ParseJSON(cx, static_cast<const char16_t*>(js_string.get()),
                      js_string.Length(), &val)) {
      if (!jsapi.HasException()) {
        mPromise->MaybeReject(NS_ERROR_DOM_UNKNOWN_ERR);
      } else {
        JS::RootedValue exn(cx);
        DebugOnly<bool> gotException = jsapi.StealException(&exn);
        MOZ_ASSERT(gotException);

        jsapi.ClearException();
        mPromise->MaybeReject(cx, exn);
      }
    } else {
      mPromise->MaybeResolve(val);
    }
  }

  Reset();
}
Esempio n. 28
0
static bool
Process(AutoJSAPI& jsapi, const char* filename, bool forceTTY)
{
    FILE* file;

    if (forceTTY || !filename || strcmp(filename, "-") == 0) {
        file = stdin;
    } else {
        file = fopen(filename, "r");
        if (!file) {
            JS_ReportErrorNumber(jsapi.cx(), my_GetErrorMessage, nullptr,
                                 JSSMSG_CANT_OPEN,
                                 filename, strerror(errno));
            gExitCode = EXITCODE_FILE_NOT_FOUND;
            return false;
        }
    }

    bool ok = ProcessFile(jsapi, filename, file, forceTTY);
    if (file != stdin)
        fclose(file);
    return ok;
}
Esempio n. 29
0
NS_IMETHODIMP
PostMessageEvent::Run()
{
  MOZ_ASSERT(mTargetWindow->IsOuterWindow(),
             "should have been passed an outer window!");
  MOZ_ASSERT(!mSource || mSource->IsOuterWindow(),
             "should have been passed an outer window!");

  AutoJSAPI jsapi;
  jsapi.Init();
  JSContext* cx = jsapi.cx();

  // The document is just used for the principal mismatch error message below.
  // Use a stack variable so mSourceDocument is not held onto after this method
  // finishes, regardless of the method outcome.
  nsCOMPtr<nsIDocument> sourceDocument;
  sourceDocument.swap(mSourceDocument);

  // If we bailed before this point we're going to leak mMessage, but
  // that's probably better than crashing.

  RefPtr<nsGlobalWindow> targetWindow;
  if (mTargetWindow->IsClosedOrClosing() ||
      !(targetWindow = mTargetWindow->GetCurrentInnerWindowInternal()) ||
      targetWindow->IsClosedOrClosing())
    return NS_OK;

  MOZ_ASSERT(targetWindow->IsInnerWindow(),
             "we ordered an inner window!");
  JSAutoCompartment ac(cx, targetWindow->GetWrapperPreserveColor());

  // Ensure that any origin which might have been provided is the origin of this
  // window's document.  Note that we do this *now* instead of when postMessage
  // is called because the target window might have been navigated to a
  // different location between then and now.  If this check happened when
  // postMessage was called, it would be fairly easy for a malicious webpage to
  // intercept messages intended for another site by carefully timing navigation
  // of the target window so it changed location after postMessage but before
  // now.
  if (mProvidedPrincipal) {
    // Get the target's origin either from its principal or, in the case the
    // principal doesn't carry a URI (e.g. the system principal), the target's
    // document.
    nsIPrincipal* targetPrin = targetWindow->GetPrincipal();
    if (NS_WARN_IF(!targetPrin))
      return NS_OK;

    // Note: This is contrary to the spec with respect to file: URLs, which
    //       the spec groups into a single origin, but given we intentionally
    //       don't do that in other places it seems better to hold the line for
    //       now.  Long-term, we want HTML5 to address this so that we can
    //       be compliant while being safer.
    if (!targetPrin->Equals(mProvidedPrincipal)) {
      nsAutoString providedOrigin, targetOrigin;
      nsresult rv = nsContentUtils::GetUTFOrigin(targetPrin, targetOrigin);
      NS_ENSURE_SUCCESS(rv, rv);
      rv = nsContentUtils::GetUTFOrigin(mProvidedPrincipal, providedOrigin);
      NS_ENSURE_SUCCESS(rv, rv);

      const char16_t* params[] = { providedOrigin.get(), targetOrigin.get() };

      nsContentUtils::ReportToConsole(nsIScriptError::errorFlag,
        NS_LITERAL_CSTRING("DOM Window"), sourceDocument,
        nsContentUtils::eDOM_PROPERTIES,
        "TargetPrincipalDoesNotMatch",
        params, ArrayLength(params));

      return NS_OK;
    }
  }

  ErrorResult rv;
  JS::Rooted<JS::Value> messageData(cx);
  nsCOMPtr<nsPIDOMWindowInner> window = targetWindow->AsInner();

  Read(window, cx, &messageData, rv);
  if (NS_WARN_IF(rv.Failed())) {
    return rv.StealNSResult();
  }

  // Create the event
  nsCOMPtr<mozilla::dom::EventTarget> eventTarget = do_QueryObject(targetWindow);
  RefPtr<MessageEvent> event =
    new MessageEvent(eventTarget, nullptr, nullptr);


  Nullable<WindowProxyOrMessagePort> source;
  source.SetValue().SetAsWindowProxy() = mSource ? mSource->AsOuter() : nullptr;

  event->InitMessageEvent(nullptr, NS_LITERAL_STRING("message"),
                          false /*non-bubbling */, false /*cancelable */,
                          messageData, mCallerOrigin,
                          EmptyString(), source, nullptr);

  nsTArray<RefPtr<MessagePort>> ports = TakeTransferredPorts();

  event->SetPorts(new MessagePortList(static_cast<dom::Event*>(event.get()),
                                      ports));

  // We can't simply call dispatchEvent on the window because doing so ends
  // up flipping the trusted bit on the event, and we don't want that to
  // happen because then untrusted content can call postMessage on a chrome
  // window if it can get a reference to it.

  nsIPresShell *shell = targetWindow->GetExtantDoc()->GetShell();
  RefPtr<nsPresContext> presContext;
  if (shell)
    presContext = shell->GetPresContext();

  event->SetTrusted(mTrustedCaller);
  WidgetEvent* internalEvent = event->GetInternalNSEvent();

  nsEventStatus status = nsEventStatus_eIgnore;
  EventDispatcher::Dispatch(window,
                            presContext,
                            internalEvent,
                            static_cast<dom::Event*>(event.get()),
                            &status);
  return NS_OK;
}
Esempio n. 30
0
NS_IMETHODIMP
PostMessageEvent::Run()
{
  MOZ_ASSERT(mTargetWindow->IsOuterWindow(),
             "should have been passed an outer window!");
  MOZ_ASSERT(!mSource || mSource->IsOuterWindow(),
             "should have been passed an outer window!");

  AutoJSAPI jsapi;
  jsapi.Init();
  JSContext* cx = jsapi.cx();

  // If we bailed before this point we're going to leak mMessage, but
  // that's probably better than crashing.

  nsRefPtr<nsGlobalWindow> targetWindow;
  if (mTargetWindow->IsClosedOrClosing() ||
      !(targetWindow = mTargetWindow->GetCurrentInnerWindowInternal()) ||
      targetWindow->IsClosedOrClosing())
    return NS_OK;

  MOZ_ASSERT(targetWindow->IsInnerWindow(),
             "we ordered an inner window!");
  JSAutoCompartment ac(cx, targetWindow->GetWrapperPreserveColor());

  // Ensure that any origin which might have been provided is the origin of this
  // window's document.  Note that we do this *now* instead of when postMessage
  // is called because the target window might have been navigated to a
  // different location between then and now.  If this check happened when
  // postMessage was called, it would be fairly easy for a malicious webpage to
  // intercept messages intended for another site by carefully timing navigation
  // of the target window so it changed location after postMessage but before
  // now.
  if (mProvidedPrincipal) {
    // Get the target's origin either from its principal or, in the case the
    // principal doesn't carry a URI (e.g. the system principal), the target's
    // document.
    nsIPrincipal* targetPrin = targetWindow->GetPrincipal();
    if (NS_WARN_IF(!targetPrin))
      return NS_OK;

    // Note: This is contrary to the spec with respect to file: URLs, which
    //       the spec groups into a single origin, but given we intentionally
    //       don't do that in other places it seems better to hold the line for
    //       now.  Long-term, we want HTML5 to address this so that we can
    //       be compliant while being safer.
    if (!targetPrin->Equals(mProvidedPrincipal)) {
      return NS_OK;
    }
  }

  ErrorResult rv;
  JS::Rooted<JS::Value> messageData(cx);
  nsCOMPtr<nsPIDOMWindow> window = targetWindow.get();

  Read(window, cx, &messageData, rv);
  if (NS_WARN_IF(rv.Failed())) {
    return rv.StealNSResult();
  }

  // Create the event
  nsCOMPtr<mozilla::dom::EventTarget> eventTarget =
    do_QueryInterface(static_cast<nsPIDOMWindow*>(targetWindow.get()));
  nsRefPtr<MessageEvent> event =
    new MessageEvent(eventTarget, nullptr, nullptr);

  event->InitMessageEvent(NS_LITERAL_STRING("message"), false /*non-bubbling */,
                          false /*cancelable */, messageData, mCallerOrigin,
                          EmptyString(), mSource);

  nsTArray<nsRefPtr<MessagePortBase>> ports;
  TakeTransferredPorts(ports);

  event->SetPorts(new MessagePortList(static_cast<dom::Event*>(event.get()),
                                      ports));

  // We can't simply call dispatchEvent on the window because doing so ends
  // up flipping the trusted bit on the event, and we don't want that to
  // happen because then untrusted content can call postMessage on a chrome
  // window if it can get a reference to it.

  nsIPresShell *shell = targetWindow->GetExtantDoc()->GetShell();
  nsRefPtr<nsPresContext> presContext;
  if (shell)
    presContext = shell->GetPresContext();

  event->SetTrusted(mTrustedCaller);
  WidgetEvent* internalEvent = event->GetInternalNSEvent();

  nsEventStatus status = nsEventStatus_eIgnore;
  EventDispatcher::Dispatch(static_cast<nsPIDOMWindow*>(mTargetWindow),
                            presContext,
                            internalEvent,
                            static_cast<dom::Event*>(event.get()),
                            &status);
  return NS_OK;
}