aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/components/script/dom/bindings/codegen/CodegenRust.py61
-rw-r--r--src/components/script/dom/bindings/error.rs24
-rw-r--r--src/components/script/dom/domexception.rs24
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 {