diff options
Diffstat (limited to 'components/script/dom')
-rw-r--r-- | components/script/dom/bindings/structuredclone.rs | 54 | ||||
-rw-r--r-- | components/script/dom/serviceworker.rs | 36 | ||||
-rw-r--r-- | components/script/dom/serviceworkercontainer.rs | 3 | ||||
-rw-r--r-- | components/script/dom/serviceworkerregistration.rs | 8 |
4 files changed, 48 insertions, 53 deletions
diff --git a/components/script/dom/bindings/structuredclone.rs b/components/script/dom/bindings/structuredclone.rs index 1078ffcacc8..21963eec172 100644 --- a/components/script/dom/bindings/structuredclone.rs +++ b/components/script/dom/bindings/structuredclone.rs @@ -11,14 +11,15 @@ use js::jsapi::{HandleValue, MutableHandleValue}; use js::jsapi::{JSContext, JS_ReadStructuredClone, JS_STRUCTURED_CLONE_VERSION}; use js::jsapi::{JS_ClearPendingException, JS_WriteStructuredClone}; use libc::size_t; -use script_traits::DOMMessage; use std::ptr; use std::slice; /// A buffer for a structured clone. -pub struct StructuredCloneData { - data: *mut u64, - nbytes: size_t, +pub enum StructuredCloneData { + /// A non-serializable (default) variant + Struct(*mut u64, size_t), + /// A variant that can be serialized + Vector(Vec<u8>) } impl StructuredCloneData { @@ -41,44 +42,47 @@ impl StructuredCloneData { } return Err(Error::DataClone); } - Ok(StructuredCloneData { - data: data, - nbytes: nbytes, - }) + Ok(StructuredCloneData::Struct(data, nbytes)) } /// Converts a StructuredCloneData to Vec<u8> for inter-thread sharing - pub fn move_to_arraybuffer(self) -> DOMMessage { - unsafe { - DOMMessage(slice::from_raw_parts(self.data as *mut u8, self.nbytes).to_vec()) - } - } - - /// Converts back to StructuredCloneData - pub fn make_structured_clone(data: DOMMessage) -> StructuredCloneData { - let DOMMessage(mut data) = data; - let nbytes = data.len(); - let data = data.as_mut_ptr() as *mut u64; - StructuredCloneData { - data: data, - nbytes: nbytes + pub fn move_to_arraybuffer(self) -> Vec<u8> { + match self { + StructuredCloneData::Struct(data, nbytes) => { + unsafe { + slice::from_raw_parts(data as *mut u8, nbytes).to_vec() + } + } + StructuredCloneData::Vector(msg) => msg } } /// Reads a structured clone. /// /// Panics if `JS_ReadStructuredClone` fails. - pub fn read(self, global: GlobalRef, rval: MutableHandleValue) { + fn read_clone(global: GlobalRef, data: *mut u64, nbytes: size_t, rval: MutableHandleValue) { unsafe { assert!(JS_ReadStructuredClone(global.get_cx(), - self.data, - self.nbytes, + data, + nbytes, JS_STRUCTURED_CLONE_VERSION, rval, ptr::null(), ptr::null_mut())); } } + + /// Thunk for the actual `read_clone` method. Resolves proper variant for read_clone. + pub fn read(self, global: GlobalRef, rval: MutableHandleValue) { + match self { + StructuredCloneData::Vector(mut vec_msg) => { + let nbytes = vec_msg.len(); + let data = vec_msg.as_mut_ptr() as *mut u64; + StructuredCloneData::read_clone(global, data, nbytes, rval); + } + StructuredCloneData::Struct(data, nbytes) => StructuredCloneData::read_clone(global, data, nbytes, rval) + } + } } unsafe impl Send for StructuredCloneData {} diff --git a/components/script/dom/serviceworker.rs b/components/script/dom/serviceworker.rs index e966173921f..9c37d73bd9e 100644 --- a/components/script/dom/serviceworker.rs +++ b/components/script/dom/serviceworker.rs @@ -11,13 +11,13 @@ use dom::bindings::global::GlobalRef; use dom::bindings::inheritance::Castable; use dom::bindings::js::Root; use dom::bindings::refcounted::Trusted; -use dom::bindings::reflector::reflect_dom_object; +use dom::bindings::reflector::{Reflectable, reflect_dom_object}; use dom::bindings::str::USVString; use dom::bindings::structuredclone::StructuredCloneData; use dom::eventtarget::EventTarget; use js::jsapi::{HandleValue, JSContext}; use script_thread::Runnable; -use script_traits::ScriptMsg; +use script_traits::{ScriptMsg, DOMMessage}; use std::cell::Cell; use url::Url; @@ -27,7 +27,7 @@ pub type TrustedServiceWorkerAddress = Trusted<ServiceWorker>; pub struct ServiceWorker { eventtarget: EventTarget, script_url: DOMRefCell<String>, - scope_url: DOMRefCell<String>, + scope_url: Url, state: Cell<ServiceWorkerState>, skip_waiting: Cell<bool> } @@ -35,21 +35,23 @@ pub struct ServiceWorker { impl ServiceWorker { fn new_inherited(script_url: &str, skip_waiting: bool, - scope_url: &str) -> ServiceWorker { + scope_url: Url) -> ServiceWorker { ServiceWorker { eventtarget: EventTarget::new_inherited(), script_url: DOMRefCell::new(String::from(script_url)), state: Cell::new(ServiceWorkerState::Installing), - scope_url: DOMRefCell::new(String::from(scope_url)), + scope_url: scope_url, skip_waiting: Cell::new(skip_waiting) } } - pub fn new(global: GlobalRef, - script_url: &str, - scope_url: &str, + pub fn install_serviceworker(global: GlobalRef, + script_url: Url, + scope_url: Url, skip_waiting: bool) -> Root<ServiceWorker> { - reflect_dom_object(box ServiceWorker::new_inherited(script_url, skip_waiting, scope_url), global, Wrap) + reflect_dom_object(box ServiceWorker::new_inherited(script_url.as_str(), + skip_waiting, + scope_url), global, Wrap) } pub fn dispatch_simple_error(address: TrustedServiceWorkerAddress) { @@ -65,16 +67,6 @@ impl ServiceWorker { pub fn get_script_url(&self) -> Url { Url::parse(&self.script_url.borrow().clone()).unwrap() } - - pub fn install_serviceworker(global: GlobalRef, - script_url: Url, - scope_url: &str, - skip_waiting: bool) -> Root<ServiceWorker> { - ServiceWorker::new(global, - script_url.as_str(), - scope_url, - skip_waiting) - } } impl ServiceWorkerMethods for ServiceWorker { @@ -96,9 +88,9 @@ impl ServiceWorkerMethods for ServiceWorker { } // Step 7 let data = try!(StructuredCloneData::write(cx, message)); - let msg_vec = data.move_to_arraybuffer(); - let scope_url = Url::parse(&*self.scope_url.borrow()).unwrap(); - let _ = self.global().r().constellation_chan().send(ScriptMsg::ForwardDOMMessage(msg_vec, scope_url)); + let msg_vec = DOMMessage(data.move_to_arraybuffer()); + let _ = self.global().r().constellation_chan().send(ScriptMsg::ForwardDOMMessage(msg_vec, + self.scope_url.clone())); Ok(()) } diff --git a/components/script/dom/serviceworkercontainer.rs b/components/script/dom/serviceworkercontainer.rs index 4487c064fe1..90e2fe1da8f 100644 --- a/components/script/dom/serviceworkercontainer.rs +++ b/components/script/dom/serviceworkercontainer.rs @@ -95,10 +95,9 @@ impl ServiceWorkerContainerMethods for ServiceWorkerContainer { return Err(Error::Type("Scope URL contains forbidden characters".to_owned())); } - let scope_str = scope.as_str().to_owned(); let worker_registration = ServiceWorkerRegistration::new(self.global().r(), script_url, - scope_str.clone(), + scope.clone(), self); ScriptThread::set_registration(scope, &*worker_registration, self.global().r().pipeline()); Ok(worker_registration) diff --git a/components/script/dom/serviceworkerregistration.rs b/components/script/dom/serviceworkerregistration.rs index c95d68856e8..a885681f629 100644 --- a/components/script/dom/serviceworkerregistration.rs +++ b/components/script/dom/serviceworkerregistration.rs @@ -25,21 +25,21 @@ pub struct ServiceWorkerRegistration { } impl ServiceWorkerRegistration { - fn new_inherited(active_sw: &ServiceWorker, scope: String) -> ServiceWorkerRegistration { + fn new_inherited(active_sw: &ServiceWorker, scope: Url) -> ServiceWorkerRegistration { ServiceWorkerRegistration { eventtarget: EventTarget::new_inherited(), active: Some(JS::from_ref(active_sw)), installing: None, waiting: None, - scope: scope, + scope: scope.as_str().to_owned(), } } #[allow(unrooted_must_root)] pub fn new(global: GlobalRef, script_url: Url, - scope: String, + scope: Url, container: &Controllable) -> Root<ServiceWorkerRegistration> { - let active_worker = ServiceWorker::install_serviceworker(global, script_url.clone(), &scope, true); + let active_worker = ServiceWorker::install_serviceworker(global, script_url.clone(), scope.clone(), true); active_worker.set_transition_state(ServiceWorkerState::Installed); container.set_controller(&*active_worker.clone()); reflect_dom_object(box ServiceWorkerRegistration::new_inherited(&*active_worker, scope), global, Wrap) |