diff options
Diffstat (limited to 'components/script/script_thread.rs')
-rw-r--r-- | components/script/script_thread.rs | 159 |
1 files changed, 87 insertions, 72 deletions
diff --git a/components/script/script_thread.rs b/components/script/script_thread.rs index f55d9279138..447b6775bdc 100644 --- a/components/script/script_thread.rs +++ b/components/script/script_thread.rs @@ -32,7 +32,7 @@ use dom::bindings::codegen::Bindings::TransitionEventBinding::TransitionEventIni use dom::bindings::codegen::Bindings::WindowBinding::WindowMethods; use dom::bindings::conversions::{ConversionResult, FromJSValConvertible, StringificationBehavior}; use dom::bindings::inheritance::Castable; -use dom::bindings::js::{JS, MutNullableHeap, Root, RootCollection}; +use dom::bindings::js::{JS, MutNullableJS, Root, RootCollection}; use dom::bindings::js::{RootCollectionPtr, RootedReference}; use dom::bindings::num::Finite; use dom::bindings::refcounted::Trusted; @@ -91,6 +91,7 @@ use script_traits::CompositorEvent::{KeyEvent, MouseButtonEvent, MouseMoveEvent, use script_traits::CompositorEvent::{TouchEvent, TouchpadPressureEvent}; use script_traits::webdriver_msg::WebDriverScriptCommand; use serviceworkerjob::{Job, JobQueue, AsyncJobHandler, FinishJobHandler, InvokeType, SettleType}; +use servo_config::opts; use servo_url::ServoUrl; use std::cell::Cell; use std::collections::{hash_map, HashMap, HashSet}; @@ -101,6 +102,7 @@ use std::result::Result; use std::sync::{Arc, Mutex}; use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::mpsc::{Receiver, Select, Sender, channel}; +use std::thread; use style::context::ReflowGoal; use style::dom::{TNode, UnsafeNode}; use style::thread_state; @@ -112,8 +114,6 @@ use task_source::networking::NetworkingTaskSource; use task_source::user_interaction::{UserInteractionTask, UserInteractionTaskSource}; use time::Tm; use url::Position; -use util::opts; -use util::thread; use webdriver_handlers; thread_local!(pub static STACK_ROOTS: Cell<Option<RootCollectionPtr>> = Cell::new(None)); @@ -461,7 +461,7 @@ pub struct ScriptThread { js_runtime: Rc<Runtime>, /// The topmost element over the mouse. - topmost_mouse_over_target: MutNullableHeap<JS<Element>>, + topmost_mouse_over_target: MutNullableJS<Element>, /// List of pipelines that have been owned and closed by this script thread. closed_pipelines: DOMRefCell<HashSet<PipelineId>>, @@ -498,13 +498,10 @@ impl<'a> ScriptMemoryFailsafe<'a> { impl<'a> Drop for ScriptMemoryFailsafe<'a> { #[allow(unrooted_must_root)] fn drop(&mut self) { - match self.owner { - Some(owner) => { - for (_, document) in owner.documents.borrow().iter() { - document.window().clear_js_runtime_for_script_deallocation(); - } + if let Some(owner) = self.owner { + for (_, document) in owner.documents.borrow().iter() { + document.window().clear_js_runtime_for_script_deallocation(); } - None => (), } } } @@ -519,8 +516,7 @@ impl ScriptThreadFactory for ScriptThread { let (sender, receiver) = channel(); let layout_chan = sender.clone(); - thread::spawn_named(format!("ScriptThread {:?}", state.id), - move || { + thread::Builder::new().name(format!("ScriptThread {:?}", state.id)).spawn(move || { thread_state::initialize(thread_state::SCRIPT); PipelineNamespace::install(state.pipeline_namespace_id); FrameId::install(state.top_level_frame_id); @@ -553,7 +549,7 @@ impl ScriptThreadFactory for ScriptThread { // This must always be the very last operation performed before the thread completes failsafe.neuter(); - }); + }).expect("Thread spawning failed"); (sender, receiver) } @@ -686,7 +682,7 @@ impl ScriptThread { devtools_sender: ipc_devtools_sender, js_runtime: Rc::new(runtime), - topmost_mouse_over_target: MutNullableHeap::new(Default::default()), + topmost_mouse_over_target: MutNullableJS::new(Default::default()), closed_pipelines: DOMRefCell::new(HashSet::new()), scheduler_chan: state.scheduler_chan, @@ -726,10 +722,8 @@ impl ScriptThread { for (id, document) in self.documents.borrow().iter() { // Only process a resize if layout is idle. - let resize_event = document.window().steal_resize_event(); - match resize_event { - Some((size, size_type)) => resizes.push((id, size, size_type)), - None => () + if let Some((size, size_type)) = document.window().steal_resize_event() { + resizes.push((id, size, size_type)); } } @@ -1050,8 +1044,11 @@ impl ScriptThread { TimerSource::FromWorker => panic!("Worker timeouts must not be sent to script thread"), }; - let window = self.documents.borrow().find_window(pipeline_id) - .expect("ScriptThread: received fire timer msg for a pipeline not in this script thread. This is a bug."); + let window = self.documents.borrow().find_window(pipeline_id); + let window = match window { + Some(w) => w, + None => return warn!("Received fire timer msg for a closed pipeline {}.", pipeline_id), + }; window.handle_fire_timer(id); } @@ -1143,7 +1140,8 @@ impl ScriptThread { } fn handle_resize(&self, id: PipelineId, size: WindowSizeData, size_type: WindowSizeType) { - if let Some(ref window) = self.documents.borrow().find_window(id) { + let window = self.documents.borrow().find_window(id); + if let Some(ref window) = window { window.set_resize_event(size, size_type); return; } @@ -1156,7 +1154,8 @@ impl ScriptThread { } fn handle_viewport(&self, id: PipelineId, rect: Rect<f32>) { - if let Some(document) = self.documents.borrow().find_document(id) { + let document = self.documents.borrow().find_document(id); + if let Some(document) = document { if document.window().set_page_clip_rect_with_new_viewport(rect) { self.rebuild_and_force_reflow(&document, ReflowReason::Viewport); } @@ -1173,7 +1172,7 @@ impl ScriptThread { fn handle_set_scroll_state(&self, id: PipelineId, scroll_states: &[(UntrustedNodeAddress, Point2D<f32>)]) { - let window = match self.documents.borrow().find_window(id) { + let window = match { self.documents.borrow().find_window(id) } { Some(window) => window, None => return warn!("Set scroll state message sent to nonexistent pipeline: {:?}", id), }; @@ -1241,7 +1240,7 @@ impl ScriptThread { } fn handle_loads_complete(&self, pipeline: PipelineId) { - let doc = match self.documents.borrow().find_document(pipeline) { + let doc = match { self.documents.borrow().find_document(pipeline) } { Some(doc) => doc, None => return warn!("Message sent to closed pipeline {}.", pipeline), }; @@ -1296,7 +1295,8 @@ impl ScriptThread { /// To slow/speed up timers and manage any other script thread resource based on visibility. /// Returns true if successful. fn alter_resource_utilization(&self, id: PipelineId, visible: bool) -> bool { - if let Some(window) = self.documents.borrow().find_window(id) { + let window = self.documents.borrow().find_window(id); + if let Some(window) = window { if visible { window.upcast::<GlobalScope>().speed_up_timers(); } else { @@ -1309,7 +1309,8 @@ impl ScriptThread { /// Updates iframe element after a change in visibility fn handle_visibility_change_complete_msg(&self, parent_pipeline_id: PipelineId, id: FrameId, visible: bool) { - if let Some(iframe) = self.documents.borrow().find_iframe(parent_pipeline_id, id) { + let iframe = self.documents.borrow().find_iframe(parent_pipeline_id, id); + if let Some(iframe) = iframe { iframe.change_visibility_status(visible); } } @@ -1337,7 +1338,8 @@ impl ScriptThread { /// Handles freeze message fn handle_freeze_msg(&self, id: PipelineId) { - if let Some(window) = self.documents.borrow().find_window(id) { + let window = self.documents.borrow().find_window(id); + if let Some(window) = window { window.upcast::<GlobalScope>().suspend(); return; } @@ -1351,7 +1353,8 @@ impl ScriptThread { /// Handles thaw message fn handle_thaw_msg(&self, id: PipelineId) { - if let Some(document) = self.documents.borrow().find_document(id) { + let document = self.documents.borrow().find_document(id); + if let Some(document) = document { if let Some(context) = document.browsing_context() { let needed_reflow = context.set_reflow_status(false); if needed_reflow { @@ -1402,14 +1405,16 @@ impl ScriptThread { parent_pipeline_id: PipelineId, frame_id: Option<FrameId>, event: MozBrowserEvent) { - match self.documents.borrow().find_document(parent_pipeline_id) { - None => warn!("Mozbrowser event after pipeline {:?} closed.", parent_pipeline_id), - Some(doc) => match frame_id { - None => doc.window().dispatch_mozbrowser_event(event), - Some(frame_id) => match doc.find_iframe(frame_id) { - None => warn!("Mozbrowser event after iframe {:?}/{:?} closed.", parent_pipeline_id, frame_id), - Some(frame_element) => frame_element.dispatch_mozbrowser_event(event), - }, + let doc = match { self.documents.borrow().find_document(parent_pipeline_id) } { + None => return warn!("Mozbrowser event after pipeline {:?} closed.", parent_pipeline_id), + Some(doc) => doc, + }; + + match frame_id { + None => doc.window().dispatch_mozbrowser_event(event), + Some(frame_id) => match doc.find_iframe(frame_id) { + None => warn!("Mozbrowser event after iframe {:?}/{:?} closed.", parent_pipeline_id, frame_id), + Some(frame_element) => frame_element.dispatch_mozbrowser_event(event), }, } } @@ -1418,7 +1423,8 @@ impl ScriptThread { parent_pipeline_id: PipelineId, frame_id: FrameId, new_pipeline_id: PipelineId) { - if let Some(frame_element) = self.documents.borrow().find_iframe(parent_pipeline_id, frame_id) { + let frame_element = self.documents.borrow().find_iframe(parent_pipeline_id, frame_id); + if let Some(frame_element) = frame_element { frame_element.update_pipeline_id(new_pipeline_id); } } @@ -1487,13 +1493,14 @@ impl ScriptThread { Some(r) => r, None => return }; - if let Some(window) = self.documents.borrow().find_window(pipeline_id) { - let script_url = maybe_registration.get_installed().get_script_url(); - let scope_things = ServiceWorkerRegistration::create_scope_things(window.upcast(), script_url); - let _ = self.constellation_chan.send(ConstellationMsg::RegisterServiceWorker(scope_things, scope.clone())); - } else { - warn!("Registration failed for {}", scope); - } + let window = match { self.documents.borrow().find_window(pipeline_id) } { + Some(window) => window, + None => return warn!("Registration failed for {}", scope), + }; + + let script_url = maybe_registration.get_installed().get_script_url(); + let scope_things = ServiceWorkerRegistration::create_scope_things(window.upcast(), script_url); + let _ = self.constellation_chan.send(ConstellationMsg::RegisterServiceWorker(scope_things, scope.clone())); } pub fn dispatch_job_queue(&self, job_handler: Box<AsyncJobHandler>) { @@ -1544,7 +1551,7 @@ impl ScriptThread { /// Handles a request for the window title. fn handle_get_title_msg(&self, pipeline_id: PipelineId) { - let document = match self.documents.borrow().find_document(pipeline_id) { + let document = match { self.documents.borrow().find_document(pipeline_id) } { Some(document) => document, None => return warn!("Message sent to closed pipeline {}.", pipeline_id), }; @@ -1601,7 +1608,7 @@ impl ScriptThread { /// Handles when layout thread finishes all animation in one tick fn handle_tick_all_animations(&self, id: PipelineId) { - let document = match self.documents.borrow().find_document(id) { + let document = match { self.documents.borrow().find_document(id) } { Some(document) => document, None => return warn!("Message sent to closed pipeline {}.", id), }; @@ -1642,7 +1649,8 @@ impl ScriptThread { /// Handles a Web font being loaded. Does nothing if the page no longer exists. fn handle_web_font_loaded(&self, pipeline_id: PipelineId) { - if let Some(document) = self.documents.borrow().find_document(pipeline_id) { + let document = self.documents.borrow().find_document(pipeline_id); + if let Some(document) = document { self.rebuild_and_force_reflow(&document, ReflowReason::WebFontLoaded); } } @@ -1650,12 +1658,14 @@ impl ScriptThread { /// Notify a window of a storage event fn handle_storage_event(&self, pipeline_id: PipelineId, storage_type: StorageType, url: ServoUrl, key: Option<String>, old_value: Option<String>, new_value: Option<String>) { - let storage = match self.documents.borrow().find_window(pipeline_id) { + let window = match { self.documents.borrow().find_window(pipeline_id) } { None => return warn!("Storage event sent to closed pipeline {}.", pipeline_id), - Some(window) => match storage_type { - StorageType::Local => window.LocalStorage(), - StorageType::Session => window.SessionStorage(), - }, + Some(window) => window, + }; + + let storage = match storage_type { + StorageType::Local => window.LocalStorage(), + StorageType::Session => window.SessionStorage(), }; storage.queue_storage_event(url, key, old_value, new_value); @@ -1908,7 +1918,7 @@ impl ScriptThread { } MouseMoveEvent(point) => { - let document = match self.documents.borrow().find_document(pipeline_id) { + let document = match { self.documents.borrow().find_document(pipeline_id) } { Some(document) => document, None => return warn!("Message sent to closed pipeline {}.", pipeline_id), }; @@ -1980,17 +1990,19 @@ impl ScriptThread { } TouchpadPressureEvent(point, pressure, phase) => { - match self.documents.borrow().find_document(pipeline_id) { - Some(doc) => doc.handle_touchpad_pressure_event(self.js_runtime.rt(), point, pressure, phase), - None => warn!("Message sent to closed pipeline {}.", pipeline_id), - } + let doc = match { self.documents.borrow().find_document(pipeline_id) } { + Some(doc) => doc, + None => return warn!("Message sent to closed pipeline {}.", pipeline_id), + }; + doc.handle_touchpad_pressure_event(self.js_runtime.rt(), point, pressure, phase); } KeyEvent(ch, key, state, modifiers) => { - match self.documents.borrow().find_document(pipeline_id) { - Some(document) => document.dispatch_key_event(ch, key, state, modifiers, &self.constellation_chan), - None => warn!("Message sent to closed pipeline {}.", pipeline_id), - } + let document = match { self.documents.borrow().find_document(pipeline_id) } { + Some(document) => document, + None => return warn!("Message sent to closed pipeline {}.", pipeline_id), + }; + document.dispatch_key_event(ch, key, state, modifiers, &self.constellation_chan); } } } @@ -2000,10 +2012,11 @@ impl ScriptThread { mouse_event_type: MouseEventType, button: MouseButton, point: Point2D<f32>) { - match self.documents.borrow().find_document(pipeline_id) { - Some(document) => document.handle_mouse_event(self.js_runtime.rt(), button, point, mouse_event_type), - None => warn!("Message sent to closed pipeline {}.", pipeline_id), - } + let document = match { self.documents.borrow().find_document(pipeline_id) } { + Some(document) => document, + None => return warn!("Message sent to closed pipeline {}.", pipeline_id), + }; + document.handle_mouse_event(self.js_runtime.rt(), button, point, mouse_event_type); } fn handle_touch_event(&self, @@ -2012,13 +2025,14 @@ impl ScriptThread { identifier: TouchId, point: Point2D<f32>) -> TouchEventResult { - match self.documents.borrow().find_document(pipeline_id) { - Some(document) => document.handle_touch_event(self.js_runtime.rt(), event_type, identifier, point), + let document = match { self.documents.borrow().find_document(pipeline_id) } { + Some(document) => document, None => { warn!("Message sent to closed pipeline {}.", pipeline_id); - TouchEventResult::Processed(true) + return TouchEventResult::Processed(true); }, - } + }; + document.handle_touch_event(self.js_runtime.rt(), event_type, identifier, point) } /// https://html.spec.whatwg.org/multipage/#navigating-across-documents @@ -2044,7 +2058,7 @@ impl ScriptThread { } fn handle_resize_event(&self, pipeline_id: PipelineId, new_size: WindowSizeData, size_type: WindowSizeType) { - let document = match self.documents.borrow().find_document(pipeline_id) { + let document = match { self.documents.borrow().find_document(pipeline_id) } { Some(document) => document, None => return warn!("Message sent to closed pipeline {}.", pipeline_id), }; @@ -2127,7 +2141,7 @@ impl ScriptThread { } fn handle_parsing_complete(&self, id: PipelineId) { - let document = match self.documents.borrow().find_document(id) { + let document = match { self.documents.borrow().find_document(id) } { Some(document) => document, None => return, }; @@ -2175,7 +2189,8 @@ impl ScriptThread { } fn handle_reload(&self, pipeline_id: PipelineId) { - if let Some(window) = self.documents.borrow().find_window(pipeline_id) { + let window = self.documents.borrow().find_window(pipeline_id); + if let Some(window) = window { window.Location().Reload(); } } |