diff options
author | Zhen Zhang <izgzhen@gmail.com> | 2016-05-18 00:07:42 +0800 |
---|---|---|
committer | Zhen Zhang <izgzhen@gmail.com> | 2016-05-20 08:00:16 +0800 |
commit | a51db4cfa857d7567ce1078830f5c00ea7bd9f59 (patch) | |
tree | 9a604ff41983c9bded331f4ec80f94c9f6b1cd45 | |
parent | 051a749e0d0ff298a3cbce8c6284386dc0d67f24 (diff) | |
download | servo-a51db4cfa857d7567ce1078830f5c00ea7bd9f59.tar.gz servo-a51db4cfa857d7567ce1078830f5c00ea7bd9f59.zip |
Implement trait-based ResourceThreads and clean up related naming issues
Changes include:
- Introduce an IpcSend trait to abstract over a collection of IpcSenders
- Implement ResourceThreads collection to abstract the resource-related
sub threads across the component
- Rename original ResourceThread and ControlMsg into an unifed CoreResource__
to accommodate above changes and avoid confusions
22 files changed, 213 insertions, 179 deletions
diff --git a/components/compositing/pipeline.rs b/components/compositing/pipeline.rs index 15550f99002..b1f76bd0ec0 100644 --- a/components/compositing/pipeline.rs +++ b/components/compositing/pipeline.rs @@ -16,10 +16,9 @@ use layers::geometry::DevicePixel; use layout_traits::{LayoutControlChan, LayoutThreadFactory}; use msg::constellation_msg::{FrameId, LoadData, PanicMsg, PipelineId}; use msg::constellation_msg::{PipelineNamespaceId, SubpageId, WindowSizeData}; -use net_traits::ResourceThread; +use net_traits::ResourceThreads; use net_traits::bluetooth_thread::BluetoothMethodMsg; use net_traits::image_cache_thread::ImageCacheThread; -use net_traits::storage_thread::StorageThread; use profile_traits::mem as profile_mem; use profile_traits::time; use script_traits::{ConstellationControlMsg, InitialScriptState, MozBrowserEvent}; @@ -98,10 +97,8 @@ pub struct InitialPipelineState { pub image_cache_thread: ImageCacheThread, /// A channel to the font cache thread. pub font_cache_thread: FontCacheThread, - /// A channel to the resource thread. - pub resource_thread: ResourceThread, - /// A channel to the storage thread. - pub storage_thread: StorageThread, + /// Channels to the resource-related threads. + pub resource_threads: ResourceThreads, /// A channel to the time profiler thread. pub time_profiler_chan: time::ProfilerChan, /// A channel to the memory profiler thread. @@ -219,8 +216,7 @@ impl Pipeline { bluetooth_thread: state.bluetooth_thread, image_cache_thread: state.image_cache_thread, font_cache_thread: state.font_cache_thread.clone(), - resource_thread: state.resource_thread, - storage_thread: state.storage_thread, + resource_threads: state.resource_threads, time_profiler_chan: state.time_profiler_chan.clone(), mem_profiler_chan: state.mem_profiler_chan.clone(), window_size: window_size, @@ -396,8 +392,7 @@ pub struct UnprivilegedPipelineContent { bluetooth_thread: IpcSender<BluetoothMethodMsg>, image_cache_thread: ImageCacheThread, font_cache_thread: FontCacheThread, - resource_thread: ResourceThread, - storage_thread: StorageThread, + resource_threads: ResourceThreads, time_profiler_chan: time::ProfilerChan, mem_profiler_chan: profile_mem::ProfilerChan, window_size: Option<WindowSizeData>, @@ -435,8 +430,7 @@ impl UnprivilegedPipelineContent { scheduler_chan: self.scheduler_chan.clone(), panic_chan: self.panic_chan.clone(), bluetooth_thread: self.bluetooth_thread.clone(), - resource_thread: self.resource_thread, - storage_thread: self.storage_thread.clone(), + resource_threads: self.resource_threads, image_cache_thread: self.image_cache_thread.clone(), time_profiler_chan: self.time_profiler_chan.clone(), mem_profiler_chan: self.mem_profiler_chan.clone(), diff --git a/components/constellation/constellation.rs b/components/constellation/constellation.rs index 4b2a0d431c5..88f8bd02265 100644 --- a/components/constellation/constellation.rs +++ b/components/constellation/constellation.rs @@ -43,8 +43,8 @@ use msg::constellation_msg::{self, PanicMsg}; use msg::webdriver_msg; use net_traits::bluetooth_thread::BluetoothMethodMsg; use net_traits::image_cache_thread::ImageCacheThread; -use net_traits::storage_thread::{StorageThread, StorageThreadMsg}; -use net_traits::{self, ResourceThread}; +use net_traits::storage_thread::StorageThreadMsg; +use net_traits::{self, ResourceThreads, IpcSend}; use offscreen_gl_context::{GLContextAttributes, GLLimits}; use profile_traits::mem; use profile_traits::time; @@ -118,8 +118,8 @@ pub struct Constellation<LTF, STF> { /// to the compositor. compositor_proxy: Box<CompositorProxy>, - /// A channel through which messages can be sent to the resource thread. - resource_thread: ResourceThread, + /// Channels through which messages can be sent to the resource-related threads. + resource_threads: ResourceThreads, /// A channel through which messages can be sent to the image cache thread. image_cache_thread: ImageCacheThread, @@ -130,9 +130,6 @@ pub struct Constellation<LTF, STF> { /// A channel through which messages can be sent to the bluetooth thread. bluetooth_thread: IpcSender<BluetoothMethodMsg>, - /// A channel through which messages can be sent to the storage thread. - storage_thread: StorageThread, - /// A list of all the pipelines. (See the `pipeline` module for more details.) pipelines: HashMap<PipelineId, Pipeline>, @@ -212,9 +209,7 @@ pub struct InitialConstellationState { /// A channel to the font cache thread. pub font_cache_thread: FontCacheThread, /// A channel to the resource thread. - pub resource_thread: ResourceThread, - /// A channel to the storage thread. - pub storage_thread: StorageThread, + pub resource_threads: ResourceThreads, /// A channel to the time profiler thread. pub time_profiler_chan: time::ProfilerChan, /// A channel to the memory profiler thread. @@ -348,10 +343,9 @@ impl<LTF: LayoutThreadFactory, STF: ScriptThreadFactory> Constellation<LTF, STF> compositor_proxy: state.compositor_proxy, devtools_chan: state.devtools_chan, bluetooth_thread: state.bluetooth_thread, - resource_thread: state.resource_thread, + resource_threads: state.resource_threads, image_cache_thread: state.image_cache_thread, font_cache_thread: state.font_cache_thread, - storage_thread: state.storage_thread, pipelines: HashMap::new(), frames: HashMap::new(), pipeline_to_frame_map: HashMap::new(), @@ -437,8 +431,7 @@ impl<LTF: LayoutThreadFactory, STF: ScriptThreadFactory> Constellation<LTF, STF> bluetooth_thread: self.bluetooth_thread.clone(), image_cache_thread: self.image_cache_thread.clone(), font_cache_thread: self.font_cache_thread.clone(), - resource_thread: self.resource_thread.clone(), - storage_thread: self.storage_thread.clone(), + resource_threads: self.resource_threads.clone(), time_profiler_chan: self.time_profiler_chan.clone(), mem_profiler_chan: self.mem_profiler_chan.clone(), window_size: initial_window_size, @@ -843,7 +836,7 @@ impl<LTF: LayoutThreadFactory, STF: ScriptThreadFactory> Constellation<LTF, STF> pipeline.exit(); } self.image_cache_thread.exit(); - if let Err(e) = self.resource_thread.send(net_traits::ControlMsg::Exit) { + if let Err(e) = self.resource_threads.send(net_traits::CoreResourceMsg::Exit) { warn!("Exit resource thread failed ({})", e); } if let Some(ref chan) = self.devtools_chan { @@ -852,7 +845,7 @@ impl<LTF: LayoutThreadFactory, STF: ScriptThreadFactory> Constellation<LTF, STF> warn!("Exit devtools failed ({})", e); } } - if let Err(e) = self.storage_thread.send(StorageThreadMsg::Exit) { + if let Err(e) = self.resource_threads.send(StorageThreadMsg::Exit) { warn!("Exit storage thread failed ({})", e); } if let Err(e) = self.bluetooth_thread.send(BluetoothMethodMsg::Exit) { diff --git a/components/gfx/font_cache_thread.rs b/components/gfx/font_cache_thread.rs index d71081d126c..9d9d65c94e9 100644 --- a/components/gfx/font_cache_thread.rs +++ b/components/gfx/font_cache_thread.rs @@ -6,7 +6,7 @@ use font_template::{FontTemplate, FontTemplateDescriptor}; use ipc_channel::ipc::{self, IpcReceiver, IpcSender}; use ipc_channel::router::ROUTER; use mime::{TopLevel, SubLevel}; -use net_traits::{AsyncResponseTarget, LoadContext, PendingAsyncLoad, ResourceThread, ResponseAction}; +use net_traits::{AsyncResponseTarget, LoadContext, PendingAsyncLoad, CoreResourceThread, ResponseAction}; use platform::font_context::FontContextHandle; use platform::font_list::SANS_SERIF_FONT_FAMILY; use platform::font_list::for_each_available_family; @@ -125,7 +125,7 @@ struct FontCache { local_families: HashMap<LowercaseString, FontTemplates>, web_families: HashMap<LowercaseString, FontTemplates>, font_context: FontContextHandle, - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, webrender_api: Option<webrender_traits::RenderApi>, webrender_fonts: HashMap<Atom, webrender_traits::FontKey>, } @@ -182,7 +182,7 @@ impl FontCache { Source::Url(ref url_source) => { let url = &url_source.url; let load = PendingAsyncLoad::new(LoadContext::Font, - self.resource_thread.clone(), + self.core_resource_thread.clone(), url.clone(), None, None, @@ -372,7 +372,7 @@ pub struct FontCacheThread { } impl FontCacheThread { - pub fn new(resource_thread: ResourceThread, + pub fn new(core_resource_thread: CoreResourceThread, webrender_api: Option<webrender_traits::RenderApi>) -> FontCacheThread { let (chan, port) = ipc::channel().unwrap(); @@ -388,7 +388,7 @@ impl FontCacheThread { local_families: HashMap::new(), web_families: HashMap::new(), font_context: FontContextHandle::new(), - resource_thread: resource_thread, + core_resource_thread: core_resource_thread, webrender_api: webrender_api, webrender_fonts: HashMap::new(), }; diff --git a/components/net/filemanager_thread.rs b/components/net/filemanager_thread.rs index 04a19a3a3d6..83695434328 100644 --- a/components/net/filemanager_thread.rs +++ b/components/net/filemanager_thread.rs @@ -18,7 +18,7 @@ pub struct FileManager { } impl FileManager { - pub fn new(recv: IpcReceiver<FileManagerThreadMsg>) -> FileManager { + fn new(recv: IpcReceiver<FileManagerThreadMsg>) -> FileManager { FileManager { receiver: recv, idmap: RefCell::new(HashMap::new()), @@ -36,7 +36,7 @@ impl FileManager { } /// Start the file manager event loop - pub fn start(&mut self) { + fn start(&mut self) { loop { match self.receiver.recv().unwrap() { FileManagerThreadMsg::SelectFile(sender) => self.select_file(sender), diff --git a/components/net/image_cache_thread.rs b/components/net/image_cache_thread.rs index 3ca281761d4..6ecf32f5730 100644 --- a/components/net/image_cache_thread.rs +++ b/components/net/image_cache_thread.rs @@ -9,7 +9,7 @@ use net_traits::image::base::{Image, ImageMetadata, load_from_memory, PixelForma use net_traits::image_cache_thread::ImageResponder; use net_traits::image_cache_thread::{ImageCacheChan, ImageCacheCommand, ImageCacheThread, ImageState}; use net_traits::image_cache_thread::{ImageCacheResult, ImageOrMetadataAvailable, ImageResponse, UsePlaceholder}; -use net_traits::{AsyncResponseTarget, ControlMsg, LoadConsumer, LoadData, ResourceThread}; +use net_traits::{AsyncResponseTarget, CoreResourceMsg, LoadConsumer, LoadData, CoreResourceThread}; use net_traits::{ResponseAction, LoadContext, NetworkError}; use std::borrow::ToOwned; use std::collections::HashMap; @@ -240,7 +240,7 @@ struct ImageCache { thread_pool: ThreadPool, // Resource thread handle - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, // Images that are loading over network, or decoding. pending_loads: AllPendingLoads, @@ -305,7 +305,7 @@ fn convert_format(format: PixelFormat) -> webrender_traits::ImageFormat { } impl ImageCache { - fn run(resource_thread: ResourceThread, + fn run(core_resource_thread: CoreResourceThread, webrender_api: Option<webrender_traits::RenderApi>, ipc_command_receiver: IpcReceiver<ImageCacheCommand>) { // Preload the placeholder image, used when images fail to load. @@ -338,7 +338,7 @@ impl ImageCache { thread_pool: ThreadPool::new(4), pending_loads: AllPendingLoads::new(), completed_loads: HashMap::new(), - resource_thread: resource_thread, + core_resource_thread: core_resource_thread, placeholder_image: placeholder_image, webrender_api: webrender_api, }; @@ -525,7 +525,7 @@ impl ImageCache { let response_target = AsyncResponseTarget { sender: action_sender, }; - let msg = ControlMsg::Load(load_data, + let msg = CoreResourceMsg::Load(load_data, LoadConsumer::Listener(response_target), None); let progress_sender = self.progress_sender.clone(); @@ -536,7 +536,7 @@ impl ImageCache { key: load_key, }).unwrap(); }); - self.resource_thread.send(msg).unwrap(); + self.core_resource_thread.send(msg).unwrap(); } CacheResult::Hit => { // Request is already on its way. @@ -611,12 +611,12 @@ impl ImageCache { } /// Create a new image cache. -pub fn new_image_cache_thread(resource_thread: ResourceThread, +pub fn new_image_cache_thread(core_resource_thread: CoreResourceThread, webrender_api: Option<webrender_traits::RenderApi>) -> ImageCacheThread { let (ipc_command_sender, ipc_command_receiver) = ipc::channel().unwrap(); spawn_named("ImageCacheThread".to_owned(), move || { - ImageCache::run(resource_thread, webrender_api, ipc_command_receiver) + ImageCache::run(core_resource_thread, webrender_api, ipc_command_receiver) }); ImageCacheThread::new(ipc_command_sender) diff --git a/components/net/lib.rs b/components/net/lib.rs index 91b3066d111..03e17955d3a 100644 --- a/components/net/lib.rs +++ b/components/net/lib.rs @@ -2,12 +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/. */ +#![feature(custom_attribute)] +#![feature(custom_derive)] #![feature(box_syntax)] #![feature(fnbox)] #![feature(fs_time)] #![feature(mpsc_select)] #![feature(plugin)] -#![feature(plugin)] #![plugin(plugins)] #![deny(unsafe_code)] diff --git a/components/net/resource_thread.rs b/components/net/resource_thread.rs index 5f3de8f6f69..7e93901a740 100644 --- a/components/net/resource_thread.rs +++ b/components/net/resource_thread.rs @@ -20,9 +20,9 @@ use ipc_channel::ipc::{self, IpcReceiver, IpcSender}; use mime_classifier::{ApacheBugFlag, MIMEClassifier, NoSniffFlag}; use net_traits::LoadContext; use net_traits::ProgressMsg::Done; -use net_traits::{AsyncResponseTarget, Metadata, ProgressMsg, ResourceThread, ResponseAction}; -use net_traits::{ControlMsg, CookieSource, LoadConsumer, LoadData, LoadResponse, ResourceId}; -use net_traits::{NetworkError, WebSocketCommunicate, WebSocketConnectData}; +use net_traits::{AsyncResponseTarget, Metadata, ProgressMsg, ResponseAction, CoreResourceThread}; +use net_traits::{CoreResourceMsg, CookieSource, LoadConsumer, LoadData, LoadResponse, ResourceId}; +use net_traits::{NetworkError, WebSocketCommunicate, WebSocketConnectData, ResourceThreads}; use profile_traits::time::ProfilerChan; use rustc_serialize::json; use rustc_serialize::{Decodable, Encodable}; @@ -36,6 +36,7 @@ use std::io::prelude::*; use std::path::Path; use std::sync::mpsc::{Receiver, Sender, channel}; use std::sync::{Arc, RwLock}; +use storage_thread::StorageThreadFactory; use url::Url; use util::opts; use util::prefs; @@ -149,15 +150,23 @@ fn start_sending_opt(start_chan: LoadConsumer, metadata: Metadata, } } -/// Create a ResourceThread -pub fn new_resource_thread(user_agent: String, - devtools_chan: Option<Sender<DevtoolsControlMsg>>, - profiler_chan: ProfilerChan) -> ResourceThread { +pub fn new_resource_threads(user_agent: String, + devtools_chan: Option<Sender<DevtoolsControlMsg>>, + profiler_chan: ProfilerChan) -> ResourceThreads { + ResourceThreads::new(new_core_resource_thread(user_agent, devtools_chan, profiler_chan), + StorageThreadFactory::new()) +} + + +/// Create a CoreResourceThread +pub fn new_core_resource_thread(user_agent: String, + devtools_chan: Option<Sender<DevtoolsControlMsg>>, + profiler_chan: ProfilerChan) -> CoreResourceThread { let hsts_preload = HstsList::from_servo_preload(); let (setup_chan, setup_port) = ipc::channel().unwrap(); let setup_chan_clone = setup_chan.clone(); spawn_named("ResourceManager".to_owned(), move || { - let resource_manager = ResourceManager::new( + let resource_manager = CoreResourceManager::new( user_agent, hsts_preload, devtools_chan, profiler_chan ); @@ -171,35 +180,35 @@ pub fn new_resource_thread(user_agent: String, } struct ResourceChannelManager { - from_client: IpcReceiver<ControlMsg>, - resource_manager: ResourceManager + from_client: IpcReceiver<CoreResourceMsg>, + resource_manager: CoreResourceManager } impl ResourceChannelManager { - fn start(&mut self, control_sender: ResourceThread) { + fn start(&mut self, control_sender: CoreResourceThread) { loop { match self.from_client.recv().unwrap() { - ControlMsg::Load(load_data, consumer, id_sender) => + CoreResourceMsg::Load(load_data, consumer, id_sender) => self.resource_manager.load(load_data, consumer, id_sender, control_sender.clone()), - ControlMsg::WebsocketConnect(connect, connect_data) => + CoreResourceMsg::WebsocketConnect(connect, connect_data) => self.resource_manager.websocket_connect(connect, connect_data), - ControlMsg::SetCookiesForUrl(request, cookie_list, source) => + CoreResourceMsg::SetCookiesForUrl(request, cookie_list, source) => self.resource_manager.set_cookies_for_url(request, cookie_list, source), - ControlMsg::GetCookiesForUrl(url, consumer, source) => { + CoreResourceMsg::GetCookiesForUrl(url, consumer, source) => { let cookie_jar = &self.resource_manager.cookie_jar; let mut cookie_jar = cookie_jar.write().unwrap(); consumer.send(cookie_jar.cookies_for_url(&url, source)).unwrap(); } - ControlMsg::Cancel(res_id) => { + CoreResourceMsg::Cancel(res_id) => { if let Some(cancel_sender) = self.resource_manager.cancel_load_map.get(&res_id) { let _ = cancel_sender.send(()); } self.resource_manager.cancel_load_map.remove(&res_id); } - ControlMsg::Synchronize(sender) => { + CoreResourceMsg::Synchronize(sender) => { let _ = sender.send(()); } - ControlMsg::Exit => { + CoreResourceMsg::Exit => { if let Some(ref profile_dir) = opts::get().profile_dir { match self.resource_manager.auth_cache.read() { Ok(auth_cache) => write_json_to_file(&*auth_cache, profile_dir, "auth_cache.json"), @@ -283,12 +292,12 @@ pub struct CancellableResource { resource_id: ResourceId, /// If we haven't initiated any cancel requests, then the loaders ask /// the listener to remove the `ResourceId` in the `HashMap` of - /// `ResourceManager` once they finish loading - resource_thread: ResourceThread, + /// `CoreResourceManager` once they finish loading + resource_thread: CoreResourceThread, } impl CancellableResource { - pub fn new(receiver: Receiver<()>, res_id: ResourceId, res_thread: ResourceThread) -> CancellableResource { + pub fn new(receiver: Receiver<()>, res_id: ResourceId, res_thread: CoreResourceThread) -> CancellableResource { CancellableResource { cancel_receiver: receiver, resource_id: res_id, @@ -333,7 +342,7 @@ impl Drop for CancellationListener { fn drop(&mut self) { if let Some(ref resource) = self.cancel_resource { // Ensure that the resource manager stops tracking this request now that it's terminated. - let _ = resource.resource_thread.send(ControlMsg::Cancel(resource.resource_id)); + let _ = resource.resource_thread.send(CoreResourceMsg::Cancel(resource.resource_id)); } } } @@ -360,7 +369,7 @@ pub struct AuthCache { pub entries: HashMap<Url, AuthCacheEntry>, } -pub struct ResourceManager { +pub struct CoreResourceManager { user_agent: String, cookie_jar: Arc<RwLock<CookieStorage>>, auth_cache: Arc<RwLock<AuthCache>>, @@ -373,11 +382,11 @@ pub struct ResourceManager { next_resource_id: ResourceId, } -impl ResourceManager { +impl CoreResourceManager { pub fn new(user_agent: String, mut hsts_list: HstsList, devtools_channel: Option<Sender<DevtoolsControlMsg>>, - profiler_chan: ProfilerChan) -> ResourceManager { + profiler_chan: ProfilerChan) -> CoreResourceManager { let mut auth_cache = AuthCache::new(); let mut cookie_jar = CookieStorage::new(); if let Some(ref profile_dir) = opts::get().profile_dir { @@ -385,7 +394,7 @@ impl ResourceManager { read_json_from_file(&mut hsts_list, profile_dir, "hsts_list.json"); read_json_from_file(&mut cookie_jar, profile_dir, "cookie_jar.json"); } - ResourceManager { + CoreResourceManager { user_agent: user_agent, cookie_jar: Arc::new(RwLock::new(cookie_jar)), auth_cache: Arc::new(RwLock::new(auth_cache)), @@ -416,7 +425,7 @@ impl ResourceManager { load_data: LoadData, consumer: LoadConsumer, id_sender: Option<IpcSender<ResourceId>>, - resource_thread: ResourceThread) { + resource_thread: CoreResourceThread) { fn from_factory(factory: fn(LoadData, LoadConsumer, Arc<MIMEClassifier>, CancellationListener)) -> Box<FnBox(LoadData, diff --git a/components/net_traits/lib.rs b/components/net_traits/lib.rs index b7ffadff2bb..94b43b65694 100644 --- a/components/net_traits/lib.rs +++ b/components/net_traits/lib.rs @@ -8,7 +8,6 @@ #![feature(plugin)] #![feature(slice_patterns)] #![feature(step_by)] -#![feature(custom_attribute)] #![plugin(heapsize_plugin, serde_macros)] #![deny(unsafe_code)] @@ -29,14 +28,17 @@ extern crate util; extern crate uuid; extern crate websocket; +use heapsize::HeapSizeOf; use hyper::header::{ContentType, Headers}; use hyper::http::RawStatus; use hyper::method::Method; use hyper::mime::{Attr, Mime}; use ipc_channel::ipc::{self, IpcReceiver, IpcSender}; use msg::constellation_msg::{PipelineId, ReferrerPolicy}; +use std::io::Error as IOError; use std::sync::mpsc::Sender; use std::thread; +use storage_thread::{StorageThread, StorageThreadMsg}; use url::Url; use websocket::header; @@ -180,7 +182,59 @@ pub enum LoadConsumer { } /// Handle to a resource thread -pub type ResourceThread = IpcSender<ControlMsg>; +pub type CoreResourceThread = IpcSender<CoreResourceMsg>; + +pub type IpcSendResult = Result<(), IOError>; + +pub trait IpcSend<T> where T: serde::Serialize + serde::Deserialize { + fn send(&self, T) -> IpcSendResult; + fn sender(&self) -> IpcSender<T>; +} + +// FIXME: Originally we will construct an Arc<ResourceThread> from ResourceThread +// in script_thread to avoid some performance pitfall. Now we decide to deal with +// the "Arc" hack implicitly in future. +// See discussion: http://logs.glob.uno/?c=mozilla%23servo&s=16+May+2016&e=16+May+2016#c430412 +// See also: https://github.com/servo/servo/blob/735480/components/script/script_thread.rs#L313 +#[derive(Clone, Serialize, Deserialize)] +pub struct ResourceThreads { + core_thread: CoreResourceThread, + storage_thread: StorageThread, +} + +impl ResourceThreads { + pub fn new(c: CoreResourceThread, s: StorageThread) -> ResourceThreads { + ResourceThreads { + core_thread: c, + storage_thread: s, + } + } +} + +impl IpcSend<CoreResourceMsg> for ResourceThreads { + fn send(&self, msg: CoreResourceMsg) -> IpcSendResult { + self.core_thread.send(msg) + } + + fn sender(&self) -> IpcSender<CoreResourceMsg> { + self.core_thread.clone() + } +} + +impl IpcSend<StorageThreadMsg> for ResourceThreads { + fn send(&self, msg: StorageThreadMsg) -> IpcSendResult { + self.storage_thread.send(msg) + } + + fn sender(&self) -> IpcSender<StorageThreadMsg> { + self.storage_thread.clone() + } +} + +// Ignore the sub-fields +impl HeapSizeOf for ResourceThreads { + fn heap_size_of_children(&self) -> usize { 0 } +} #[derive(PartialEq, Copy, Clone, Deserialize, Serialize)] pub enum IncludeSubdomains { @@ -222,7 +276,7 @@ pub struct WebSocketConnectData { } #[derive(Deserialize, Serialize)] -pub enum ControlMsg { +pub enum CoreResourceMsg { /// Request the data associated with a particular URL Load(LoadData, LoadConsumer, Option<IpcSender<ResourceId>>), /// Try to make a websocket connection to a URL. @@ -243,7 +297,7 @@ pub enum ControlMsg { /// the resource thread to make a new request. The `load` method *must* be called before /// destruction or the thread will panic. pub struct PendingAsyncLoad { - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, url: Url, pipeline: Option<PipelineId>, guard: PendingLoadGuard, @@ -272,14 +326,14 @@ impl Drop for PendingLoadGuard { impl PendingAsyncLoad { pub fn new(context: LoadContext, - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, url: Url, pipeline: Option<PipelineId>, referrer_policy: Option<ReferrerPolicy>, referrer_url: Option<Url>) -> PendingAsyncLoad { PendingAsyncLoad { - resource_thread: resource_thread, + core_resource_thread: core_resource_thread, url: url, pipeline: pipeline, guard: PendingLoadGuard { loaded: false, }, @@ -294,7 +348,7 @@ impl PendingAsyncLoad { self.guard.neuter(); let load_data = LoadData::new(self.context, self.url, self.pipeline, self.referrer_policy, self.referrer_url); let consumer = LoadConsumer::Listener(listener); - self.resource_thread.send(ControlMsg::Load(load_data, consumer, None)).unwrap(); + self.core_resource_thread.send(CoreResourceMsg::Load(load_data, consumer, None)).unwrap(); } } @@ -404,13 +458,13 @@ pub enum ProgressMsg { /// Convenience function for synchronously loading a whole resource. pub fn load_whole_resource(context: LoadContext, - resource_thread: &ResourceThread, + core_resource_thread: &CoreResourceThread, url: Url, pipeline_id: Option<PipelineId>) -> Result<(Metadata, Vec<u8>), NetworkError> { let (start_chan, start_port) = ipc::channel().unwrap(); - resource_thread.send(ControlMsg::Load(LoadData::new(context, url, pipeline_id, None, None), - LoadConsumer::Channel(start_chan), None)).unwrap(); + core_resource_thread.send(CoreResourceMsg::Load(LoadData::new(context, url, pipeline_id, None, None), + LoadConsumer::Channel(start_chan), None)).unwrap(); let response = start_port.recv().unwrap(); let mut buf = vec!(); diff --git a/components/script/document_loader.rs b/components/script/document_loader.rs index cd1f806294e..7282e23c322 100644 --- a/components/script/document_loader.rs +++ b/components/script/document_loader.rs @@ -9,7 +9,7 @@ use dom::bindings::js::JS; use dom::document::Document; use msg::constellation_msg::PipelineId; use net_traits::AsyncResponseTarget; -use net_traits::{PendingAsyncLoad, ResourceThread, LoadContext}; +use net_traits::{PendingAsyncLoad, CoreResourceThread, LoadContext}; use std::sync::Arc; use std::thread; use url::Url; @@ -93,10 +93,10 @@ impl Drop for LoadBlocker { #[derive(JSTraceable, HeapSizeOf)] pub struct DocumentLoader { - /// We use an `Arc<ResourceThread>` here in order to avoid file descriptor exhaustion when there + /// We use an `Arc<CoreResourceThread>` here in order to avoid file descriptor exhaustion when there /// are lots of iframes. #[ignore_heap_size_of = "channels are hard"] - pub resource_thread: Arc<ResourceThread>, + pub resource_thread: Arc<CoreResourceThread>, pipeline: Option<PipelineId>, blocking_loads: Vec<LoadType>, events_inhibited: bool, @@ -107,9 +107,9 @@ impl DocumentLoader { DocumentLoader::new_with_thread(existing.resource_thread.clone(), None, None) } - /// We use an `Arc<ResourceThread>` here in order to avoid file descriptor exhaustion when there + /// We use an `Arc<CoreResourceThread>` here in order to avoid file descriptor exhaustion when there /// are lots of iframes. - pub fn new_with_thread(resource_thread: Arc<ResourceThread>, + pub fn new_with_thread(resource_thread: Arc<CoreResourceThread>, pipeline: Option<PipelineId>, initial_load: Option<Url>) -> DocumentLoader { diff --git a/components/script/dom/bindings/global.rs b/components/script/dom/bindings/global.rs index b48a941af01..61b948dbf35 100644 --- a/components/script/dom/bindings/global.rs +++ b/components/script/dom/bindings/global.rs @@ -19,7 +19,7 @@ use js::jsapi::{CurrentGlobalOrNull, GetGlobalForObjectCrossCompartment}; use js::jsapi::{JSContext, JSObject, JS_GetClass, MutableHandleValue}; use js::{JSCLASS_IS_DOMJSCLASS, JSCLASS_IS_GLOBAL}; use msg::constellation_msg::{PanicMsg, PipelineId}; -use net_traits::ResourceThread; +use net_traits::CoreResourceThread; use profile_traits::{mem, time}; use script_runtime::{CommonScriptMsg, ScriptChan, ScriptPort}; use script_thread::{MainThreadScriptChan, ScriptThread}; @@ -114,8 +114,8 @@ impl<'a> GlobalRef<'a> { } } - /// Get the `ResourceThread` for this global scope. - pub fn resource_thread(&self) -> ResourceThread { + /// Get the `CoreResourceThread` for this global scope. + pub fn core_resource_thread(&self) -> CoreResourceThread { match *self { GlobalRef::Window(ref window) => { let doc = window.Document(); @@ -123,7 +123,7 @@ impl<'a> GlobalRef<'a> { let loader = doc.loader(); (*loader.resource_thread).clone() } - GlobalRef::Worker(ref worker) => worker.resource_thread().clone(), + GlobalRef::Worker(ref worker) => worker.core_resource_thread().clone(), } } diff --git a/components/script/dom/dedicatedworkerglobalscope.rs b/components/script/dom/dedicatedworkerglobalscope.rs index 42b2dad043a..bd5cd63fcfb 100644 --- a/components/script/dom/dedicatedworkerglobalscope.rs +++ b/components/script/dom/dedicatedworkerglobalscope.rs @@ -224,7 +224,7 @@ impl DedicatedWorkerGlobalScope { let _stack_roots_tls = StackRootTLS::new(&roots); let (url, source) = match load_whole_resource(LoadContext::Script, - &init.resource_thread, + &init.core_resource_thread, worker_url, None) { Err(_) => { diff --git a/components/script/dom/document.rs b/components/script/dom/document.rs index f6000e28a8b..ddf23297282 100644 --- a/components/script/dom/document.rs +++ b/components/script/dom/document.rs @@ -96,11 +96,11 @@ use layout_interface::{LayoutChan, Msg, ReflowQueryType}; use msg::constellation_msg::{ALT, CONTROL, SHIFT, SUPER}; use msg::constellation_msg::{Key, KeyModifiers, KeyState}; use msg::constellation_msg::{PipelineId, ReferrerPolicy, SubpageId}; -use net_traits::ControlMsg::{GetCookiesForUrl, SetCookiesForUrl}; use net_traits::CookieSource::NonHTTP; +use net_traits::CoreResourceMsg::{GetCookiesForUrl, SetCookiesForUrl}; use net_traits::response::HttpsState; -use net_traits::{AsyncResponseTarget, PendingAsyncLoad}; -use num_traits::ToPrimitive; +use net_traits::{AsyncResponseTarget, PendingAsyncLoad, IpcSend}; +use num_traits::{ToPrimitive}; use origin::Origin; use parse::{ParserRoot, ParserRef, MutNullableParserField}; use script_thread::{MainThreadScriptMsg, Runnable}; @@ -2570,7 +2570,7 @@ impl DocumentMethods for Document { let url = self.url(); let (tx, rx) = ipc::channel().unwrap(); - let _ = self.window.resource_thread().send(GetCookiesForUrl((*url).clone(), tx, NonHTTP)); + let _ = self.window.resource_threads().send(GetCookiesForUrl((*url).clone(), tx, NonHTTP)); let cookies = rx.recv().unwrap(); Ok(cookies.map_or(DOMString::new(), DOMString::from)) } @@ -2587,7 +2587,7 @@ impl DocumentMethods for Document { let url = self.url(); let _ = self.window - .resource_thread() + .resource_threads() .send(SetCookiesForUrl((*url).clone(), String::from(cookie), NonHTTP)); Ok(()) } diff --git a/components/script/dom/storage.rs b/components/script/dom/storage.rs index 9801c701ec7..c3004a1031a 100644 --- a/components/script/dom/storage.rs +++ b/components/script/dom/storage.rs @@ -15,6 +15,7 @@ use dom::event::{Event, EventBubbles, EventCancelable}; use dom::storageevent::StorageEvent; use dom::urlhelper::UrlHelper; use ipc_channel::ipc; +use net_traits::IpcSend; use net_traits::storage_thread::{StorageThread, StorageThreadMsg, StorageType}; use script_thread::{MainThreadRunnable, ScriptThread}; use task_source::dom_manipulation::DOMManipulationTask; @@ -48,7 +49,7 @@ impl Storage { fn get_storage_thread(&self) -> StorageThread { let global_root = self.global(); let global_ref = global_root.r(); - global_ref.as_window().storage_thread() + global_ref.as_window().resource_threads().sender() } } diff --git a/components/script/dom/websocket.rs b/components/script/dom/websocket.rs index 76f311a185d..796fb6a6d5f 100644 --- a/components/script/dom/websocket.rs +++ b/components/script/dom/websocket.rs @@ -27,8 +27,8 @@ use js::jsapi::{JSAutoCompartment, RootedValue}; use js::jsapi::{JS_GetArrayBufferData, JS_NewArrayBuffer}; use js::jsval::UndefinedValue; use libc::{uint32_t, uint8_t}; -use net_traits::ControlMsg::{WebsocketConnect, SetCookiesForUrl}; use net_traits::CookieSource::HTTP; +use net_traits::CoreResourceMsg::{WebsocketConnect, SetCookiesForUrl}; use net_traits::MessageData; use net_traits::hosts::replace_hosts; use net_traits::unwrap_websocket_protocol; @@ -265,8 +265,7 @@ impl WebSocket { action_receiver: resource_action_receiver, }; - let resource_thread = global.resource_thread(); - let _ = resource_thread.send(WebsocketConnect(connect, connect_data)); + let _ = global.core_resource_thread().send(WebsocketConnect(connect, connect_data)); *ws.sender.borrow_mut() = Some(dom_action_sender); @@ -493,7 +492,7 @@ impl Runnable for ConnectionEstablishedTask { if let Some(cookies) = self.headers.get_raw("set-cookie") { for cookie in cookies.iter() { if let Ok(cookie_value) = String::from_utf8(cookie.clone()) { - let _ = ws.global().r().resource_thread().send(SetCookiesForUrl(ws.url.clone(), + let _ = ws.global().r().core_resource_thread().send(SetCookiesForUrl(ws.url.clone(), cookie_value, HTTP)); } diff --git a/components/script/dom/window.rs b/components/script/dom/window.rs index e665add7928..c9111ad15e5 100644 --- a/components/script/dom/window.rs +++ b/components/script/dom/window.rs @@ -45,10 +45,10 @@ use libc; use msg::constellation_msg::{LoadData, PanicMsg, PipelineId, SubpageId}; use msg::constellation_msg::{WindowSizeData, WindowSizeType}; use msg::webdriver_msg::{WebDriverJSError, WebDriverJSResult}; -use net_traits::ResourceThread; +use net_traits::ResourceThreads; use net_traits::bluetooth_thread::BluetoothMethodMsg; use net_traits::image_cache_thread::{ImageCacheChan, ImageCacheThread}; -use net_traits::storage_thread::{StorageThread, StorageType}; +use net_traits::storage_thread::StorageType; use num_traits::ToPrimitive; use profile_traits::mem; use profile_traits::time::{ProfilerCategory, TimerMetadata, TimerMetadataFrameType}; @@ -214,18 +214,14 @@ pub struct Window { /// The current size of the window, in pixels. window_size: Cell<Option<WindowSizeData>>, - /// Associated resource thread for use by DOM objects like XMLHttpRequest - #[ignore_heap_size_of = "channels are hard"] - resource_thread: Arc<ResourceThread>, + /// Associated resource threads for use by DOM objects like XMLHttpRequest, + /// including resource_thread, filemanager_thread and storage_thread + resource_threads: ResourceThreads, /// A handle for communicating messages to the bluetooth thread. #[ignore_heap_size_of = "channels are hard"] bluetooth_thread: IpcSender<BluetoothMethodMsg>, - /// A handle for communicating messages to the storage thread. - #[ignore_heap_size_of = "channels are hard"] - storage_thread: StorageThread, - /// A handle for communicating messages to the constellation thread. #[ignore_heap_size_of = "channels are hard"] constellation_chan: IpcSender<ConstellationMsg>, @@ -347,10 +343,6 @@ impl Window { self.bluetooth_thread.clone() } - pub fn storage_thread(&self) -> StorageThread { - self.storage_thread.clone() - } - pub fn css_error_reporter(&self) -> Box<ParseErrorReporter + Send> { self.error_reporter.clone() } @@ -1276,8 +1268,8 @@ impl Window { (*self.Document().url()).clone() } - pub fn resource_thread(&self) -> ResourceThread { - (*self.resource_thread).clone() + pub fn resource_threads(&self) -> &ResourceThreads { + &self.resource_threads } pub fn mem_profiler_chan(&self) -> &mem::ProfilerChan { @@ -1453,9 +1445,8 @@ impl Window { image_cache_chan: ImageCacheChan, compositor: IpcSender<ScriptToCompositorMsg>, image_cache_thread: ImageCacheThread, - resource_thread: Arc<ResourceThread>, + resource_threads: ResourceThreads, bluetooth_thread: IpcSender<BluetoothMethodMsg>, - storage_thread: StorageThread, mem_profiler_chan: mem::ProfilerChan, time_profiler_chan: ProfilerChan, devtools_chan: Option<IpcSender<ScriptToDevtoolsControlMsg>>, @@ -1511,9 +1502,8 @@ impl Window { parent_info: parent_info, dom_static: GlobalStaticData::new(), js_runtime: DOMRefCell::new(Some(runtime.clone())), - resource_thread: resource_thread, + resource_threads: resource_threads, bluetooth_thread: bluetooth_thread, - storage_thread: storage_thread, constellation_chan: constellation_chan, page_clip_rect: Cell::new(MAX_RECT), fragment_name: DOMRefCell::new(None), @@ -1605,3 +1595,5 @@ fn debug_reflow_events(id: PipelineId, goal: &ReflowGoal, query_type: &ReflowQue println!("{}", debug_msg); } + +no_jsmanaged_fields!(ResourceThreads); diff --git a/components/script/dom/worker.rs b/components/script/dom/worker.rs index 11dca86573d..661d397460f 100644 --- a/components/script/dom/worker.rs +++ b/components/script/dom/worker.rs @@ -72,7 +72,7 @@ impl Worker { Err(_) => return Err(Error::Syntax), }; - let resource_thread = global.resource_thread(); + let core_resource_thread = global.core_resource_thread(); let constellation_chan = global.constellation_chan().clone(); let scheduler_chan = global.scheduler_chan().clone(); @@ -100,7 +100,7 @@ impl Worker { }; let init = WorkerGlobalScopeInit { - resource_thread: resource_thread, + core_resource_thread: core_resource_thread, mem_profiler_chan: global.mem_profiler_chan().clone(), time_profiler_chan: global.time_profiler_chan().clone(), to_devtools_sender: global.devtools_chan(), diff --git a/components/script/dom/workerglobalscope.rs b/components/script/dom/workerglobalscope.rs index 8b5b2637179..ef9afd34cf7 100644 --- a/components/script/dom/workerglobalscope.rs +++ b/components/script/dom/workerglobalscope.rs @@ -22,7 +22,7 @@ use js::jsapi::{HandleValue, JSContext, JSRuntime, RootedValue}; use js::jsval::UndefinedValue; use js::rust::Runtime; use msg::constellation_msg::{PanicMsg, PipelineId}; -use net_traits::{LoadContext, ResourceThread, load_whole_resource}; +use net_traits::{LoadContext, CoreResourceThread, load_whole_resource}; use profile_traits::{mem, time}; use script_runtime::{CommonScriptMsg, ScriptChan, ScriptPort}; use script_traits::ScriptMsg as ConstellationMsg; @@ -43,7 +43,7 @@ pub enum WorkerGlobalScopeTypeId { } pub struct WorkerGlobalScopeInit { - pub resource_thread: ResourceThread, + pub core_resource_thread: CoreResourceThread, pub mem_profiler_chan: mem::ProfilerChan, pub time_profiler_chan: time::ProfilerChan, pub to_devtools_sender: Option<IpcSender<ScriptToDevtoolsControlMsg>>, @@ -66,7 +66,7 @@ pub struct WorkerGlobalScope { runtime: Runtime, next_worker_id: Cell<WorkerId>, #[ignore_heap_size_of = "Defined in std"] - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, location: MutNullableHeap<JS<WorkerLocation>>, navigator: MutNullableHeap<JS<WorkerNavigator>>, console: MutNullableHeap<JS<Console>>, @@ -118,7 +118,7 @@ impl WorkerGlobalScope { worker_url: worker_url, closing: init.closing, runtime: runtime, - resource_thread: init.resource_thread, + core_resource_thread: init.core_resource_thread, location: Default::default(), navigator: Default::default(), console: Default::default(), @@ -186,8 +186,8 @@ impl WorkerGlobalScope { self.closing.load(Ordering::SeqCst) } - pub fn resource_thread(&self) -> &ResourceThread { - &self.resource_thread + pub fn core_resource_thread(&self) -> &CoreResourceThread { + &self.core_resource_thread } pub fn get_url(&self) -> &Url { @@ -236,7 +236,7 @@ impl WorkerGlobalScopeMethods for WorkerGlobalScope { let mut rval = RootedValue::new(self.runtime.cx(), UndefinedValue()); for url in urls { - let (url, source) = match load_whole_resource(LoadContext::Script, &self.resource_thread, url, None) { + let (url, source) = match load_whole_resource(LoadContext::Script, &self.core_resource_thread, url, None) { Err(_) => return Err(Error::Network), Ok((metadata, bytes)) => { (metadata.final_url, String::from_utf8(bytes).unwrap()) diff --git a/components/script/dom/xmlhttprequest.rs b/components/script/dom/xmlhttprequest.rs index e3d14ce6e67..b72d5995b20 100644 --- a/components/script/dom/xmlhttprequest.rs +++ b/components/script/dom/xmlhttprequest.rs @@ -44,9 +44,9 @@ use ipc_channel::router::ROUTER; use js::jsapi::JS_ClearPendingException; use js::jsapi::{JSContext, JS_ParseJSON, RootedValue}; use js::jsval::{JSVal, NullValue, UndefinedValue}; -use net_traits::ControlMsg::Load; +use net_traits::CoreResourceMsg::Load; use net_traits::{AsyncResponseListener, AsyncResponseTarget, Metadata, NetworkError}; -use net_traits::{LoadConsumer, LoadContext, LoadData, ResourceCORSData, ResourceThread}; +use net_traits::{LoadConsumer, LoadContext, LoadData, ResourceCORSData, CoreResourceThread}; use network_listener::{NetworkListener, PreInvoke}; use parse::html::{ParseContext, parse_html}; use parse::xml::{self, parse_xml}; @@ -207,13 +207,13 @@ impl XMLHttpRequest { load_data: LoadData, req: CORSRequest, script_chan: Box<ScriptChan + Send>, - resource_thread: ResourceThread) { + core_resource_thread: CoreResourceThread) { struct CORSContext { xhr: Arc<Mutex<XHRContext>>, load_data: RefCell<Option<LoadData>>, req: CORSRequest, script_chan: Box<ScriptChan + Send>, - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, } impl AsyncCORSResponseListener for CORSContext { @@ -233,7 +233,7 @@ impl XMLHttpRequest { }); XMLHttpRequest::initiate_async_xhr(self.xhr.clone(), self.script_chan.clone(), - self.resource_thread.clone(), load_data); + self.core_resource_thread.clone(), load_data); } } @@ -242,7 +242,7 @@ impl XMLHttpRequest { load_data: RefCell::new(Some(load_data)), req: req.clone(), script_chan: script_chan.clone(), - resource_thread: resource_thread, + core_resource_thread: core_resource_thread, }; req.http_fetch_async(box cors_context, script_chan); @@ -250,7 +250,7 @@ impl XMLHttpRequest { fn initiate_async_xhr(context: Arc<Mutex<XHRContext>>, script_chan: Box<ScriptChan + Send>, - resource_thread: ResourceThread, + core_resource_thread: CoreResourceThread, load_data: LoadData) { impl AsyncResponseListener for XHRContext { fn headers_available(&mut self, metadata: Result<Metadata, NetworkError>) { @@ -291,7 +291,7 @@ impl XMLHttpRequest { ROUTER.add_route(action_receiver.to_opaque(), box move |message| { listener.notify(message.to().unwrap()); }); - resource_thread.send(Load(load_data, LoadConsumer::Listener(response_target), None)).unwrap(); + core_resource_thread.send(Load(load_data, LoadConsumer::Listener(response_target), None)).unwrap(); } } @@ -1318,13 +1318,13 @@ impl XMLHttpRequest { (global.networking_task_source(), None) }; - let resource_thread = global.resource_thread(); + let core_resource_thread = global.core_resource_thread(); if let Some(req) = cors_request { XMLHttpRequest::check_cors(context.clone(), load_data, req.clone(), - script_chan.clone(), resource_thread); + script_chan.clone(), core_resource_thread); } else { XMLHttpRequest::initiate_async_xhr(context.clone(), script_chan, - resource_thread, load_data); + core_resource_thread, load_data); } if let Some(script_port) = script_port { diff --git a/components/script/script_thread.rs b/components/script/script_thread.rs index 0fe4ab3ea3c..960d39cc244 100644 --- a/components/script/script_thread.rs +++ b/components/script/script_thread.rs @@ -65,8 +65,8 @@ use msg::webdriver_msg::WebDriverScriptCommand; use net_traits::LoadData as NetLoadData; use net_traits::bluetooth_thread::BluetoothMethodMsg; use net_traits::image_cache_thread::{ImageCacheChan, ImageCacheResult, ImageCacheThread}; -use net_traits::storage_thread::StorageThread; -use net_traits::{AsyncResponseTarget, ControlMsg, LoadConsumer, LoadContext, Metadata, ResourceThread}; +use net_traits::{AsyncResponseTarget, CoreResourceMsg, LoadConsumer, LoadContext, Metadata}; +use net_traits::{ResourceThreads, IpcSend}; use network_listener::NetworkListener; use parse::ParserRoot; use parse::html::{ParseContext, parse_html}; @@ -311,11 +311,9 @@ pub struct ScriptThread { image_cache_thread: ImageCacheThread, /// A handle to the resource thread. This is an `Arc` to avoid running out of file descriptors if /// there are many iframes. - resource_thread: Arc<ResourceThread>, + resource_threads: ResourceThreads, /// A handle to the bluetooth thread. bluetooth_thread: IpcSender<BluetoothMethodMsg>, - /// A handle to the storage thread. - storage_thread: StorageThread, /// The port on which the script thread receives messages (load URL, exit, etc.) port: Receiver<MainThreadScriptMsg>, @@ -557,9 +555,8 @@ impl ScriptThread { image_cache_channel: ImageCacheChan(ipc_image_cache_channel), image_cache_port: image_cache_port, - resource_thread: Arc::new(state.resource_thread), + resource_threads: state.resource_threads, bluetooth_thread: state.bluetooth_thread, - storage_thread: state.storage_thread, port: port, chan: MainThreadScriptChan(chan.clone()), @@ -1444,9 +1441,8 @@ impl ScriptThread { self.image_cache_channel.clone(), self.compositor.borrow_mut().clone(), self.image_cache_thread.clone(), - self.resource_thread.clone(), + self.resource_threads.clone(), self.bluetooth_thread.clone(), - self.storage_thread.clone(), self.mem_profiler_chan.clone(), self.time_profiler_chan.clone(), self.devtools_chan.clone(), @@ -1542,7 +1538,7 @@ impl ScriptThread { } }); - let loader = DocumentLoader::new_with_thread(self.resource_thread.clone(), + let loader = DocumentLoader::new_with_thread(Arc::new(self.resource_threads.sender()), Some(browsing_context.pipeline()), Some(incomplete.url.clone())); @@ -1899,7 +1895,7 @@ impl ScriptThread { load_data.url = Url::parse("about:blank").unwrap(); } - self.resource_thread.send(ControlMsg::Load(NetLoadData { + self.resource_threads.send(CoreResourceMsg::Load(NetLoadData { context: LoadContext::Browsing, url: load_data.url, method: load_data.method, diff --git a/components/script_traits/lib.rs b/components/script_traits/lib.rs index 47a69012bb3..14c3338dbc2 100644 --- a/components/script_traits/lib.rs +++ b/components/script_traits/lib.rs @@ -45,11 +45,10 @@ use msg::constellation_msg::{Key, KeyModifiers, KeyState, LoadData}; use msg::constellation_msg::{PanicMsg, PipelineId, PipelineNamespaceId}; use msg::constellation_msg::{SubpageId, WindowSizeData, WindowSizeType}; use msg::webdriver_msg::WebDriverScriptCommand; -use net_traits::ResourceThread; +use net_traits::ResourceThreads; use net_traits::bluetooth_thread::BluetoothMethodMsg; use net_traits::image_cache_thread::ImageCacheThread; use net_traits::response::HttpsState; -use net_traits::storage_thread::StorageThread; use profile_traits::mem; use std::any::Any; use util::ipc::OptionalOpaqueIpcSender; @@ -320,11 +319,9 @@ pub struct InitialScriptState { /// A channel to schedule timer events. pub scheduler_chan: IpcSender<TimerEventRequest>, /// A channel to the resource manager thread. - pub resource_thread: ResourceThread, + pub resource_threads: ResourceThreads, /// A channel to the bluetooth thread. pub bluetooth_thread: IpcSender<BluetoothMethodMsg>, - /// A channel to the storage thread. - pub storage_thread: StorageThread, /// A channel to the image cache thread. pub image_cache_thread: ImageCacheThread, /// A channel to the time profiler thread. diff --git a/components/servo/lib.rs b/components/servo/lib.rs index 4daac715f7c..edc362985b9 100644 --- a/components/servo/lib.rs +++ b/components/servo/lib.rs @@ -73,10 +73,9 @@ use gfx::font_cache_thread::FontCacheThread; use ipc_channel::ipc::{self, IpcSender}; use net::bluetooth_thread::BluetoothThreadFactory; use net::image_cache_thread::new_image_cache_thread; -use net::resource_thread::new_resource_thread; -use net::storage_thread::StorageThreadFactory; +use net::resource_thread::new_resource_threads; +use net_traits::IpcSend; use net_traits::bluetooth_thread::BluetoothMethodMsg; -use net_traits::storage_thread::StorageThread; use profile::mem as profile_mem; use profile::time as profile_time; use profile_traits::mem; @@ -211,14 +210,14 @@ fn create_constellation(opts: opts::Opts, supports_clipboard: bool, webrender_api_sender: Option<webrender_traits::RenderApiSender>) -> Sender<ConstellationMsg> { let bluetooth_thread: IpcSender<BluetoothMethodMsg> = BluetoothThreadFactory::new(); - let resource_thread = new_resource_thread(opts.user_agent.clone(), - devtools_chan.clone(), - time_profiler_chan.clone()); - let image_cache_thread = new_image_cache_thread(resource_thread.clone(), + + let resource_threads = new_resource_threads(opts.user_agent.clone(), + devtools_chan.clone(), + time_profiler_chan.clone()); + let image_cache_thread = new_image_cache_thread(resource_threads.sender(), webrender_api_sender.as_ref().map(|wr| wr.create_api())); - let font_cache_thread = FontCacheThread::new(resource_thread.clone(), + let font_cache_thread = FontCacheThread::new(resource_threads.sender(), webrender_api_sender.as_ref().map(|wr| wr.create_api())); - let storage_thread: StorageThread = StorageThreadFactory::new(); let initial_state = InitialConstellationState { compositor_proxy: compositor_proxy, @@ -226,8 +225,7 @@ fn create_constellation(opts: opts::Opts, bluetooth_thread: bluetooth_thread, image_cache_thread: image_cache_thread, font_cache_thread: font_cache_thread, - resource_thread: resource_thread, - storage_thread: storage_thread, + resource_threads: resource_threads, time_profiler_chan: time_profiler_chan, mem_profiler_chan: mem_profiler_chan, supports_clipboard: supports_clipboard, diff --git a/tests/unit/net/resource_thread.rs b/tests/unit/net/resource_thread.rs index 941419c3428..b4451448033 100644 --- a/tests/unit/net/resource_thread.rs +++ b/tests/unit/net/resource_thread.rs @@ -3,9 +3,9 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ use ipc_channel::ipc; -use net::resource_thread::new_resource_thread; +use net::resource_thread::new_core_resource_thread; use net_traits::hosts::{parse_hostsfile, host_replacement}; -use net_traits::{ControlMsg, LoadData, LoadConsumer, LoadContext, NetworkError, ProgressMsg}; +use net_traits::{CoreResourceMsg, LoadData, LoadConsumer, LoadContext, NetworkError, ProgressMsg}; use profile_traits::time::ProfilerChan; use std::borrow::ToOwned; use std::collections::HashMap; @@ -20,17 +20,17 @@ fn ip(s: &str) -> IpAddr { #[test] fn test_exit() { let (tx, _rx) = ipc::channel().unwrap(); - let resource_thread = new_resource_thread("".to_owned(), None, ProfilerChan(tx)); - resource_thread.send(ControlMsg::Exit).unwrap(); + let resource_thread = new_core_resource_thread("".to_owned(), None, ProfilerChan(tx)); + resource_thread.send(CoreResourceMsg::Exit).unwrap(); } #[test] fn test_bad_scheme() { let (tx, _rx) = ipc::channel().unwrap(); - let resource_thread = new_resource_thread("".to_owned(), None, ProfilerChan(tx)); + let resource_thread = new_core_resource_thread("".to_owned(), None, ProfilerChan(tx)); let (start_chan, start) = ipc::channel().unwrap(); let url = Url::parse("bogus://whatever").unwrap(); - resource_thread.send(ControlMsg::Load(LoadData::new(LoadContext::Browsing, url, None, None, None), + resource_thread.send(CoreResourceMsg::Load(LoadData::new(LoadContext::Browsing, url, None, None, None), LoadConsumer::Channel(start_chan), None)).unwrap(); let response = start.recv().unwrap(); @@ -38,7 +38,7 @@ fn test_bad_scheme() { ProgressMsg::Done(result) => { assert!(result.is_err()) } _ => panic!("bleh") } - resource_thread.send(ControlMsg::Exit).unwrap(); + resource_thread.send(CoreResourceMsg::Exit).unwrap(); } #[test] @@ -204,20 +204,20 @@ fn test_cancelled_listener() { }); let (tx, _rx) = ipc::channel().unwrap(); - let resource_thread = new_resource_thread("".to_owned(), None, ProfilerChan(tx)); + let resource_thread = new_core_resource_thread("".to_owned(), None, ProfilerChan(tx)); let (sender, receiver) = ipc::channel().unwrap(); let (id_sender, id_receiver) = ipc::channel().unwrap(); let (sync_sender, sync_receiver) = ipc::channel().unwrap(); let url = Url::parse(&format!("http://127.0.0.1:{}", port)).unwrap(); - resource_thread.send(ControlMsg::Load(LoadData::new(LoadContext::Browsing, url, None, None, None), + resource_thread.send(CoreResourceMsg::Load(LoadData::new(LoadContext::Browsing, url, None, None, None), LoadConsumer::Channel(sender), Some(id_sender))).unwrap(); // get the `ResourceId` and send a cancel message, which should stop the loading loop let res_id = id_receiver.recv().unwrap(); - resource_thread.send(ControlMsg::Cancel(res_id)).unwrap(); + resource_thread.send(CoreResourceMsg::Cancel(res_id)).unwrap(); // synchronize with the resource_thread loop, so that we don't simply send everything at once! - resource_thread.send(ControlMsg::Synchronize(sync_sender)).unwrap(); + resource_thread.send(CoreResourceMsg::Synchronize(sync_sender)).unwrap(); let _ = sync_receiver.recv(); // now, let's send the body, because the connection is still active and data would be loaded // (but, the loading has been cancelled) @@ -225,5 +225,5 @@ fn test_cancelled_listener() { let response = receiver.recv().unwrap(); assert_eq!(response.progress_port.recv().unwrap(), ProgressMsg::Done(Err(NetworkError::LoadCancelled))); - resource_thread.send(ControlMsg::Exit).unwrap(); + resource_thread.send(CoreResourceMsg::Exit).unwrap(); } |