diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/components/script/dom/bindings/codegen/CodegenRust.py | 61 | ||||
-rw-r--r-- | src/components/script/dom/bindings/error.rs | 24 | ||||
-rw-r--r-- | src/components/script/dom/domexception.rs | 24 |
3 files changed, 67 insertions, 42 deletions
diff --git a/src/components/script/dom/bindings/codegen/CodegenRust.py b/src/components/script/dom/bindings/codegen/CodegenRust.py index a6da30bad29..fb66afa5a42 100644 --- a/src/components/script/dom/bindings/codegen/CodegenRust.py +++ b/src/components/script/dom/bindings/codegen/CodegenRust.py @@ -2129,19 +2129,21 @@ class CGCallGenerator(CGThing): A class to generate an actual call to a C++ object. Assumes that the C++ object is stored in a variable whose name is given by the |object| argument. - errorReport should be a CGThing for an error report or None if no - error reporting is needed. + errorResult should be a string for the value to return in case of an + exception from the native code, or None if no error reporting is needed. """ - def __init__(self, errorReport, arguments, argsPre, returnType, + def __init__(self, errorResult, arguments, argsPre, returnType, extendedAttributes, descriptorProvider, nativeMethodName, static, object="this"): CGThing.__init__(self) - assert errorReport is None or isinstance(errorReport, CGThing) + assert errorResult is None or isinstance(errorResult, str) - isFallible = errorReport is not None + isFallible = errorResult is not None result = getRetvalDeclarationForType(returnType, descriptorProvider) + if isFallible: + result = CGWrapper(result, pre="Result<", post=", Error>") args = CGList([CGGeneric(arg) for arg in argsPre], ", ") for (a, name) in arguments: @@ -2172,26 +2174,29 @@ class CGCallGenerator(CGThing): call = CGWrapper(call, pre="(*%s)." % object) call = CGList([call, CGWrapper(args, pre="(", post=");")]) - if isFallible: - self.cgRoot.prepend(CGWrapper(result, - pre="let result_fallible: Result<", post=",Error>;")) - - result = CGWrapper(result, pre="let result: ", post=";") - self.cgRoot.prepend(result) - - if isFallible: - call = CGWrapper(call, pre="result_fallible = ") - else: - call = CGWrapper(call, pre="result = ") - - call = CGWrapper(call) - self.cgRoot.append(call) + self.cgRoot.append(CGList([ + CGGeneric("let result: "), + result, + CGGeneric(" = "), + call, + CGGeneric(";"), + ])) if isFallible: - self.cgRoot.append(CGGeneric("if result_fallible.is_err() {")) - self.cgRoot.append(CGIndenter(errorReport)) - self.cgRoot.append(CGGeneric("}")) - self.cgRoot.append(CGGeneric("result = result_fallible.unwrap();")) + if static: + glob = "" + else: + glob = " let global = global_object_for_js_object(this.reflector().get_jsobject()).root();\n" + + self.cgRoot.append(CGGeneric( + "let result = match result {\n" + " Ok(result) => result,\n" + " Err(e) => {\n" + "%s" + " throw_dom_exception(cx, &*global, e);\n" + " return%s;" + " },\n" + "};\n" % (glob, errorResult))) if typeRetValNeedsRooting(returnType): self.cgRoot.append(CGGeneric("let result = result.root();")) @@ -2250,7 +2255,7 @@ class CGPerSignatureCall(CGThing): i in range(argConversionStartsAt, self.argCount)]) cgThings.append(CGCallGenerator( - self.getErrorReport() if self.isFallible() else None, + ' false as JSBool' if self.isFallible() else None, self.getArguments(), self.argsPre, returnType, self.extendedAttributes, descriptor, nativeMethodName, static)) @@ -2276,12 +2281,6 @@ class CGPerSignatureCall(CGThing): def wrap_return_value(self): return wrapForType('*vp') - def getErrorReport(self): - return CGGeneric( - 'return throw_method_failed_with_details(cx, result_fallible, "%s", "%s");' % - (self.descriptor.interface.identifier.name, - self.idlNode.identifier.name)) - def define(self): return (self.cgRoot.define() + "\n" + self.wrap_return_value()) @@ -4302,7 +4301,7 @@ class CGBindingRoot(CGThing): 'dom::bindings::codegen::BindingDeclarations::*', 'dom::bindings::codegen::UnionTypes::*', 'dom::bindings::error::{FailureUnknown, Fallible, Error, ErrorResult}', - 'dom::bindings::error::{throw_method_failed_with_details}', + 'dom::bindings::error::throw_dom_exception', 'dom::bindings::error::throw_type_error', 'dom::bindings::proxyhandler', 'dom::bindings::proxyhandler::{_obj_toString, defineProperty}', diff --git a/src/components/script/dom/bindings/error.rs b/src/components/script/dom/bindings/error.rs index f47f28c95b6..db3337b6de2 100644 --- a/src/components/script/dom/bindings/error.rs +++ b/src/components/script/dom/bindings/error.rs @@ -2,8 +2,13 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ +use dom::bindings::conversions::ToJSValConvertible; +use dom::bindings::js::JSRef; +use dom::domexception::DOMException; +use dom::window::Window; + use js::jsapi::{JSContext, JSBool}; -use js::jsapi::{JS_IsExceptionPending}; +use js::jsapi::{JS_IsExceptionPending, JS_SetPendingException}; use js::jsapi::{JS_ReportErrorNumber, JSErrorFormatString, JSEXN_TYPEERR}; use js::glue::{ReportError}; @@ -29,17 +34,14 @@ pub type Fallible<T> = Result<T, Error>; pub type ErrorResult = Fallible<()>; -pub fn throw_method_failed_with_details<T>(cx: *mut JSContext, - result: Result<T, Error>, - interface: &'static str, - member: &'static str) -> JSBool { - assert!(result.is_err()); +pub fn throw_dom_exception(cx: *mut JSContext, global: &JSRef<Window>, + result: Error) { assert!(unsafe { JS_IsExceptionPending(cx) } == 0); - let message = format!("Method failed: {}.{}", interface, member); - message.with_c_str(|string| { - unsafe { ReportError(cx, string) }; - }); - return 0; + let exception = DOMException::new_from_error(global, result).root(); + let thrown = exception.to_jsval(cx); + unsafe { + JS_SetPendingException(cx, thrown); + } } pub fn throw_not_in_union(cx: *mut JSContext, names: &'static str) -> JSBool { diff --git a/src/components/script/dom/domexception.rs b/src/components/script/dom/domexception.rs index 860e3f72be0..e230259d0f1 100644 --- a/src/components/script/dom/domexception.rs +++ b/src/components/script/dom/domexception.rs @@ -4,6 +4,8 @@ use dom::bindings::codegen::BindingDeclarations::DOMExceptionBinding; use dom::bindings::codegen::BindingDeclarations::DOMExceptionBinding::DOMExceptionConstants; +use dom::bindings::error; +use dom::bindings::error::Error; use dom::bindings::js::{JSRef, Temporary}; use dom::bindings::utils::{Reflectable, Reflector, reflect_dom_object}; use dom::window::Window; @@ -35,6 +37,24 @@ pub enum DOMErrorName { EncodingError } +impl DOMErrorName { + fn from_error(error: Error) -> DOMErrorName { + match error { + error::IndexSize => IndexSizeError, + error::NotFound => NotFoundError, + error::HierarchyRequest => HierarchyRequestError, + error::InvalidCharacter => InvalidCharacterError, + error::NotSupported => NotSupportedError, + error::InvalidState => InvalidStateError, + error::NamespaceError => NamespaceError, + error::Syntax => SyntaxError, + error::Security => SecurityError, + error::Network => NetworkError, + error::FailureUnknown => fail!(), + } + } +} + #[deriving(Encodable)] pub struct DOMException { pub code: DOMErrorName, @@ -52,6 +72,10 @@ impl DOMException { pub fn new(window: &JSRef<Window>, code: DOMErrorName) -> Temporary<DOMException> { reflect_dom_object(box DOMException::new_inherited(code), window, DOMExceptionBinding::Wrap) } + + pub fn new_from_error(window: &JSRef<Window>, code: Error) -> Temporary<DOMException> { + DOMException::new(window, DOMErrorName::from_error(code)) + } } impl Reflectable for DOMException { |