diff --git a/components/script/dom/bindings/codegen/CodegenRust.py b/components/script/dom/bindings/codegen/CodegenRust.py index 449fda3b7ea..6da269d61cb 100644 --- a/components/script/dom/bindings/codegen/CodegenRust.py +++ b/components/script/dom/bindings/codegen/CodegenRust.py @@ -344,12 +344,17 @@ class CGMethodCall(CGThing): distinguishingIndex = method.distinguishingIndexForArgCount(argCount) - # We can't handle unions at the distinguishing index. + # We can't handle unions of non-object values at the distinguishing index. for (returnType, args) in possibleSignatures: - if args[distinguishingIndex].type.isUnion(): - raise TypeError("No support for unions as distinguishing " - "arguments yet: %s", - args[distinguishingIndex].location) + type = args[distinguishingIndex].type + if type.isUnion(): + if type.nullable(): + type = type.inner + for type in type.flatMemberTypes: + if not (type.isObject() or type.isNonCallbackInterface()): + raise TypeError("No support for unions with non-object variants " + "as distinguishing arguments yet: %s", + args[distinguishingIndex].location) # Convert all our arguments up to the distinguishing index. # Doesn't matter which of the possible signatures we use, since @@ -388,6 +393,7 @@ class CGMethodCall(CGThing): interfacesSigs = [ s for s in possibleSignatures if (s[1][distinguishingIndex].type.isObject() or + s[1][distinguishingIndex].type.isUnion() or s[1][distinguishingIndex].type.isNonCallbackInterface())] # There might be more than one of these; we need to check # which ones we unwrap to. @@ -2366,7 +2372,6 @@ def UnionTypes(descriptors, dictionaries, callbacks, typedefs, config): 'dom::bindings::conversions::ConversionBehavior', 'dom::bindings::conversions::StringificationBehavior', 'dom::bindings::conversions::root_from_handlevalue', - 'dom::bindings::error::throw_not_in_union', 'std::ptr::NonNull', 'dom::bindings::mozmap::MozMap', 'dom::bindings::root::DomRoot', @@ -4450,8 +4455,8 @@ class CGUnionConversionStruct(CGThing): other.append(booleanConversion[0]) conversions.append(CGList(other, "\n\n")) conversions.append(CGGeneric( - "throw_not_in_union(cx, \"%s\");\n" - "Err(())" % ", ".join(names))) + "Ok(ConversionResult::Failure(\"argument could not be converted to any of: %s\".into()))" % ", ".join(names) + )) method = CGWrapper( CGIndenter(CGList(conversions, "\n\n")), pre="unsafe fn from_jsval(cx: *mut JSContext,\n" diff --git a/components/script/dom/bindings/error.rs b/components/script/dom/bindings/error.rs index c953df65c1d..7c68de0df18 100644 --- a/components/script/dom/bindings/error.rs +++ b/components/script/dom/bindings/error.rs @@ -255,14 +255,6 @@ pub unsafe fn report_pending_exception(cx: *mut JSContext, dispatch_event: bool) } } -/// Throw an exception to signal that a `JSVal` can not be converted to any of -/// the types in an IDL union type. -pub unsafe fn throw_not_in_union(cx: *mut JSContext, names: &'static str) { - assert!(!JS_IsExceptionPending(cx)); - let error = format!("argument could not be converted to any of: {}", names); - throw_type_error(cx, &error); -} - /// Throw an exception to signal that a `JSObject` can not be converted to a /// given DOM type. pub unsafe fn throw_invalid_this(cx: *mut JSContext, proto_id: u16) { diff --git a/components/script/dom/webgl2renderingcontext.rs b/components/script/dom/webgl2renderingcontext.rs index 811fc100e6b..69ef20e4fc2 100644 --- a/components/script/dom/webgl2renderingcontext.rs +++ b/components/script/dom/webgl2renderingcontext.rs @@ -240,14 +240,18 @@ impl WebGL2RenderingContextMethods for WebGL2RenderingContext { self.base.GenerateMipmap(target) } - #[allow(unsafe_code)] /// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5 - unsafe fn BufferData(&self, cx: *mut JSContext, target: u32, data: *mut JSObject, usage: u32) -> Fallible<()> { - self.base.BufferData(cx, target, data, usage) + fn BufferData( + &self, + target: u32, + data: Option, + usage: u32, + ) { + self.base.BufferData(target, data, usage) } /// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5 - fn BufferData_(&self, target: u32, size: i64, usage: u32) -> Fallible<()> { + fn BufferData_(&self, target: u32, size: i64, usage: u32) { self.base.BufferData_(target, size, usage) } diff --git a/components/script/dom/webglrenderingcontext.rs b/components/script/dom/webglrenderingcontext.rs index bb4304e3276..546a0950ea4 100644 --- a/components/script/dom/webglrenderingcontext.rs +++ b/components/script/dom/webglrenderingcontext.rs @@ -1326,19 +1326,6 @@ impl Drop for WebGLRenderingContext { } } -#[allow(unsafe_code)] -unsafe fn fallible_array_buffer_view_to_vec( - cx: *mut JSContext, - abv: *mut JSObject, -) -> Result, Error> { - assert!(!abv.is_null()); - typedarray!(in(cx) let array_buffer_view: ArrayBufferView = abv); - match array_buffer_view { - Ok(v) => Ok(v.to_vec()), - Err(_) => Err(Error::Type("Not an ArrayBufferView".to_owned())), - } -} - impl WebGLRenderingContextMethods for WebGLRenderingContext { // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.1 fn Canvas(&self) -> DomRoot { @@ -1894,52 +1881,44 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext { handle_potential_webgl_error!(self, texture.generate_mipmap()); } - #[allow(unsafe_code)] // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5 - unsafe fn BufferData( + fn BufferData( &self, - cx: *mut JSContext, target: u32, - data: *mut JSObject, + data: Option, usage: u32, - ) -> ErrorResult { - if data.is_null() { - return Ok(self.webgl_error(InvalidValue)); - } - - typedarray!(in(cx) let array_buffer: ArrayBuffer = data); - let data_vec = match array_buffer { - Ok(data) => data.to_vec(), - Err(_) => fallible_array_buffer_view_to_vec(cx, data)?, + ) { + let data = match data { + Some(ArrayBufferViewOrArrayBuffer::ArrayBuffer(data)) => data.to_vec(), + Some(ArrayBufferViewOrArrayBuffer::ArrayBufferView(data)) => data.to_vec(), + None => return self.webgl_error(InvalidValue), }; - let bound_buffer = handle_potential_webgl_error!(self, self.bound_buffer(target), return Ok(())); + let bound_buffer = handle_potential_webgl_error!(self, self.bound_buffer(target), return); let bound_buffer = match bound_buffer { Some(bound_buffer) => bound_buffer, - None => return Ok(self.webgl_error(InvalidOperation)), + None => return self.webgl_error(InvalidOperation), }; - handle_potential_webgl_error!(self, bound_buffer.buffer_data(target, data_vec, usage)); - Ok(()) + handle_potential_webgl_error!(self, bound_buffer.buffer_data(target, data, usage)); } // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5 - fn BufferData_(&self, target: u32, size: i64, usage: u32) -> ErrorResult { - let bound_buffer = handle_potential_webgl_error!(self, self.bound_buffer(target), return Ok(())); + fn BufferData_(&self, target: u32, size: i64, usage: u32) { + let bound_buffer = handle_potential_webgl_error!(self, self.bound_buffer(target), return); let bound_buffer = match bound_buffer { Some(bound_buffer) => bound_buffer, - None => return Ok(self.webgl_error(InvalidOperation)), + None => return self.webgl_error(InvalidOperation), }; if size < 0 { - return Ok(self.webgl_error(InvalidValue)); + return self.webgl_error(InvalidValue); } // FIXME: Allocating a buffer based on user-requested size is // not great, but we don't have a fallible allocation to try. let data = vec![0u8; size as usize]; handle_potential_webgl_error!(self, bound_buffer.buffer_data(target, data, usage)); - Ok(()) } // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.5 diff --git a/components/script/dom/webidls/WebGL2RenderingContext.webidl b/components/script/dom/webidls/WebGL2RenderingContext.webidl index b14711d107e..88a2fb273b6 100644 --- a/components/script/dom/webidls/WebGL2RenderingContext.webidl +++ b/components/script/dom/webidls/WebGL2RenderingContext.webidl @@ -305,10 +305,7 @@ interface WebGL2RenderingContextBase /* Buffer objects */ // WebGL1: // BUG: https://github.com/KhronosGroup/WebGL/issues/2216 - // FIXME(xanewok): https://github.com/servo/servo/issues/20513 - [Throws] - void bufferData(GLenum target, object? data, GLenum usage); - [Throws] + void bufferData(GLenum target, /*[AllowShared]*/ BufferSource? data, GLenum usage); void bufferData(GLenum target, GLsizeiptr size, GLenum usage); void bufferSubData(GLenum target, GLintptr dstByteOffset, /*[AllowShared]*/ BufferSource srcData); // WebGL2: diff --git a/components/script/dom/webidls/WebGLRenderingContext.webidl b/components/script/dom/webidls/WebGLRenderingContext.webidl index 2ad85964e5a..2a5d8cf99d0 100644 --- a/components/script/dom/webidls/WebGLRenderingContext.webidl +++ b/components/script/dom/webidls/WebGLRenderingContext.webidl @@ -688,10 +688,7 @@ interface WebGLRenderingContext { // BUG: https://github.com/KhronosGroup/WebGL/issues/2216 - // FIXME(xanewok): https://github.com/servo/servo/issues/20513 - [Throws] - void bufferData(GLenum target, object? data, GLenum usage); - [Throws] + void bufferData(GLenum target, /*[AllowShared]*/ BufferSource? data, GLenum usage); void bufferData(GLenum target, GLsizeiptr size, GLenum usage); void bufferSubData(GLenum target, GLintptr offset, /*[AllowShared]*/ BufferSource data); diff --git a/tests/wpt/webgl/meta/conformance/buffers/buffer-data-and-buffer-sub-data.html.ini b/tests/wpt/webgl/meta/conformance/buffers/buffer-data-and-buffer-sub-data.html.ini deleted file mode 100644 index a88889c1dc2..00000000000 --- a/tests/wpt/webgl/meta/conformance/buffers/buffer-data-and-buffer-sub-data.html.ini +++ /dev/null @@ -1,6 +0,0 @@ -[buffer-data-and-buffer-sub-data.html] - bug: https://github.com/servo/servo/issues/20513 - expected: ERROR - [WebGL test #27: successfullyParsed should be true (of type boolean). Was undefined (of type undefined).] - expected: FAIL - diff --git a/tests/wpt/webgl/meta/conformance/misc/type-conversion-test.html.ini b/tests/wpt/webgl/meta/conformance/misc/type-conversion-test.html.ini deleted file mode 100644 index d3a7c9af95b..00000000000 --- a/tests/wpt/webgl/meta/conformance/misc/type-conversion-test.html.ini +++ /dev/null @@ -1,20 +0,0 @@ -[type-conversion-test.html] - bug: https://github.com/servo/servo/issues/20513 - [WebGL test #340: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL - - [WebGL test #407: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL - - [WebGL test #474: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL - - [WebGL test #541: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL - - [WebGL test #608: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL - - [WebGL test #675: context.bufferData(context.ARRAY_BUFFER, argument, context.STATIC_DRAW) should be undefined. Threw exception TypeError: Not an ArrayBufferView] - expected: FAIL -