diff options
| author | Brian Anderson <banderson@mozilla.com> | 2013-01-08 19:46:12 -0800 |
|---|---|---|
| committer | Brian Anderson <banderson@mozilla.com> | 2013-01-15 18:00:19 -0800 |
| commit | 090b247056a9dd2d4d4a32c631fe2f0ddd3e744d (patch) | |
| tree | b7b9d7ab483fa7150480f90c9a5ad69905753685 /src/libcore/task | |
| parent | 989667e545cb45265d3cb4b19500224459c3bf8c (diff) | |
| download | rust-090b247056a9dd2d4d4a32c631fe2f0ddd3e744d.tar.gz rust-090b247056a9dd2d4d4a32c631fe2f0ddd3e744d.zip | |
Spawn new tasks onto the primary scheduler by default. #3760
Diffstat (limited to 'src/libcore/task')
| -rw-r--r-- | src/libcore/task/mod.rs | 100 | ||||
| -rw-r--r-- | src/libcore/task/spawn.rs | 23 |
2 files changed, 55 insertions, 68 deletions
diff --git a/src/libcore/task/mod.rs b/src/libcore/task/mod.rs index c6b0491786d..86d38a18c50 100644 --- a/src/libcore/task/mod.rs +++ b/src/libcore/task/mod.rs @@ -52,7 +52,7 @@ use prelude::*; use ptr; use result; use task::local_data_priv::{local_get, local_set}; -use task::rt::{task_id, rust_task}; +use task::rt::{task_id, sched_id, rust_task}; use task; use util; use util::replace; @@ -62,6 +62,12 @@ pub mod local_data; pub mod rt; pub mod spawn; +/// A handle to a scheduler +#[deriving_eq] +pub enum Scheduler { + SchedulerHandle(sched_id) +} + /// A handle to a task #[deriving_eq] pub enum Task { @@ -95,7 +101,21 @@ impl TaskResult : Eq { } /// Scheduler modes +#[deriving_eq] pub enum SchedMode { + /// Run task on the default scheduler + DefaultScheduler, + /// Run task on the current scheduler + CurrentScheduler, + /// Run task on a specific scheduler + ExistingScheduler(Scheduler), + /** + * Tasks are scheduled on the main OS thread + * + * The main OS thread is the thread used to launch the runtime which, + * in most cases, is the process's initial thread as created by the OS. + */ + PlatformThread, /// All tasks run in the same OS thread SingleThreaded, /// Tasks are distributed among available CPUs @@ -104,53 +124,6 @@ pub enum SchedMode { ThreadPerTask, /// Tasks are distributed among a fixed number of OS threads ManualThreads(uint), - /** - * Tasks are scheduled on the main OS thread - * - * The main OS thread is the thread used to launch the runtime which, - * in most cases, is the process's initial thread as created by the OS. - */ - PlatformThread -} - -impl SchedMode : cmp::Eq { - pure fn eq(&self, other: &SchedMode) -> bool { - match (*self) { - SingleThreaded => { - match (*other) { - SingleThreaded => true, - _ => false - } - } - ThreadPerCore => { - match (*other) { - ThreadPerCore => true, - _ => false - } - } - ThreadPerTask => { - match (*other) { - ThreadPerTask => true, - _ => false - } - } - ManualThreads(e0a) => { - match (*other) { - ManualThreads(e0b) => e0a == e0b, - _ => false - } - } - PlatformThread => { - match (*other) { - PlatformThread => true, - _ => false - } - } - } - } - pure fn ne(&self, other: &SchedMode) -> bool { - !(*self).eq(other) - } } /** @@ -204,7 +177,7 @@ pub type TaskOpts = { linked: bool, supervised: bool, mut notify_chan: Option<Chan<TaskResult>>, - sched: Option<SchedOpts>, + sched: SchedOpts, }; /** @@ -370,7 +343,7 @@ impl TaskBuilder { linked: self.opts.linked, supervised: self.opts.supervised, mut notify_chan: move notify_chan, - sched: Some({ mode: mode, foreign_stack_size: None}) + sched: { mode: mode, foreign_stack_size: None} }, can_not_copy: None, .. self.consume() @@ -486,7 +459,10 @@ pub fn default_task_opts() -> TaskOpts { linked: true, supervised: false, mut notify_chan: None, - sched: None + sched: { + mode: DefaultScheduler, + foreign_stack_size: None + } } } @@ -539,10 +515,9 @@ pub fn spawn_with<A:Owned>(arg: A, f: fn~(v: A)) { pub fn spawn_sched(mode: SchedMode, f: fn~()) { /*! - * Creates a new scheduler and executes a task on it - * - * Tasks subsequently spawned by that task will also execute on - * the new scheduler. When there are no more tasks to execute the + * Creates a new task on a new or existing scheduler + + * When there are no more tasks to execute the * scheduler terminates. * * # Failure @@ -590,6 +565,10 @@ pub fn get_task() -> Task { TaskHandle(rt::get_task_id()) } +pub fn get_scheduler() -> Scheduler { + SchedulerHandle(rt::rust_get_sched_id()) +} + /** * Temporarily make the task unkillable * @@ -927,16 +906,19 @@ fn test_spawn_sched() { } #[test] -fn test_spawn_sched_childs_on_same_sched() { +fn test_spawn_sched_childs_on_default_sched() { let po = oldcomm::Port(); let ch = oldcomm::Chan(&po); + // Assuming tests run on the default scheduler + let default_id = rt::rust_get_sched_id(); + do spawn_sched(SingleThreaded) { let parent_sched_id = rt::rust_get_sched_id(); do spawn { let child_sched_id = rt::rust_get_sched_id(); - // This should be on the same scheduler - assert parent_sched_id == child_sched_id; + assert parent_sched_id != child_sched_id; + assert child_sched_id == default_id; oldcomm::send(ch, ()); }; }; @@ -1206,7 +1188,7 @@ fn test_spawn_thread_on_demand() { let (port2, chan2) = pipes::stream(); - do spawn() |move chan2| { + do spawn_sched(CurrentScheduler) |move chan2| { chan2.send(()); } diff --git a/src/libcore/task/spawn.rs b/src/libcore/task/spawn.rs index 1c5531303e1..e3afa7c4535 100644 --- a/src/libcore/task/spawn.rs +++ b/src/libcore/task/spawn.rs @@ -88,6 +88,7 @@ use task::rt::rust_closure; use task::rt; use task::{Failure, ManualThreads, PlatformThread, SchedOpts, SingleThreaded}; use task::{Success, TaskOpts, TaskResult, ThreadPerCore, ThreadPerTask}; +use task::{ExistingScheduler, SchedulerHandle}; use task::{default_task_opts, unkillable}; use uint; use util; @@ -525,9 +526,9 @@ pub fn spawn_raw(opts: TaskOpts, f: fn~()) { // Agh. Get move-mode items into the closure. FIXME (#2829) let (child_tg, ancestors, f) = option::swap_unwrap(child_data); // Create child task. - let new_task = match opts.sched { - None => rt::new_task(), - Some(sched_opts) => new_task_in_new_sched(sched_opts) + let new_task = match opts.sched.mode { + DefaultScheduler => rt::new_task(), + _ => new_task_in_sched(opts.sched) }; assert !new_task.is_null(); // Getting killed after here would leak the task. @@ -631,12 +632,16 @@ pub fn spawn_raw(opts: TaskOpts, f: fn~()) { } } - fn new_task_in_new_sched(opts: SchedOpts) -> *rust_task { + fn new_task_in_sched(opts: SchedOpts) -> *rust_task { if opts.foreign_stack_size != None { fail ~"foreign_stack_size scheduler option unimplemented"; } let num_threads = match opts.mode { + DefaultScheduler + | CurrentScheduler + | ExistingScheduler(*) + | PlatformThread => 0u, /* Won't be used */ SingleThreaded => 1u, ThreadPerCore => rt::rust_num_threads(), ThreadPerTask => { @@ -648,13 +653,13 @@ pub fn spawn_raw(opts: TaskOpts, f: fn~()) { } threads } - PlatformThread => 0u /* Won't be used */ }; - let sched_id = if opts.mode != PlatformThread { - rt::rust_new_sched(num_threads) - } else { - rt::rust_osmain_sched_id() + let sched_id = match opts.mode { + CurrentScheduler => rt::rust_get_sched_id(), + ExistingScheduler(SchedulerHandle(id)) => id, + PlatformThread => rt::rust_osmain_sched_id(), + _ => rt::rust_new_sched(num_threads) }; rt::rust_new_task_in_sched(sched_id) } |
