Bug 1154366. Pass in a JSContext to StructuredCloneContainer::InitFromJSVal so it will throw its exceptions somewhere where people might see them. r=bholley

This commit is contained in:
Boris Zbarsky
2015-04-16 13:22:15 -04:00
parent 3e27204fc6
commit b2c93fc96e
8 changed files with 19 additions and 24 deletions

View File

@@ -11474,7 +11474,7 @@ nsDocShell::AddState(JS::Handle<JS::Value> aData, const nsAString& aTitle,
nsCOMPtr<nsIPrincipal> origPrincipal = origDocument->NodePrincipal(); nsCOMPtr<nsIPrincipal> origPrincipal = origDocument->NodePrincipal();
scContainer = new nsStructuredCloneContainer(); scContainer = new nsStructuredCloneContainer();
rv = scContainer->InitFromJSVal(aData); rv = scContainer->InitFromJSVal(aData, aCx);
NS_ENSURE_SUCCESS(rv, rv); NS_ENSURE_SUCCESS(rv, rv);
nsCOMPtr<nsIDocument> newDocument = GetDocument(); nsCOMPtr<nsIDocument> newDocument = GetDocument();

View File

@@ -200,4 +200,5 @@ pref(dom.webcomponents.enabled,true) load 1029710.html
HTTP(..) load xhr_abortinprogress.html HTTP(..) load xhr_abortinprogress.html
load xhr_empty_datauri.html load xhr_empty_datauri.html
load xhr_html_nullresponse.html load xhr_html_nullresponse.html
load structured_clone_container_throws.html
load 1154598.xhtml load 1154598.xhtml

View File

@@ -0,0 +1,9 @@
<iframe></iframe>
<script>
try { frames[0].history.pushState({ dummy: function() {} }, ''); }
catch (e) {}
var doc = frames[0].document;
var s = doc.createElement("script");
s.textContent = "1";
doc.body.appendChild(s);
</script>

View File

@@ -42,28 +42,19 @@ nsStructuredCloneContainer::~nsStructuredCloneContainer()
} }
nsresult nsresult
nsStructuredCloneContainer::InitFromJSVal(JS::Handle<JS::Value> aData) nsStructuredCloneContainer::InitFromJSVal(JS::Handle<JS::Value> aData,
JSContext* aCx)
{ {
NS_ENSURE_STATE(!mData); NS_ENSURE_STATE(!mData);
uint64_t* jsBytes = nullptr; uint64_t* jsBytes = nullptr;
bool success = false; bool success = false;
if (aData.isPrimitive()) { if (aData.isPrimitive()) {
// |aData| is a primitive, so the structured clone algorithm won't run success = JS_WriteStructuredClone(aCx, aData, &jsBytes, &mSize,
// script and we can just use AutoJSAPI.
dom::AutoJSAPI jsapi;
jsapi.Init();
success = JS_WriteStructuredClone(jsapi.cx(), aData, &jsBytes, &mSize,
nullptr, nullptr, nullptr, nullptr,
JS::UndefinedHandleValue); JS::UndefinedHandleValue);
} else { } else {
// |aData| is an object and the structured clone algorithm can run script as success = JS_WriteStructuredClone(aCx, aData, &jsBytes, &mSize,
// part of the "own" "deep clone" sub-steps, so we need an AutoEntryScript.
// http://www.whatwg.org/specs/web-apps/current-work/#internal-structured-cloning-algorithm
nsIGlobalObject* nativeGlobal =
xpc::NativeGlobal(js::GetGlobalForObjectCrossCompartment(&aData.toObject()));
dom::AutoEntryScript aes(nativeGlobal);
success = JS_WriteStructuredClone(aes.cx(), aData, &jsBytes, &mSize,
nullptr, nullptr, nullptr, nullptr,
JS::UndefinedHandleValue); JS::UndefinedHandleValue);
} }

View File

@@ -19,7 +19,7 @@ interface nsIDocument;
* structured clone algorithm. * structured clone algorithm.
* *
* You can copy an object into an nsIStructuredCloneContainer using * You can copy an object into an nsIStructuredCloneContainer using
* initFromVariant or initFromBase64. It's an error to initialize an * initFromJSVal or initFromBase64. It's an error to initialize an
* nsIStructuredCloneContainer more than once. * nsIStructuredCloneContainer more than once.
* *
* Once you've initialized the container, you can get a copy of the object it * Once you've initialized the container, you can get a copy of the object it
@@ -27,14 +27,14 @@ interface nsIDocument;
* string containing a copy of the container's serialized data, using * string containing a copy of the container's serialized data, using
* getDataAsBase64. * getDataAsBase64.
*/ */
[scriptable, uuid(8144021a-7f8a-483a-a0f1-ca02b761403f)] [scriptable, uuid(63eeafec-63f5-42c3-aea9-5c04678784e7)]
interface nsIStructuredCloneContainer : nsISupports interface nsIStructuredCloneContainer : nsISupports
{ {
/** /**
* Initialize this structured clone container so it contains a clone of the * Initialize this structured clone container so it contains a clone of the
* given jsval. * given jsval.
*/ */
[noscript] [noscript, implicit_jscontext]
void initFromJSVal(in jsval aData); void initFromJSVal(in jsval aData);
/** /**

View File

@@ -941,7 +941,7 @@ Notification::InitFromJSVal(JSContext* aCx, JS::Handle<JS::Value> aData,
return; return;
} }
mDataObjectContainer = new nsStructuredCloneContainer(); mDataObjectContainer = new nsStructuredCloneContainer();
aRv = mDataObjectContainer->InitFromJSVal(aData); aRv = mDataObjectContainer->InitFromJSVal(aData, aCx);
} }
void Notification::InitFromBase64(JSContext* aCx, const nsAString& aData, void Notification::InitFromBase64(JSContext* aCx, const nsAString& aData,

View File

@@ -9,9 +9,6 @@
[pushState must remove any tasks queued by the history traversal task source] [pushState must remove any tasks queued by the history traversal task source]
expected: FAIL expected: FAIL
[security errors are expected to be thrown in the context of the document that owns the history object (2)]
expected: FAIL
[history.state should be a separate clone of the object, not a reference to the object passed to the event handler] [history.state should be a separate clone of the object, not a reference to the object passed to the event handler]
expected: FAIL expected: FAIL

View File

@@ -12,9 +12,6 @@
[.go must queue a task with the history traversal task source (run asynchronously)] [.go must queue a task with the history traversal task source (run asynchronously)]
expected: FAIL expected: FAIL
[security errors are expected to be thrown in the context of the document that owns the history object (2)]
expected: FAIL
[history.state should be a separate clone of the object, not a reference to the object passed to the event handler] [history.state should be a separate clone of the object, not a reference to the object passed to the event handler]
expected: FAIL expected: FAIL