author | Martin Thomson <martin.thomson@gmail.com> |
Fri, 09 Jan 2015 10:55:44 -0800 | |
changeset 223059 | da03d6aff37d92878b0c19897fd759db92600f59 |
parent 223058 | b206ea15cb59f9b0ae591404e811d0eff9e7a459 |
child 223060 | 0c40a9e043cea4f5c3bf9e2e51f1ce6531b32567 |
push id | 28082 |
push user | cbook@mozilla.com |
push date | Mon, 12 Jan 2015 10:44:52 +0000 |
treeherder | mozilla-central@643589c3ef94 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | gabor |
bugs | 1116269 |
milestone | 37.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
|
--- a/js/xpconnect/src/Sandbox.cpp +++ b/js/xpconnect/src/Sandbox.cpp @@ -22,18 +22,20 @@ #include "nsNetUtil.h" #include "nsNullPrincipal.h" #include "nsPrincipal.h" #include "nsXMLHttpRequest.h" #include "WrapperFactory.h" #include "xpcprivate.h" #include "XPCWrapper.h" #include "XrayWrapper.h" +#include "Crypto.h" #include "mozilla/dom/BindingUtils.h" #include "mozilla/dom/BlobBinding.h" +#include "mozilla/dom/CryptoBinding.h" #include "mozilla/dom/CSSBinding.h" #include "mozilla/dom/indexedDB/IndexedDatabaseManager.h" #include "mozilla/dom/FileBinding.h" #include "mozilla/dom/PromiseBinding.h" #include "mozilla/dom/ScriptSettings.h" #include "mozilla/dom/TextDecoderBinding.h" #include "mozilla/dom/TextEncoderBinding.h" #include "mozilla/dom/URLBinding.h" @@ -213,16 +215,30 @@ SandboxCreateXMLHttpRequest(JSContext *c rv = nsContentUtils::WrapNative(cx, xhr, args.rval()); if (NS_FAILED(rv)) return false; return true; } static bool +SandboxCreateCrypto(JSContext *cx, JS::HandleObject obj) +{ + MOZ_ASSERT(JS_IsGlobalObject(obj)); + + nsIGlobalObject* native = xpc::NativeGlobal(obj); + MOZ_ASSERT(native); + + dom::Crypto* crypto = new dom::Crypto(); + crypto->Init(native); + JS::RootedObject wrapped(cx, dom::CryptoBinding::Wrap(cx, crypto)); + return JS_DefineProperty(cx, obj, "crypto", wrapped, JSPROP_ENUMERATE); +} + +static bool SandboxIsProxy(JSContext *cx, unsigned argc, jsval *vp) { CallArgs args = CallArgsFromVp(argc, vp); if (args.length() < 1) { JS_ReportError(cx, "Function requires at least 1 argument"); return false; } if (!args[0].isObject()) { @@ -778,16 +794,18 @@ xpc::GlobalProperties::Parse(JSContext * } else if (!strcmp(name.ptr(), "atob")) { atob = true; } else if (!strcmp(name.ptr(), "btoa")) { btoa = true; } else if (!strcmp(name.ptr(), "Blob")) { Blob = true; } else if (!strcmp(name.ptr(), "File")) { File = true; + } else if (!strcmp(name.ptr(), "crypto")) { + crypto = true; } else { JS_ReportError(cx, "Unknown property name: %s", name.ptr()); return false; } } return true; } @@ -832,16 +850,19 @@ xpc::GlobalProperties::Define(JSContext if (Blob && !dom::BlobBinding::GetConstructorObject(cx, obj)) return false; if (File && !dom::FileBinding::GetConstructorObject(cx, obj)) return false; + if (crypto && !SandboxCreateCrypto(cx, obj)) + return false; + return true; } nsresult xpc::CreateSandboxObject(JSContext *cx, MutableHandleValue vp, nsISupports *prinOrSop, SandboxOptions& options) { // Create the sandbox global object
--- a/js/xpconnect/src/xpcprivate.h +++ b/js/xpconnect/src/xpcprivate.h @@ -3366,16 +3366,17 @@ struct GlobalProperties { bool TextDecoder : 1; bool TextEncoder : 1; bool URL : 1; bool URLSearchParams : 1; bool atob : 1; bool btoa : 1; bool Blob : 1; bool File : 1; + bool crypto : 1; }; // Infallible. already_AddRefed<nsIXPCComponents_utils_Sandbox> NewSandboxConstructor(); // Returns true if class of 'obj' is SandboxClass. bool
new file mode 100644 --- /dev/null +++ b/js/xpconnect/tests/unit/test_crypto.js @@ -0,0 +1,28 @@ +/* Any copyright is dedicated to the Public Domain. + * http://creativecommons.org/publicdomain/zero/1.0/ */ + +function run_test() { + let Cu = Components.utils; + let sb = new Cu.Sandbox('https://www.example.com', + { wantGlobalProperties: + ["crypto", "TextEncoder", "TextDecoder"] + }); + sb.ok = ok; + Cu.evalInSandbox('ok(this.crypto);', sb); + Cu.evalInSandbox('ok(this.crypto.subtle);', sb); + sb.do_check_eq = do_check_eq; + let innerPromise = new Promise(r => (sb.test_done = r)); + Cu.evalInSandbox('crypto.subtle.digest("SHA-256", ' + + ' new TextEncoder("utf-8").encode("abc"))' + + ' .then(h => do_check_eq(new Uint16Array(h)[0], 30906))' + + ' .then(test_done);', sb); + + Cu.importGlobalProperties(["crypto"]); + ok(crypto); + ok(crypto.subtle); + let outerPromise = crypto.subtle.digest("SHA-256", new TextEncoder("utf-8").encode("abc")) + .then(h => do_check_eq(new Uint16Array(h)[0], 30906)); + + do_test_pending(); + Promise.all([innerPromise, outerPromise]).then(() => do_test_finished()); +}
--- a/js/xpconnect/tests/unit/xpcshell.ini +++ b/js/xpconnect/tests/unit/xpcshell.ini @@ -86,16 +86,17 @@ fail-if = os == "android" [test_sandbox_metadata.js] [test_exportFunction.js] [test_promise.js] [test_returncode.js] skip-if = os == "android" # native test components aren't available on Android [test_textDecoder.js] [test_url.js] [test_URLSearchParams.js] +[test_crypto.js] [test_css.js] [test_sandbox_atob.js] [test_isProxy.js] [test_getObjectPrincipal.js] [test_watchdog_enable.js] head = head_watchdog.js [test_watchdog_disable.js] head = head_watchdog.js