Commit e9c887a8 authored by junov@chromium.org's avatar junov@chromium.org

Fix crash when creating an ImageBitmap from an invalid canvas

BUG=354356

Review URL: https://codereview.chromium.org/211313003

git-svn-id: svn://svn.chromium.org/blink/trunk@169973 bbb929c8-8fbe-4397-9dbb-9b2b20218538
parent a9ca2310
...@@ -21,6 +21,7 @@ PASS createImageBitmap(testBitmap, 0, 0, 0, 10) threw exception IndexSizeError: ...@@ -21,6 +21,7 @@ PASS createImageBitmap(testBitmap, 0, 0, 0, 10) threw exception IndexSizeError:
PASS createImageBitmap(blob, 0, 0, 10, 0) threw exception IndexSizeError: Failed to execute 'createImageBitmap' on 'Window': The source height provided is 0.. PASS createImageBitmap(blob, 0, 0, 10, 0) threw exception IndexSizeError: Failed to execute 'createImageBitmap' on 'Window': The source height provided is 0..
PASS createImageBitmap(blob, 0, 0, 0, 10) threw exception IndexSizeError: Failed to execute 'createImageBitmap' on 'Window': The source width provided is 0.. PASS createImageBitmap(blob, 0, 0, 0, 10) threw exception IndexSizeError: Failed to execute 'createImageBitmap' on 'Window': The source width provided is 0..
PASS createImageBitmap(invalidBlob) was rejected. PASS createImageBitmap(invalidBlob) was rejected.
PASS createImageBitmap(invalidCanvas) was rejected.
PASS successfullyParsed is true PASS successfullyParsed is true
TEST COMPLETE TEST COMPLETE
......
...@@ -16,6 +16,8 @@ var testBitmap; // an ImageBitmap that is uncropped. We use this to test createI ...@@ -16,6 +16,8 @@ var testBitmap; // an ImageBitmap that is uncropped. We use this to test createI
var d; // image.imageData var d; // image.imageData
var blob; var blob;
var invalidBlob; var invalidBlob;
var invalidBlobTestPassed = false;
var invalidCanvasTestPassed = false;
// Draw to an auxillary canvas. // Draw to an auxillary canvas.
var aCanvas = document.createElement("canvas"); var aCanvas = document.createElement("canvas");
...@@ -23,6 +25,11 @@ aCanvas.setAttribute("width", "200"); ...@@ -23,6 +25,11 @@ aCanvas.setAttribute("width", "200");
aCanvas.setAttribute("height", "200"); aCanvas.setAttribute("height", "200");
var aCtx = aCanvas.getContext("2d"); var aCtx = aCanvas.getContext("2d");
// Create a terapixel canvas to generate an invalid canvas through allocation failure
var invalidCanvas = document.createElement("canvas");
invalidCanvas.setAttribute("width", "1000000");
invalidCanvas.setAttribute("height", "1000000");
image = new Image(); image = new Image();
image.onload = imageLoaded; image.onload = imageLoaded;
...@@ -84,6 +91,26 @@ xhr2.onload = function() { ...@@ -84,6 +91,26 @@ xhr2.onload = function() {
loaded(); loaded();
} }
var finishIfDoneCallsRemaining = 2;
function finishIfDone() {
finishIfDoneCallsRemaining--;
if (!finishIfDoneCallsRemaining) {
// Because promise fulfillment is asynchonous, pass/fail messages
// must be handled here to ensure a deterministic message order.
if (invalidBlobTestPassed) {
testPassed("createImageBitmap(invalidBlob) was rejected.");
} else {
testFailed("Invalid blob fulfilled.");
}
if (invalidCanvasTestPassed) {
testPassed("createImageBitmap(invalidCanvas) was rejected.");
} else {
testFailed("Invalid canvas fulfilled.");
}
finishJSTest();
}
}
function loaded() { function loaded() {
if (imageLoaded && videoLoaded && imageBitmapLoaded && blobLoaded && invalidBlobLoaded) { if (imageLoaded && videoLoaded && imageBitmapLoaded && blobLoaded && invalidBlobLoaded) {
shouldThrow("createImageBitmap(undefined)", "TypeError"); shouldThrow("createImageBitmap(undefined)", "TypeError");
...@@ -110,15 +137,20 @@ function loaded() { ...@@ -110,15 +137,20 @@ function loaded() {
shouldThrow("createImageBitmap(blob, 0, 0, 0, 10)"); shouldThrow("createImageBitmap(blob, 0, 0, 0, 10)");
createImageBitmap(invalidBlob).then(function() { createImageBitmap(invalidBlob).then(function() {
testFailed("Invalid blob fulfilled."); finishIfDone();
finishJSTest();
}, function() { }, function() {
testPassed("createImageBitmap(invalidBlob) was rejected."); invalidBlobTestPassed = true;
finishJSTest(); finishIfDone();
}); });
}
}
createImageBitmap(invalidCanvas).then(function() {
finishIfDone();
}, function() {
invalidCanvasTestPassed = true;
finishIfDone();
});
}
}
</script> </script>
</body> </body>
</html> </html>
...@@ -67,7 +67,12 @@ static ScriptPromise fulfillImageBitmap(ExecutionContext* context, PassRefPtrWil ...@@ -67,7 +67,12 @@ static ScriptPromise fulfillImageBitmap(ExecutionContext* context, PassRefPtrWil
{ {
RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(context); RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(context);
ScriptPromise promise = resolver->promise(); ScriptPromise promise = resolver->promise();
resolver->resolve(imageBitmap); if (imageBitmap) {
resolver->resolve(imageBitmap);
} else {
v8::Isolate* isolate = ScriptState::current()->isolate();
resolver->reject(ScriptValue(v8::Null(isolate), isolate));
}
return promise; return promise;
} }
...@@ -185,8 +190,9 @@ ScriptPromise ImageBitmapFactories::createImageBitmap(EventTarget& eventTarget, ...@@ -185,8 +190,9 @@ ScriptPromise ImageBitmapFactories::createImageBitmap(EventTarget& eventTarget,
exceptionState.throwDOMException(IndexSizeError, String::format("The source %s provided is 0.", sw ? "height" : "width")); exceptionState.throwDOMException(IndexSizeError, String::format("The source %s provided is 0.", sw ? "height" : "width"));
return ScriptPromise(); return ScriptPromise();
} }
// FIXME: make ImageBitmap creation asynchronous crbug.com/258082 // FIXME: make ImageBitmap creation asynchronous crbug.com/258082
return fulfillImageBitmap(eventTarget.executionContext(), ImageBitmap::create(canvas, IntRect(sx, sy, sw, sh))); return fulfillImageBitmap(eventTarget.executionContext(), canvas->buffer() ? ImageBitmap::create(canvas, IntRect(sx, sy, sw, sh)) : nullptr);
} }
ScriptPromise ImageBitmapFactories::createImageBitmap(EventTarget& eventTarget, Blob* blob, ExceptionState& exceptionState) ScriptPromise ImageBitmapFactories::createImageBitmap(EventTarget& eventTarget, Blob* blob, ExceptionState& exceptionState)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment