mirror of
https://github.com/servo/servo.git
synced 2025-08-04 13:10:20 +01:00
Auto merge of #6586 - pcwalton:resource-task-ipc, r=jdm
script: Make the resource task communication use IPC channels. This change makes Servo use serialized messages over IPC channels for resource loading. The goal is to make it easier to make Servo multiprocess in the future. This patch does not make Servo multiprocess now; there are many other channels that need to be changed to IPC before that can happen. It does introduce a dependency on https://github.com/serde-rs/serde and https://github.com/pcwalton/ipc-channel for the first time. At the moment, `ipc-channel` uses JSON for serialization. This is because serde does not yet have official support for bincode. When serde gains support for bincode, I'll switch to that. For now, however, the JSON encoding and decoding will constitute a significant performance regression in resource loading. To avoid having to send boxed `AsyncResponseTarget` trait objects across process boundaries, this series of commits changes `AsyncResponseTarget` to wrap a sender only. It is then the client's responsibility to spawn a thread to proxy calls from that sender to the consumer of the resource data. This only had to be done in a few places. In the future, we may want to collapse those threads into one per process to reduce overhead. (It is impossible to continue to use `AsyncResponseTarget` as a boxed trait object across processes, regardless of how much work is done on `ipc-channel`. Vtables are fundamentally incompatible with IPC across mutually untrusting processes.) In general, I was pretty pleased with how this turned out. The main changes are adding serialization functionality to various objects that `serde` does not know how to serialize natively—the most complicated being Hyper objects—and reworking `AsyncResponseTarget`. The overall structure of the code is unchanged, and other than `AsyncResponseTarget` no functionality was lost in moving to serialization and IPC. r? @jdm <!-- Reviewable:start --> [<img src="https://reviewable.io/review_button.png" height=40 alt="Review on Reviewable"/>](https://reviewable.io/reviews/servo/servo/6586) <!-- Reviewable:end -->
This commit is contained in:
commit
2eb122f394
36 changed files with 232 additions and 129 deletions
|
@ -66,10 +66,13 @@ git = "https://github.com/pcwalton/ipc-channel"
|
|||
git = "https://github.com/ecoal95/rust-offscreen-rendering-context"
|
||||
features = ["texture_surface"]
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
num = "0.1.24"
|
||||
url = "0.2.36"
|
||||
time = "0.1.17"
|
||||
libc = "0.1"
|
||||
gleam = "0.1"
|
||||
|
@ -80,3 +83,4 @@ core-graphics = "0.1"
|
|||
|
||||
[target.x86_64-apple-darwin.dependencies.core-text]
|
||||
git = "https://github.com/servo/core-text-rs"
|
||||
|
||||
|
|
|
@ -47,10 +47,13 @@ path = "../script_traits"
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
fnv = "1.0"
|
||||
url = "0.2.36"
|
||||
time = "0.1.12"
|
||||
bitflags = "0.3"
|
||||
rustc-serialize = "0.3"
|
||||
|
|
|
@ -62,11 +62,14 @@ features = [ "serde-serialization" ]
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
encoding = "0.2"
|
||||
fnv = "1.0"
|
||||
url = "0.2.36"
|
||||
bitflags = "0.3"
|
||||
rustc-serialize = "0.3"
|
||||
libc = "0.1"
|
||||
|
|
|
@ -28,8 +28,11 @@ path = "../util"
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
url = "0.2.36"
|
||||
euclid = "0.1"
|
||||
serde = "0.4"
|
||||
serde_macros = "0.4"
|
||||
|
|
|
@ -27,9 +27,12 @@ features = [ "serde-serialization" ]
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
url = "0.2.36"
|
||||
time = "0.1.17"
|
||||
openssl="0.6.1"
|
||||
rustc-serialize = "0.3"
|
||||
|
@ -39,3 +42,4 @@ regex_macros = "0.1.8"
|
|||
flate2 = "0.2.0"
|
||||
uuid = "0.1.16"
|
||||
euclid = "0.1"
|
||||
|
||||
|
|
|
@ -39,7 +39,8 @@ pub fn factory(mut load_data: LoadData, start_chan: LoadConsumer, classifier: Ar
|
|||
}
|
||||
_ => {
|
||||
start_sending(start_chan, Metadata::default(load_data.url))
|
||||
.send(Done(Err("Unknown about: URL.".to_string()))).unwrap();
|
||||
.send(Done(Err("Unknown about: URL.".to_string())))
|
||||
.unwrap();
|
||||
return
|
||||
}
|
||||
};
|
||||
|
|
|
@ -34,15 +34,16 @@ pub fn load(load_data: LoadData, start_chan: LoadConsumer) {
|
|||
_ => panic!("Expected a non-relative scheme URL.")
|
||||
};
|
||||
match url.query {
|
||||
Some(query) => {
|
||||
Some(ref query) => {
|
||||
scheme_data.push_str("?");
|
||||
scheme_data.push_str(&query);
|
||||
scheme_data.push_str(query);
|
||||
},
|
||||
None => ()
|
||||
}
|
||||
let parts: Vec<&str> = scheme_data.splitn(2, ',').collect();
|
||||
if parts.len() != 2 {
|
||||
start_sending(start_chan, metadata).send(Done(Err("invalid data uri".to_string()))).unwrap();
|
||||
start_sending(start_chan,
|
||||
metadata).send(Done(Err("invalid data uri".to_string()))).unwrap();
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -9,6 +9,7 @@ use mime_classifier::MIMEClassifier;
|
|||
use resource_task::{start_sending_opt, start_sending_sniffed_opt};
|
||||
use hsts::{HSTSList, secure_url};
|
||||
|
||||
use ipc_channel::ipc::{self, IpcSender};
|
||||
use log;
|
||||
use std::collections::HashSet;
|
||||
use file_loader;
|
||||
|
@ -36,7 +37,7 @@ use uuid;
|
|||
use std::borrow::ToOwned;
|
||||
use std::boxed::FnBox;
|
||||
|
||||
pub fn factory(cookies_chan: Sender<ControlMsg>,
|
||||
pub fn factory(cookies_chan: IpcSender<ControlMsg>,
|
||||
devtools_chan: Option<Sender<DevtoolsControlMsg>>,
|
||||
hsts_list: Arc<Mutex<HSTSList>>)
|
||||
-> Box<FnBox(LoadData, LoadConsumer, Arc<MIMEClassifier>) + Send> {
|
||||
|
@ -86,7 +87,7 @@ fn request_must_be_secured(hsts_list: &HSTSList, url: &Url) -> bool {
|
|||
fn load(mut load_data: LoadData,
|
||||
start_chan: LoadConsumer,
|
||||
classifier: Arc<MIMEClassifier>,
|
||||
cookies_chan: Sender<ControlMsg>,
|
||||
cookies_chan: IpcSender<ControlMsg>,
|
||||
devtools_chan: Option<Sender<DevtoolsControlMsg>>,
|
||||
hsts_list: Arc<Mutex<HSTSList>>) {
|
||||
// FIXME: At the time of writing this FIXME, servo didn't have any central
|
||||
|
@ -153,6 +154,7 @@ reason: \"certificate verify failed\" }]))";
|
|||
Request::with_connector(load_data.method.clone(), url.clone(),
|
||||
&HttpsConnector::new(Openssl { context: Arc::new(context) }))
|
||||
};
|
||||
|
||||
let mut req = match req {
|
||||
Ok(req) => req,
|
||||
Err(HttpError::Io(ref io_error)) if (
|
||||
|
@ -201,8 +203,10 @@ reason: \"certificate verify failed\" }]))";
|
|||
req.headers_mut().set(accept);
|
||||
}
|
||||
|
||||
let (tx, rx) = channel();
|
||||
cookies_chan.send(ControlMsg::GetCookiesForUrl(url.clone(), tx, CookieSource::HTTP)).unwrap();
|
||||
let (tx, rx) = ipc::channel().unwrap();
|
||||
cookies_chan.send(ControlMsg::GetCookiesForUrl(url.clone(),
|
||||
tx,
|
||||
CookieSource::HTTP)).unwrap();
|
||||
if let Some(cookie_list) = rx.recv().unwrap() {
|
||||
let mut v = Vec::new();
|
||||
v.push(cookie_list.into_bytes());
|
||||
|
|
|
@ -97,20 +97,6 @@ struct ResourceLoadInfo {
|
|||
url: Url,
|
||||
}
|
||||
|
||||
struct ResourceListener {
|
||||
url: Url,
|
||||
sender: Sender<ResourceLoadInfo>,
|
||||
}
|
||||
|
||||
impl AsyncResponseTarget for ResourceListener {
|
||||
fn invoke_with_listener(&self, action: ResponseAction) {
|
||||
self.sender.send(ResourceLoadInfo {
|
||||
action: action,
|
||||
url: self.url.clone(),
|
||||
}).unwrap();
|
||||
}
|
||||
}
|
||||
|
||||
/// Implementation of the image cache
|
||||
struct ImageCache {
|
||||
// Receive commands from clients
|
||||
|
@ -330,11 +316,20 @@ impl ImageCache {
|
|||
e.insert(pending_load);
|
||||
|
||||
let load_data = LoadData::new(url.clone(), None);
|
||||
let listener = box ResourceListener {
|
||||
url: url,
|
||||
sender: self.progress_sender.clone(),
|
||||
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
||||
let response_target = AsyncResponseTarget {
|
||||
sender: action_sender,
|
||||
};
|
||||
let msg = ControlMsg::Load(load_data, LoadConsumer::Listener(listener));
|
||||
let msg = ControlMsg::Load(load_data,
|
||||
LoadConsumer::Listener(response_target));
|
||||
let progress_sender = self.progress_sender.clone();
|
||||
ROUTER.add_route(action_receiver.to_opaque(), box move |message| {
|
||||
let action: ResponseAction = message.to().unwrap();
|
||||
progress_sender.send(ResourceLoadInfo {
|
||||
action: action,
|
||||
url: url.clone(),
|
||||
}).unwrap();
|
||||
});
|
||||
self.resource_task.send(msg).unwrap();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,8 +12,8 @@ use cookie_storage::CookieStorage;
|
|||
use cookie;
|
||||
use mime_classifier::MIMEClassifier;
|
||||
|
||||
use net_traits::{ControlMsg, LoadData, LoadResponse, LoadConsumer};
|
||||
use net_traits::{Metadata, ProgressMsg, ResourceTask, AsyncResponseTarget, ResponseAction, CookieSource};
|
||||
use net_traits::{ControlMsg, LoadData, LoadResponse, LoadConsumer, CookieSource};
|
||||
use net_traits::{Metadata, ProgressMsg, ResourceTask, AsyncResponseTarget, ResponseAction};
|
||||
use net_traits::ProgressMsg::Done;
|
||||
use util::opts;
|
||||
use util::task::spawn_named;
|
||||
|
@ -24,6 +24,7 @@ use hsts::{HSTSList, HSTSEntry, preload_hsts_domains};
|
|||
use devtools_traits::{DevtoolsControlMsg};
|
||||
use hyper::header::{ContentType, Header, SetCookie, UserAgent};
|
||||
use hyper::mime::{Mime, TopLevel, SubLevel};
|
||||
use ipc_channel::ipc::{self, IpcReceiver, IpcSender};
|
||||
|
||||
use regex::Regex;
|
||||
use std::borrow::ToOwned;
|
||||
|
@ -34,7 +35,7 @@ use std::fs::File;
|
|||
use std::io::{BufReader, Read};
|
||||
use std::sync::Arc;
|
||||
use std::sync::Mutex;
|
||||
use std::sync::mpsc::{channel, Receiver, Sender};
|
||||
use std::sync::mpsc::{channel, Sender};
|
||||
|
||||
static mut HOST_TABLE: Option<*mut HashMap<String, String>> = None;
|
||||
pub static IPV4_REGEX: Regex = regex!(
|
||||
|
@ -67,8 +68,8 @@ pub fn global_init() {
|
|||
}
|
||||
|
||||
pub enum ProgressSender {
|
||||
Channel(Sender<ProgressMsg>),
|
||||
Listener(Box<AsyncResponseTarget>),
|
||||
Channel(IpcSender<ProgressMsg>),
|
||||
Listener(AsyncResponseTarget),
|
||||
}
|
||||
|
||||
impl ProgressSender {
|
||||
|
@ -124,7 +125,8 @@ pub fn start_sending_sniffed_opt(start_chan: LoadConsumer, mut metadata: Metadat
|
|||
}
|
||||
}
|
||||
|
||||
let supplied_type = metadata.content_type.map(|ContentType(Mime(toplevel, sublevel, _))| {
|
||||
let supplied_type =
|
||||
metadata.content_type.map(|ContentType(Mime(toplevel, sublevel, _))| {
|
||||
(format!("{}", toplevel), format!("{}", sublevel))
|
||||
});
|
||||
metadata.content_type = classifier.classify(nosniff, check_for_apache_bug, &supplied_type,
|
||||
|
@ -143,7 +145,7 @@ pub fn start_sending_sniffed_opt(start_chan: LoadConsumer, mut metadata: Metadat
|
|||
pub fn start_sending_opt(start_chan: LoadConsumer, metadata: Metadata) -> Result<ProgressSender, ()> {
|
||||
match start_chan {
|
||||
LoadConsumer::Channel(start_chan) => {
|
||||
let (progress_chan, progress_port) = channel();
|
||||
let (progress_chan, progress_port) = ipc::channel().unwrap();
|
||||
let result = start_chan.send(LoadResponse {
|
||||
metadata: metadata,
|
||||
progress_port: progress_port,
|
||||
|
@ -168,7 +170,7 @@ pub fn new_resource_task(user_agent: Option<String>,
|
|||
None => HSTSList::new()
|
||||
};
|
||||
|
||||
let (setup_chan, setup_port) = channel();
|
||||
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(
|
||||
|
@ -218,7 +220,7 @@ pub fn replace_hosts(mut load_data: LoadData, host_table: *mut HashMap<String, S
|
|||
}
|
||||
|
||||
struct ResourceChannelManager {
|
||||
from_client: Receiver<ControlMsg>,
|
||||
from_client: IpcReceiver<ControlMsg>,
|
||||
resource_manager: ResourceManager
|
||||
}
|
||||
|
||||
|
@ -251,8 +253,7 @@ impl ResourceChannelManager {
|
|||
pub struct ResourceManager {
|
||||
user_agent: Option<String>,
|
||||
cookie_storage: CookieStorage,
|
||||
// TODO: Can this be de-coupled?
|
||||
resource_task: Sender<ControlMsg>,
|
||||
resource_task: IpcSender<ControlMsg>,
|
||||
mime_classifier: Arc<MIMEClassifier>,
|
||||
devtools_chan: Option<Sender<DevtoolsControlMsg>>,
|
||||
hsts_list: Arc<Mutex<HSTSList>>
|
||||
|
@ -260,7 +261,7 @@ pub struct ResourceManager {
|
|||
|
||||
impl ResourceManager {
|
||||
pub fn new(user_agent: Option<String>,
|
||||
resource_task: Sender<ControlMsg>,
|
||||
resource_task: IpcSender<ControlMsg>,
|
||||
hsts_list: HSTSList,
|
||||
devtools_channel: Option<Sender<DevtoolsControlMsg>>) -> ResourceManager {
|
||||
ResourceManager {
|
||||
|
@ -274,7 +275,6 @@ impl ResourceManager {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
impl ResourceManager {
|
||||
fn set_cookies_for_url(&mut self, request: Url, cookie_list: String, source: CookieSource) {
|
||||
let header = Header::parse_header(&[cookie_list.into_bytes()]);
|
||||
|
|
|
@ -24,13 +24,13 @@ git = "https://github.com/servo/rust-stb-image"
|
|||
version = "0.6"
|
||||
features = [ "serde-serialization" ]
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2.36"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
euclid = "0.1"
|
||||
|
|
|
@ -10,8 +10,6 @@
|
|||
#![feature(vec_push_all)]
|
||||
#![plugin(serde_macros)]
|
||||
|
||||
#![plugin(serde_macros)]
|
||||
|
||||
extern crate euclid;
|
||||
extern crate hyper;
|
||||
extern crate ipc_channel;
|
||||
|
@ -28,10 +26,11 @@ use hyper::header::{ContentType, Headers};
|
|||
use hyper::http::RawStatus;
|
||||
use hyper::method::Method;
|
||||
use hyper::mime::{Mime, Attr};
|
||||
use ipc_channel::ipc::{self, IpcReceiver, IpcSender};
|
||||
use msg::constellation_msg::{PipelineId};
|
||||
use serde::{Deserializer, Serializer};
|
||||
use url::Url;
|
||||
|
||||
use std::sync::mpsc::{channel, Receiver, Sender};
|
||||
use std::thread;
|
||||
|
||||
pub mod image_cache_task;
|
||||
|
@ -46,7 +45,7 @@ pub mod image {
|
|||
pub mod base;
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
#[derive(Clone, Deserialize, Serialize)]
|
||||
pub struct LoadData {
|
||||
pub url: Url,
|
||||
pub method: Method,
|
||||
|
@ -87,6 +86,7 @@ pub trait AsyncResponseListener {
|
|||
|
||||
/// Data for passing between threads/processes to indicate a particular action to
|
||||
/// take on a provided network listener.
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub enum ResponseAction {
|
||||
/// Invoke headers_available
|
||||
HeadersAvailable(Metadata),
|
||||
|
@ -109,32 +109,41 @@ impl ResponseAction {
|
|||
|
||||
/// A target for async networking events. Commonly used to dispatch a runnable event to another
|
||||
/// thread storing the wrapped closure for later execution.
|
||||
pub trait AsyncResponseTarget {
|
||||
fn invoke_with_listener(&self, action: ResponseAction);
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub struct AsyncResponseTarget {
|
||||
pub sender: IpcSender<ResponseAction>,
|
||||
}
|
||||
|
||||
impl AsyncResponseTarget {
|
||||
pub fn invoke_with_listener(&self, action: ResponseAction) {
|
||||
self.sender.send(action).unwrap()
|
||||
}
|
||||
}
|
||||
|
||||
/// A wrapper for a network load that can either be channel or event-based.
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub enum LoadConsumer {
|
||||
Channel(Sender<LoadResponse>),
|
||||
Listener(Box<AsyncResponseTarget + Send>),
|
||||
Channel(IpcSender<LoadResponse>),
|
||||
Listener(AsyncResponseTarget),
|
||||
}
|
||||
|
||||
/// Handle to a resource task
|
||||
pub type ResourceTask = Sender<ControlMsg>;
|
||||
pub type ResourceTask = IpcSender<ControlMsg>;
|
||||
|
||||
#[derive(PartialEq, Copy, Clone)]
|
||||
#[derive(PartialEq, Copy, Clone, Deserialize, Serialize)]
|
||||
pub enum IncludeSubdomains {
|
||||
Included,
|
||||
NotIncluded
|
||||
}
|
||||
|
||||
#[derive(Deserialize, Serialize)]
|
||||
pub enum ControlMsg {
|
||||
/// Request the data associated with a particular URL
|
||||
Load(LoadData, LoadConsumer),
|
||||
/// Store a set of cookies for a given originating URL
|
||||
SetCookiesForUrl(Url, String, CookieSource),
|
||||
/// Retrieve the stored cookies for a given URL
|
||||
GetCookiesForUrl(Url, Sender<Option<String>>, CookieSource),
|
||||
GetCookiesForUrl(Url, IpcSender<Option<String>>, CookieSource),
|
||||
/// Store a domain's STS information
|
||||
SetHSTSEntryForHost(String, IncludeSubdomains, Option<u64>),
|
||||
Exit
|
||||
|
@ -180,17 +189,17 @@ impl PendingAsyncLoad {
|
|||
}
|
||||
|
||||
/// Initiate the network request associated with this pending load.
|
||||
pub fn load(mut self) -> Receiver<LoadResponse> {
|
||||
pub fn load(mut self) -> IpcReceiver<LoadResponse> {
|
||||
self.guard.neuter();
|
||||
let load_data = LoadData::new(self.url, self.pipeline);
|
||||
let (sender, receiver) = channel();
|
||||
let (sender, receiver) = ipc::channel().unwrap();
|
||||
let consumer = LoadConsumer::Channel(sender);
|
||||
self.resource_task.send(ControlMsg::Load(load_data, consumer)).unwrap();
|
||||
receiver
|
||||
}
|
||||
|
||||
/// Initiate the network request associated with this pending load, using the provided target.
|
||||
pub fn load_async(mut self, listener: Box<AsyncResponseTarget + Send>) {
|
||||
pub fn load_async(mut self, listener: AsyncResponseTarget) {
|
||||
self.guard.neuter();
|
||||
let load_data = LoadData::new(self.url, self.pipeline);
|
||||
let consumer = LoadConsumer::Listener(listener);
|
||||
|
@ -203,23 +212,24 @@ impl PendingAsyncLoad {
|
|||
///
|
||||
/// Even if loading fails immediately, we send one of these and the
|
||||
/// progress_port will provide the error.
|
||||
#[derive(Serialize, Deserialize)]
|
||||
pub struct LoadResponse {
|
||||
/// Metadata, such as from HTTP headers.
|
||||
pub metadata: Metadata,
|
||||
/// Port for reading data.
|
||||
pub progress_port: Receiver<ProgressMsg>,
|
||||
pub progress_port: IpcReceiver<ProgressMsg>,
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
#[derive(Clone, Deserialize, Serialize)]
|
||||
pub struct ResourceCORSData {
|
||||
/// CORS Preflight flag
|
||||
pub preflight: bool,
|
||||
/// Origin of CORS Request
|
||||
pub origin: Url
|
||||
pub origin: Url,
|
||||
}
|
||||
|
||||
/// Metadata about a loaded resource, such as is obtained from HTTP headers.
|
||||
#[derive(Clone)]
|
||||
#[derive(Clone, Deserialize, Serialize)]
|
||||
pub struct Metadata {
|
||||
/// Final URL after redirects.
|
||||
pub final_url: Url,
|
||||
|
@ -268,7 +278,7 @@ impl Metadata {
|
|||
}
|
||||
|
||||
/// The creator of a given cookie
|
||||
#[derive(PartialEq, Copy, Clone)]
|
||||
#[derive(PartialEq, Copy, Clone, Deserialize, Serialize)]
|
||||
pub enum CookieSource {
|
||||
/// An HTTP API
|
||||
HTTP,
|
||||
|
@ -277,7 +287,7 @@ pub enum CookieSource {
|
|||
}
|
||||
|
||||
/// Messages sent in response to a `Load` message
|
||||
#[derive(PartialEq,Debug)]
|
||||
#[derive(PartialEq, Debug, Deserialize, Serialize)]
|
||||
pub enum ProgressMsg {
|
||||
/// Binary data - there may be multiple of these
|
||||
Payload(Vec<u8>),
|
||||
|
@ -288,8 +298,9 @@ pub enum ProgressMsg {
|
|||
/// Convenience function for synchronously loading a whole resource.
|
||||
pub fn load_whole_resource(resource_task: &ResourceTask, url: Url)
|
||||
-> Result<(Metadata, Vec<u8>), String> {
|
||||
let (start_chan, start_port) = channel();
|
||||
resource_task.send(ControlMsg::Load(LoadData::new(url, None), LoadConsumer::Channel(start_chan))).unwrap();
|
||||
let (start_chan, start_port) = ipc::channel().unwrap();
|
||||
resource_task.send(ControlMsg::Load(LoadData::new(url, None),
|
||||
LoadConsumer::Channel(start_chan))).unwrap();
|
||||
let response = start_port.recv().unwrap();
|
||||
|
||||
let mut buf = vec!();
|
||||
|
@ -306,13 +317,15 @@ pub fn load_whole_resource(resource_task: &ResourceTask, url: Url)
|
|||
pub fn load_bytes_iter(pending: PendingAsyncLoad) -> (Metadata, ProgressMsgPortIterator) {
|
||||
let input_port = pending.load();
|
||||
let response = input_port.recv().unwrap();
|
||||
let iter = ProgressMsgPortIterator { progress_port: response.progress_port };
|
||||
let iter = ProgressMsgPortIterator {
|
||||
progress_port: response.progress_port
|
||||
};
|
||||
(response.metadata, iter)
|
||||
}
|
||||
|
||||
/// Iterator that reads chunks of bytes from a ProgressMsg port
|
||||
pub struct ProgressMsgPortIterator {
|
||||
progress_port: Receiver<ProgressMsg>
|
||||
progress_port: IpcReceiver<ProgressMsg>,
|
||||
}
|
||||
|
||||
impl Iterator for ProgressMsgPortIterator {
|
||||
|
@ -330,4 +343,3 @@ impl Iterator for ProgressMsgPortIterator {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -10,9 +10,12 @@ path = "lib.rs"
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
serde = "0.4"
|
||||
serde_macros = "0.4"
|
||||
time = "0.1.12"
|
||||
url = "0.2.36"
|
||||
|
||||
|
|
|
@ -76,7 +76,7 @@ rustc-serialize = "0.3"
|
|||
libc = "0.1"
|
||||
unicase = "0.1"
|
||||
num = "0.1.24"
|
||||
websocket = "0.12"
|
||||
websocket = "0.12.0"
|
||||
uuid = "0.1.16"
|
||||
smallvec = "0.1"
|
||||
html5ever = { version = "0.2.1", features = ["unstable"] }
|
||||
|
|
|
@ -11,7 +11,7 @@
|
|||
|
||||
use network_listener::{NetworkListener, PreInvoke};
|
||||
use script_task::ScriptChan;
|
||||
use net_traits::{AsyncResponseTarget, AsyncResponseListener, ResponseAction, Metadata};
|
||||
use net_traits::{AsyncResponseListener, ResponseAction, Metadata};
|
||||
|
||||
use std::ascii::AsciiExt;
|
||||
use std::borrow::ToOwned;
|
||||
|
@ -144,7 +144,7 @@ impl CORSRequest {
|
|||
let mut context = listener.context.lock();
|
||||
let context = context.as_mut().unwrap();
|
||||
*context.response.borrow_mut() = Some(response);
|
||||
listener.invoke_with_listener(ResponseAction::ResponseComplete(Ok(())));
|
||||
listener.notify(ResponseAction::ResponseComplete(Ok(())));
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -9,6 +9,7 @@ use script_task::{ScriptMsg, ScriptChan};
|
|||
use msg::constellation_msg::{PipelineId};
|
||||
use net_traits::{Metadata, load_whole_resource, ResourceTask, PendingAsyncLoad};
|
||||
use net_traits::AsyncResponseTarget;
|
||||
use std::sync::Arc;
|
||||
use url::Url;
|
||||
|
||||
#[derive(JSTraceable, PartialEq, Clone, Debug)]
|
||||
|
@ -34,7 +35,9 @@ impl LoadType {
|
|||
|
||||
#[derive(JSTraceable)]
|
||||
pub struct DocumentLoader {
|
||||
pub resource_task: ResourceTask,
|
||||
/// We use an `Arc<ResourceTask>` here in order to avoid file descriptor exhaustion when there
|
||||
/// are lots of iframes.
|
||||
pub resource_task: Arc<ResourceTask>,
|
||||
notifier_data: Option<NotifierData>,
|
||||
blocking_loads: Vec<LoadType>,
|
||||
}
|
||||
|
@ -50,7 +53,9 @@ impl DocumentLoader {
|
|||
DocumentLoader::new_with_task(existing.resource_task.clone(), None, None)
|
||||
}
|
||||
|
||||
pub fn new_with_task(resource_task: ResourceTask,
|
||||
/// We use an `Arc<ResourceTask>` here in order to avoid file descriptor exhaustion when there
|
||||
/// are lots of iframes.
|
||||
pub fn new_with_task(resource_task: Arc<ResourceTask>,
|
||||
data: Option<NotifierData>,
|
||||
initial_load: Option<Url>,)
|
||||
-> DocumentLoader {
|
||||
|
@ -69,11 +74,11 @@ impl DocumentLoader {
|
|||
let url = load.url().clone();
|
||||
self.blocking_loads.push(load);
|
||||
let pipeline = self.notifier_data.as_ref().map(|data| data.pipeline);
|
||||
PendingAsyncLoad::new(self.resource_task.clone(), url, pipeline)
|
||||
PendingAsyncLoad::new((*self.resource_task).clone(), url, pipeline)
|
||||
}
|
||||
|
||||
/// Create and initiate a new network request.
|
||||
pub fn load_async(&mut self, load: LoadType, listener: Box<AsyncResponseTarget + Send>) {
|
||||
pub fn load_async(&mut self, load: LoadType, listener: AsyncResponseTarget) {
|
||||
let pending = self.prepare_async_load(load);
|
||||
pending.load_async(listener)
|
||||
}
|
||||
|
|
|
@ -116,7 +116,7 @@ impl<'a> GlobalRef<'a> {
|
|||
let doc = window.Document();
|
||||
let doc = doc.r();
|
||||
let loader = doc.loader();
|
||||
loader.resource_task.clone()
|
||||
(*loader.resource_task).clone()
|
||||
}
|
||||
GlobalRef::Worker(ref worker) => worker.resource_task().clone(),
|
||||
}
|
||||
|
|
|
@ -45,7 +45,7 @@ use euclid::size::Size2D;
|
|||
use html5ever::tree_builder::QuirksMode;
|
||||
use hyper::header::Headers;
|
||||
use hyper::method::Method;
|
||||
use ipc_channel::ipc::IpcSender;
|
||||
use ipc_channel::ipc::{IpcReceiver, IpcSender};
|
||||
use js::jsapi::{JSObject, JSTracer, JSGCTraceKind, JS_CallValueTracer, JS_CallObjectTracer, GCTraceKindToAscii, Heap};
|
||||
use js::jsapi::JS_CallUnbarrieredObjectTracer;
|
||||
use js::jsval::JSVal;
|
||||
|
@ -57,6 +57,7 @@ use net_traits::image_cache_task::{ImageCacheChan, ImageCacheTask};
|
|||
use net_traits::storage_task::StorageType;
|
||||
use script_traits::ScriptControlChan;
|
||||
use script_traits::UntrustedNodeAddress;
|
||||
use serde::{Serialize, Deserialize};
|
||||
use smallvec::SmallVec;
|
||||
use msg::compositor_msg::ScriptListener;
|
||||
use msg::constellation_msg::ConstellationChan;
|
||||
|
@ -64,7 +65,6 @@ use net_traits::image::base::Image;
|
|||
use profile_traits::mem::ProfilerChan;
|
||||
use util::str::{LengthOrPercentageOrAuto};
|
||||
use selectors::parser::PseudoElement;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use std::cell::{Cell, UnsafeCell, RefCell};
|
||||
use std::collections::{HashMap, HashSet};
|
||||
use std::collections::hash_state::HashState;
|
||||
|
@ -358,7 +358,15 @@ impl JSTraceable for Box<LayoutRPC+'static> {
|
|||
|
||||
impl JSTraceable for () {
|
||||
#[inline]
|
||||
fn trace(&self, _trc: *mut JSTracer) {
|
||||
fn trace(&self, _: *mut JSTracer) {
|
||||
// Do nothing
|
||||
}
|
||||
}
|
||||
|
||||
impl<T> JSTraceable for IpcReceiver<T> where T: Deserialize + Serialize {
|
||||
#[inline]
|
||||
fn trace(&self, _: *mut JSTracer) {
|
||||
// Do nothing
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -181,8 +181,8 @@ impl DedicatedWorkerGlobalScope {
|
|||
let serialized_url = url.serialize();
|
||||
let parent_sender_for_reporter = parent_sender.clone();
|
||||
let global = DedicatedWorkerGlobalScope::new(
|
||||
url, id, mem_profiler_chan.clone(), devtools_chan, runtime.clone(), resource_task,
|
||||
constellation_chan, parent_sender, own_sender, receiver);
|
||||
url, id, mem_profiler_chan.clone(), devtools_chan, runtime.clone(),
|
||||
resource_task, constellation_chan, parent_sender, own_sender, receiver);
|
||||
// FIXME(njn): workers currently don't have a unique ID suitable for using in reporter
|
||||
// registration (#6631), so we instead use a random number and cross our fingers.
|
||||
let reporter_name = format!("worker-reporter-{}", random::<u64>());
|
||||
|
|
|
@ -83,6 +83,7 @@ use layout_interface::{ReflowGoal, ReflowQueryType};
|
|||
|
||||
use euclid::point::Point2D;
|
||||
use html5ever::tree_builder::{QuirksMode, NoQuirks, LimitedQuirks, Quirks};
|
||||
use ipc_channel::ipc;
|
||||
use layout_interface::{LayoutChan, Msg};
|
||||
use string_cache::{Atom, QualName};
|
||||
use url::Url;
|
||||
|
@ -283,7 +284,7 @@ pub trait DocumentHelpers<'a> {
|
|||
/// https://w3c.github.io/animation-timing/#dfn-invoke-callbacks-algorithm
|
||||
fn invoke_animation_callbacks(self);
|
||||
fn prepare_async_load(self, load: LoadType) -> PendingAsyncLoad;
|
||||
fn load_async(self, load: LoadType, listener: Box<AsyncResponseTarget + Send>);
|
||||
fn load_async(self, load: LoadType, listener: AsyncResponseTarget);
|
||||
fn load_sync(self, load: LoadType) -> Result<(Metadata, Vec<u8>), String>;
|
||||
fn finish_load(self, load: LoadType);
|
||||
fn set_current_parser(self, script: Option<&ServoHTMLParser>);
|
||||
|
@ -968,7 +969,7 @@ impl<'a> DocumentHelpers<'a> for &'a Document {
|
|||
loader.prepare_async_load(load)
|
||||
}
|
||||
|
||||
fn load_async(self, load: LoadType, listener: Box<AsyncResponseTarget + Send>) {
|
||||
fn load_async(self, load: LoadType, listener: AsyncResponseTarget) {
|
||||
let mut loader = self.loader.borrow_mut();
|
||||
loader.load_async(load, listener)
|
||||
}
|
||||
|
@ -1720,7 +1721,7 @@ impl<'a> DocumentMethods for &'a Document {
|
|||
return Err(Security);
|
||||
}
|
||||
let window = self.window.root();
|
||||
let (tx, rx) = channel();
|
||||
let (tx, rx) = ipc::channel().unwrap();
|
||||
let _ = window.r().resource_task().send(GetCookiesForUrl(url, tx, NonHTTP));
|
||||
let cookies = rx.recv().unwrap();
|
||||
Ok(cookies.unwrap_or("".to_owned()))
|
||||
|
|
|
@ -40,7 +40,9 @@ use js::jsval::UndefinedValue;
|
|||
use encoding::all::UTF_8;
|
||||
use encoding::label::encoding_from_whatwg_label;
|
||||
use encoding::types::{Encoding, EncodingRef, DecoderTrap};
|
||||
use net_traits::{Metadata, AsyncResponseListener};
|
||||
use ipc_channel::ipc;
|
||||
use ipc_channel::router::ROUTER;
|
||||
use net_traits::{Metadata, AsyncResponseListener, AsyncResponseTarget};
|
||||
use util::str::{DOMString, HTML_SPACE_CHARACTERS, StaticStringVec};
|
||||
use html5ever::tree_builder::NextParserState;
|
||||
use std::cell::{RefCell, Cell};
|
||||
|
@ -330,12 +332,19 @@ impl<'a> HTMLScriptElementHelpers for &'a HTMLScriptElement {
|
|||
url: url.clone(),
|
||||
}));
|
||||
|
||||
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
||||
let listener = box NetworkListener {
|
||||
context: context,
|
||||
script_chan: script_chan,
|
||||
};
|
||||
let response_target = AsyncResponseTarget {
|
||||
sender: action_sender,
|
||||
};
|
||||
ROUTER.add_route(action_receiver.to_opaque(), box move |message| {
|
||||
listener.notify(message.to().unwrap());
|
||||
});
|
||||
|
||||
doc.r().load_async(LoadType::Script(url), listener);
|
||||
doc.r().load_async(LoadType::Script(url), response_target);
|
||||
|
||||
if self.parser_inserted.get() {
|
||||
doc.r().get_current_parser().unwrap().r().suspend();
|
||||
|
|
|
@ -74,8 +74,9 @@ use std::default::Default;
|
|||
use std::ffi::CString;
|
||||
use std::mem as std_mem;
|
||||
use std::rc::Rc;
|
||||
use std::sync::mpsc::{channel, Receiver};
|
||||
use std::sync::Arc;
|
||||
use std::sync::mpsc::TryRecvError::{Empty, Disconnected};
|
||||
use std::sync::mpsc::{channel, Receiver};
|
||||
use time;
|
||||
|
||||
/// Current state of the window object
|
||||
|
@ -173,7 +174,7 @@ pub struct Window {
|
|||
window_size: Cell<Option<WindowSizeData>>,
|
||||
|
||||
/// Associated resource task for use by DOM objects like XMLHttpRequest
|
||||
resource_task: ResourceTask,
|
||||
resource_task: Arc<ResourceTask>,
|
||||
|
||||
/// A handle for communicating messages to the storage task.
|
||||
storage_task: StorageTask,
|
||||
|
@ -883,7 +884,7 @@ impl<'a> WindowHelpers for &'a Window {
|
|||
}
|
||||
|
||||
fn resource_task(self) -> ResourceTask {
|
||||
self.resource_task.clone()
|
||||
(*self.resource_task).clone()
|
||||
}
|
||||
|
||||
fn mem_profiler_chan(self) -> mem::ProfilerChan {
|
||||
|
@ -1035,7 +1036,7 @@ impl Window {
|
|||
control_chan: ScriptControlChan,
|
||||
compositor: ScriptListener,
|
||||
image_cache_task: ImageCacheTask,
|
||||
resource_task: ResourceTask,
|
||||
resource_task: Arc<ResourceTask>,
|
||||
storage_task: StorageTask,
|
||||
mem_profiler_chan: mem::ProfilerChan,
|
||||
devtools_chan: Option<IpcSender<ScriptToDevtoolsControlMsg>>,
|
||||
|
|
|
@ -46,12 +46,14 @@ use js::jsval::{JSVal, NullValue, UndefinedValue};
|
|||
|
||||
use net_traits::ControlMsg::Load;
|
||||
use net_traits::{ResourceTask, ResourceCORSData, LoadData, LoadConsumer};
|
||||
use net_traits::{AsyncResponseListener, Metadata};
|
||||
use net_traits::{AsyncResponseListener, AsyncResponseTarget, Metadata};
|
||||
use cors::{allow_cross_origin_request, CORSRequest, RequestMode, AsyncCORSResponseListener};
|
||||
use cors::CORSResponse;
|
||||
use util::str::DOMString;
|
||||
use util::task::spawn_named;
|
||||
|
||||
use ipc_channel::ipc;
|
||||
use ipc_channel::router::ROUTER;
|
||||
use std::ascii::AsciiExt;
|
||||
use std::borrow::ToOwned;
|
||||
use std::cell::{RefCell, Cell};
|
||||
|
@ -270,11 +272,18 @@ impl XMLHttpRequest {
|
|||
}
|
||||
}
|
||||
|
||||
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
||||
let listener = box NetworkListener {
|
||||
context: context,
|
||||
script_chan: script_chan,
|
||||
};
|
||||
resource_task.send(Load(load_data, LoadConsumer::Listener(listener))).unwrap();
|
||||
let response_target = AsyncResponseTarget {
|
||||
sender: action_sender,
|
||||
};
|
||||
ROUTER.add_route(action_receiver.to_opaque(), box move |message| {
|
||||
listener.notify(message.to().unwrap());
|
||||
});
|
||||
resource_task.send(Load(load_data, LoadConsumer::Listener(response_target))).unwrap();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -558,8 +567,11 @@ impl<'a> XMLHttpRequestMethods for &'a XMLHttpRequest {
|
|||
};
|
||||
let mut combined_headers = load_data.headers.clone();
|
||||
combined_headers.extend(load_data.preserved_headers.iter());
|
||||
let cors_request = CORSRequest::maybe_new(referer_url.clone(), load_data.url.clone(), mode,
|
||||
load_data.method.clone(), combined_headers);
|
||||
let cors_request = CORSRequest::maybe_new(referer_url.clone(),
|
||||
load_data.url.clone(),
|
||||
mode,
|
||||
load_data.method.clone(),
|
||||
combined_headers);
|
||||
match cors_request {
|
||||
Ok(None) => {
|
||||
let mut buf = String::new();
|
||||
|
@ -781,7 +793,8 @@ impl<'a> PrivateXMLHttpRequestHelpers for &'a XMLHttpRequest {
|
|||
};
|
||||
// XXXManishearth Clear cache entries in case of a network error
|
||||
self.process_partial_response(XHRProgress::HeadersReceived(gen_id,
|
||||
metadata.headers, metadata.status));
|
||||
metadata.headers,
|
||||
metadata.status));
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
use script_task::{ScriptChan, ScriptMsg, Runnable};
|
||||
use net_traits::{AsyncResponseTarget, AsyncResponseListener, ResponseAction};
|
||||
use net_traits::{AsyncResponseListener, ResponseAction};
|
||||
use std::sync::{Arc, Mutex};
|
||||
|
||||
/// An off-thread sink for async network event runnables. All such events are forwarded to
|
||||
|
@ -13,12 +13,14 @@ pub struct NetworkListener<T: AsyncResponseListener + PreInvoke + Send + 'static
|
|||
pub script_chan: Box<ScriptChan+Send>,
|
||||
}
|
||||
|
||||
impl<T: AsyncResponseListener + PreInvoke + Send + 'static> AsyncResponseTarget for NetworkListener<T> {
|
||||
fn invoke_with_listener(&self, action: ResponseAction) {
|
||||
self.script_chan.send(ScriptMsg::RunnableMsg(box ListenerRunnable {
|
||||
impl<T: AsyncResponseListener + PreInvoke + Send + 'static> NetworkListener<T> {
|
||||
pub fn notify(&self, action: ResponseAction) {
|
||||
if let Err(err) = self.script_chan.send(ScriptMsg::RunnableMsg(box ListenerRunnable {
|
||||
context: self.context.clone(),
|
||||
action: action,
|
||||
})).unwrap();
|
||||
})) {
|
||||
warn!("failed to deliver network data: {:?}", err);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -67,8 +67,8 @@ use msg::constellation_msg::{LoadData, PipelineId, SubpageId, MozBrowserEvent, W
|
|||
use msg::constellation_msg::{Failure, WindowSizeData, PipelineExitType};
|
||||
use msg::constellation_msg::Msg as ConstellationMsg;
|
||||
use msg::webdriver_msg::WebDriverScriptCommand;
|
||||
use net_traits::{ResourceTask, LoadConsumer, ControlMsg, Metadata};
|
||||
use net_traits::LoadData as NetLoadData;
|
||||
use net_traits::{AsyncResponseTarget, ResourceTask, LoadConsumer, ControlMsg, Metadata};
|
||||
use net_traits::image_cache_task::{ImageCacheChan, ImageCacheTask, ImageCacheResult};
|
||||
use net_traits::storage_task::StorageTask;
|
||||
use profile_traits::mem::{self, Report, Reporter, ReporterRequest, ReportKind, ReportsChan};
|
||||
|
@ -287,8 +287,9 @@ pub struct ScriptTask {
|
|||
incomplete_loads: DOMRefCell<Vec<InProgressLoad>>,
|
||||
/// A handle to the image cache task.
|
||||
image_cache_task: ImageCacheTask,
|
||||
/// A handle to the resource task.
|
||||
resource_task: ResourceTask,
|
||||
/// A handle to the resource task. This is an `Arc` to avoid running out of file descriptors if
|
||||
/// there are many iframes.
|
||||
resource_task: Arc<ResourceTask>,
|
||||
/// A handle to the storage task.
|
||||
storage_task: StorageTask,
|
||||
|
||||
|
@ -418,7 +419,7 @@ impl ScriptTaskFactory for ScriptTask {
|
|||
control_chan,
|
||||
control_port,
|
||||
constellation_chan,
|
||||
resource_task,
|
||||
Arc::new(resource_task),
|
||||
storage_task,
|
||||
image_cache_task,
|
||||
mem_profiler_chan.clone(),
|
||||
|
@ -504,7 +505,7 @@ impl ScriptTask {
|
|||
control_chan: ScriptControlChan,
|
||||
control_port: Receiver<ConstellationControlMsg>,
|
||||
constellation_chan: ConstellationChan,
|
||||
resource_task: ResourceTask,
|
||||
resource_task: Arc<ResourceTask>,
|
||||
storage_task: StorageTask,
|
||||
image_cache_task: ImageCacheTask,
|
||||
mem_profiler_chan: mem::ProfilerChan,
|
||||
|
@ -1415,7 +1416,9 @@ impl ScriptTask {
|
|||
});
|
||||
|
||||
let content_type = match metadata.content_type {
|
||||
Some(ContentType(Mime(TopLevel::Text, SubLevel::Plain, _))) => Some("text/plain".to_owned()),
|
||||
Some(ContentType(Mime(TopLevel::Text, SubLevel::Plain, _))) => {
|
||||
Some("text/plain".to_owned())
|
||||
}
|
||||
_ => None
|
||||
};
|
||||
|
||||
|
@ -1680,10 +1683,17 @@ impl ScriptTask {
|
|||
|
||||
let context = Arc::new(Mutex::new(ParserContext::new(id, subpage, script_chan.clone(),
|
||||
load_data.url.clone())));
|
||||
let (action_sender, action_receiver) = ipc::channel().unwrap();
|
||||
let listener = box NetworkListener {
|
||||
context: context,
|
||||
script_chan: script_chan.clone(),
|
||||
};
|
||||
ROUTER.add_route(action_receiver.to_opaque(), box move |message| {
|
||||
listener.notify(message.to().unwrap());
|
||||
});
|
||||
let response_target = AsyncResponseTarget {
|
||||
sender: action_sender,
|
||||
};
|
||||
|
||||
if load_data.url.scheme == "javascript" {
|
||||
load_data.url = Url::parse("about:blank").unwrap();
|
||||
|
@ -1697,7 +1707,7 @@ impl ScriptTask {
|
|||
data: load_data.data,
|
||||
cors: None,
|
||||
pipeline_id: Some(id),
|
||||
}, LoadConsumer::Listener(listener))).unwrap();
|
||||
}, LoadConsumer::Listener(response_target))).unwrap();
|
||||
|
||||
self.incomplete_loads.borrow_mut().push(incomplete);
|
||||
}
|
||||
|
|
|
@ -25,8 +25,11 @@ path = "../devtools_traits"
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
url = "0.2.36"
|
||||
libc = "0.1"
|
||||
euclid = "0.1"
|
||||
serde = "0.4"
|
||||
|
|
1
components/servo/Cargo.lock
generated
1
components/servo/Cargo.lock
generated
|
@ -910,6 +910,7 @@ version = "0.0.1"
|
|||
dependencies = [
|
||||
"cookie 0.1.21 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||
"hyper 0.6.6 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||
"ipc-channel 0.1.0 (git+https://github.com/pcwalton/ipc-channel)",
|
||||
"net 0.0.1",
|
||||
"net_traits 0.0.1",
|
||||
"time 0.1.26 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||
|
|
|
@ -100,9 +100,12 @@ optional = true
|
|||
path = "../../support/android-rs-glue/glue"
|
||||
optional = true
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
env_logger = "0.3"
|
||||
url = "0.2.36"
|
||||
time = "0.1.12"
|
||||
bitflags = "0.3"
|
||||
libc = "0.1"
|
||||
|
|
|
@ -23,13 +23,16 @@ features = ["unstable"]
|
|||
version = "0.3"
|
||||
features = [ "serde-serialization" ]
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
encoding = "0.2"
|
||||
fnv = "1.0"
|
||||
rustc-serialize = "0.3"
|
||||
matches = "0.1"
|
||||
url = "0.2.36"
|
||||
bitflags = "0.3"
|
||||
num = "0.1.24"
|
||||
lazy_static = "0.1.10"
|
||||
|
|
|
@ -28,6 +28,10 @@ features = [ "serde-serialization" ]
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
bitflags = "0.3"
|
||||
|
@ -37,7 +41,6 @@ rustc-serialize = "0.3"
|
|||
smallvec = "0.1"
|
||||
num_cpus = "0.2.2"
|
||||
num = "0.1.24"
|
||||
url = "0.2.36"
|
||||
euclid = "0.1"
|
||||
serde = "0.4"
|
||||
serde_macros = "0.4"
|
||||
|
|
|
@ -23,8 +23,11 @@ features = [ "serde-serialization" ]
|
|||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies.url]
|
||||
version = "0.2"
|
||||
features = [ "serde_serialization" ]
|
||||
|
||||
[dependencies]
|
||||
log = "0.3"
|
||||
rustc-serialize = "0.3.4"
|
||||
url = "0.2.36"
|
||||
uuid = "0.1"
|
||||
|
|
|
@ -17,6 +17,9 @@ path = "../../../components/net_traits"
|
|||
[dependencies.util]
|
||||
path = "../../../components/util"
|
||||
|
||||
[dependencies.ipc-channel]
|
||||
git = "https://github.com/pcwalton/ipc-channel"
|
||||
|
||||
[dependencies]
|
||||
cookie = "0.1"
|
||||
hyper = "0.6"
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
|
||||
extern crate hyper;
|
||||
|
||||
use ipc_channel::ipc;
|
||||
use net_traits::LoadConsumer::Channel;
|
||||
use net_traits::LoadData;
|
||||
use net_traits::ProgressMsg::{Payload, Done};
|
||||
|
@ -19,7 +20,7 @@ fn assert_parse(url: &'static str,
|
|||
use url::Url;
|
||||
use net::data_loader::load;
|
||||
|
||||
let (start_chan, start_port) = channel();
|
||||
let (start_chan, start_port) = ipc::channel().unwrap();
|
||||
load(LoadData::new(Url::parse(url).unwrap(), None), Channel(start_chan));
|
||||
|
||||
let response = start_port.recv().unwrap();
|
||||
|
|
|
@ -7,6 +7,7 @@ use net::hsts::HSTSEntry;
|
|||
use net_traits::IncludeSubdomains;
|
||||
use net::hsts::{secure_url, preload_hsts_domains};
|
||||
use net::resource_task::ResourceManager;
|
||||
use ipc_channel::ipc;
|
||||
use std::sync::mpsc::channel;
|
||||
use url::Url;
|
||||
use time;
|
||||
|
@ -17,7 +18,7 @@ fn test_add_hsts_entry_to_resource_manager_adds_an_hsts_entry() {
|
|||
entries: Vec::new()
|
||||
};
|
||||
|
||||
let (tx, _) = channel();
|
||||
let (tx, _) = ipc::channel().unwrap();
|
||||
let mut manager = ResourceManager::new(None, tx, list, None);
|
||||
|
||||
let entry = HSTSEntry::new(
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
|
||||
#![cfg_attr(test, feature(box_raw))]
|
||||
|
||||
extern crate ipc_channel;
|
||||
extern crate net;
|
||||
extern crate net_traits;
|
||||
extern crate url;
|
||||
|
|
|
@ -2,9 +2,8 @@
|
|||
* 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 net::resource_task::new_resource_task;
|
||||
use net::resource_task::parse_hostsfile;
|
||||
use net::resource_task::replace_hosts;
|
||||
use ipc_channel::ipc;
|
||||
use net::resource_task::{new_resource_task, parse_hostsfile, replace_hosts};
|
||||
use net_traits::{ControlMsg, LoadData, LoadConsumer};
|
||||
use net_traits::ProgressMsg;
|
||||
use std::borrow::ToOwned;
|
||||
|
@ -21,7 +20,7 @@ fn test_exit() {
|
|||
#[test]
|
||||
fn test_bad_scheme() {
|
||||
let resource_task = new_resource_task(None, None);
|
||||
let (start_chan, start) = channel();
|
||||
let (start_chan, start) = ipc::channel().unwrap();
|
||||
let url = Url::parse("bogus://whatever").unwrap();
|
||||
resource_task.send(ControlMsg::Load(LoadData::new(url, None), LoadConsumer::Channel(start_chan))).unwrap();
|
||||
let response = start.recv().unwrap();
|
||||
|
@ -170,7 +169,7 @@ fn test_replace_hosts() {
|
|||
|
||||
//Start the resource task and make a request to our TCP server
|
||||
let resource_task = new_resource_task(None, None);
|
||||
let (start_chan, _) = channel();
|
||||
let (start_chan, _start_port) = ipc::channel().unwrap();
|
||||
let url = Url::parse(&format!("http://foo.bar.com:{}", port)).unwrap();
|
||||
let msg = ControlMsg::Load(replace_hosts(LoadData::new(url, None), host_table),
|
||||
LoadConsumer::Channel(start_chan));
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue