From 61518580ed60bb16edcd4fb7200d0b564b5ee9e9 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 21:46:17 +0300 Subject: introduce cancelable --- crates/ra_analysis/src/lib.rs | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 46cc0722b..b1d5c4936 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -37,6 +37,11 @@ pub use ra_editor::{ RunnableKind, StructureNode, }; +#[derive(Clone, Copy, Debug)] +pub struct Cancel; + +pub type Cancelable = Result; + #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct FileId(pub u32); -- cgit v1.2.3 From c4b0d3cd56ab68f4fa23f7c1f6c76f7f6148153e Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 21:52:49 +0300 Subject: make parent module cancelable --- crates/ra_analysis/src/imp.rs | 9 +++++---- crates/ra_analysis/src/lib.rs | 11 ++++++++++- crates/ra_lsp_server/src/main_loop/handlers.rs | 2 +- 3 files changed, 16 insertions(+), 6 deletions(-) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index a67b1717a..3a135ef13 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -20,7 +20,7 @@ use crate::{ descriptors::{FnDescriptor, ModuleTreeDescriptor, Problem}, roots::{ReadonlySourceRoot, SourceRoot, WritableSourceRoot}, CrateGraph, CrateId, Diagnostic, FileId, FileResolver, FileSystemEdit, JobToken, Position, - Query, SourceChange, SourceFileEdit, + Query, SourceChange, SourceFileEdit, Cancelable, }; #[derive(Clone, Debug)] @@ -157,10 +157,10 @@ impl AnalysisImpl { } query.search(&buf, token) } - pub fn parent_module(&self, file_id: FileId) -> Vec<(FileId, FileSymbol)> { + pub fn parent_module(&self, file_id: FileId) -> Cancelable> { let root = self.root(file_id); let module_tree = root.module_tree(); - module_tree + let res = module_tree .parent_modules(file_id) .iter() .map(|link| { @@ -174,7 +174,8 @@ impl AnalysisImpl { }; (file_id, sym) }) - .collect() + .collect(); + Ok(res) } pub fn crate_for(&self, file_id: FileId) -> Vec { let module_tree = self.root(file_id).module_tree(); diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index b1d5c4936..988a45b46 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -42,6 +42,15 @@ pub struct Cancel; pub type Cancelable = Result; +impl std::fmt::Display for Cancel { + fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { + fmt.write_str("Canceled") + } +} + +impl std::error::Error for Cancel { +} + #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct FileId(pub u32); @@ -225,7 +234,7 @@ impl Analysis { pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, token: &JobToken) -> Vec<(FileId, TextRange)> { self.imp.find_all_refs(file_id, offset, token) } - pub fn parent_module(&self, file_id: FileId) -> Vec<(FileId, FileSymbol)> { + pub fn parent_module(&self, file_id: FileId) -> Cancelable> { self.imp.parent_module(file_id) } pub fn crate_for(&self, file_id: FileId) -> Vec { diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs index 639fe4553..b0b983d0c 100644 --- a/crates/ra_lsp_server/src/main_loop/handlers.rs +++ b/crates/ra_lsp_server/src/main_loop/handlers.rs @@ -238,7 +238,7 @@ pub fn handle_parent_module( ) -> Result> { let file_id = params.try_conv_with(&world)?; let mut res = Vec::new(); - for (file_id, symbol) in world.analysis().parent_module(file_id) { + for (file_id, symbol) in world.analysis().parent_module(file_id)? { let line_index = world.analysis().file_line_index(file_id); let location = to_location(file_id, symbol.node_range, &world, &line_index)?; res.push(location); -- cgit v1.2.3 From 998f2ae7627053a9363a05a1ab79359882dce39f Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:02:41 +0300 Subject: remove job tokens --- crates/ra_analysis/src/imp.rs | 16 +++---- crates/ra_analysis/src/lib.rs | 44 +++++++++--------- crates/ra_analysis/src/symbol_index.rs | 5 +-- crates/ra_lsp_server/src/main_loop/handlers.rs | 62 +++++++++++++------------- 4 files changed, 61 insertions(+), 66 deletions(-) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index 3a135ef13..4cfb681d8 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -148,14 +148,14 @@ impl AnalysisImpl { pub fn file_line_index(&self, file_id: FileId) -> Arc { self.root(file_id).lines(file_id) } - pub fn world_symbols(&self, query: Query, token: &JobToken) -> Vec<(FileId, FileSymbol)> { + pub fn world_symbols(&self, query: Query) -> Vec<(FileId, FileSymbol)> { let mut buf = Vec::new(); if query.libs { self.data.libs.iter().for_each(|it| it.symbols(&mut buf)); } else { self.data.root.symbols(&mut buf); } - query.search(&buf, token) + query.search(&buf) } pub fn parent_module(&self, file_id: FileId) -> Cancelable> { let root = self.root(file_id); @@ -205,7 +205,6 @@ impl AnalysisImpl { &self, file_id: FileId, offset: TextUnit, - token: &JobToken, ) -> Vec<(FileId, FileSymbol)> { let root = self.root(file_id); let module_tree = root.module_tree(); @@ -227,7 +226,7 @@ impl AnalysisImpl { return vec; } else { // If that fails try the index based approach. - return self.index_resolve(name_ref, token); + return self.index_resolve(name_ref); } } if let Some(name) = find_node_at_offset::(syntax, offset) { @@ -258,7 +257,7 @@ impl AnalysisImpl { vec![] } - pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, _token: &JobToken) -> Vec<(FileId, TextRange)> { + pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit) -> Vec<(FileId, TextRange)> { let root = self.root(file_id); let file = root.syntax(file_id); let syntax = file.syntax(); @@ -380,7 +379,6 @@ impl AnalysisImpl { &self, file_id: FileId, offset: TextUnit, - token: &JobToken, ) -> Option<(FnDescriptor, Option)> { let root = self.root(file_id); let file = root.syntax(file_id); @@ -391,7 +389,7 @@ impl AnalysisImpl { let name_ref = calling_node.name_ref()?; // Resolve the function's NameRef (NOTE: this isn't entirely accurate). - let file_symbols = self.index_resolve(name_ref, token); + let file_symbols = self.index_resolve(name_ref); for (_, fs) in file_symbols { if fs.kind == FN_DEF { if let Some(fn_def) = find_node_at_offset(syntax, fs.node_range.start()) { @@ -442,12 +440,12 @@ impl AnalysisImpl { None } - fn index_resolve(&self, name_ref: ast::NameRef, token: &JobToken) -> Vec<(FileId, FileSymbol)> { + fn index_resolve(&self, name_ref: ast::NameRef) -> Vec<(FileId, FileSymbol)> { let name = name_ref.text(); let mut query = Query::new(name.to_string()); query.exact(); query.limit(4); - self.world_symbols(query, token) + self.world_symbols(query) } fn resolve_module( diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 988a45b46..7e9798c29 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -219,47 +219,46 @@ impl Analysis { let file = self.imp.file_syntax(file_id); ra_editor::file_structure(&file) } - pub fn symbol_search(&self, query: Query, token: &JobToken) -> Vec<(FileId, FileSymbol)> { - self.imp.world_symbols(query, token) + pub fn symbol_search(&self, query: Query) -> Vec<(FileId, FileSymbol)> { + self.imp.world_symbols(query) } pub fn approximately_resolve_symbol( &self, file_id: FileId, - offset: TextUnit, - token: &JobToken, + offset: TextUnit ) -> Vec<(FileId, FileSymbol)> { self.imp - .approximately_resolve_symbol(file_id, offset, token) + .approximately_resolve_symbol(file_id, offset) } - pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, token: &JobToken) -> Vec<(FileId, TextRange)> { - self.imp.find_all_refs(file_id, offset, token) + pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, ) -> Vec<(FileId, TextRange)> { + self.imp.find_all_refs(file_id, offset) } pub fn parent_module(&self, file_id: FileId) -> Cancelable> { self.imp.parent_module(file_id) } - pub fn crate_for(&self, file_id: FileId) -> Vec { - self.imp.crate_for(file_id) + pub fn crate_for(&self, file_id: FileId) -> Cancelable> { + Ok(self.imp.crate_for(file_id)) } - pub fn crate_root(&self, crate_id: CrateId) -> FileId { - self.imp.crate_root(crate_id) + pub fn crate_root(&self, crate_id: CrateId) -> Cancelable { + Ok(self.imp.crate_root(crate_id)) } - pub fn runnables(&self, file_id: FileId) -> Vec { + pub fn runnables(&self, file_id: FileId) -> Cancelable> { let file = self.imp.file_syntax(file_id); - ra_editor::runnables(&file) + Ok(ra_editor::runnables(&file)) } - pub fn highlight(&self, file_id: FileId) -> Vec { + pub fn highlight(&self, file_id: FileId) -> Cancelable> { let file = self.imp.file_syntax(file_id); - ra_editor::highlight(&file) + Ok(ra_editor::highlight(&file)) } - pub fn completions(&self, file_id: FileId, offset: TextUnit) -> Option> { + pub fn completions(&self, file_id: FileId, offset: TextUnit) -> Cancelable>> { let file = self.imp.file_syntax(file_id); - ra_editor::scope_completion(&file, offset) + Ok(ra_editor::scope_completion(&file, offset)) } - pub fn assists(&self, file_id: FileId, range: TextRange) -> Vec { - self.imp.assists(file_id, range) + pub fn assists(&self, file_id: FileId, range: TextRange) -> Cancelable> { + Ok(self.imp.assists(file_id, range)) } - pub fn diagnostics(&self, file_id: FileId) -> Vec { - self.imp.diagnostics(file_id) + pub fn diagnostics(&self, file_id: FileId) -> Cancelable> { + Ok(self.imp.diagnostics(file_id)) } pub fn folding_ranges(&self, file_id: FileId) -> Vec { let file = self.imp.file_syntax(file_id); @@ -270,9 +269,8 @@ impl Analysis { &self, file_id: FileId, offset: TextUnit, - token: &JobToken, ) -> Option<(FnDescriptor, Option)> { - self.imp.resolve_callable(file_id, offset, token) + self.imp.resolve_callable(file_id, offset) } } diff --git a/crates/ra_analysis/src/symbol_index.rs b/crates/ra_analysis/src/symbol_index.rs index 51eef8170..19f9ea47d 100644 --- a/crates/ra_analysis/src/symbol_index.rs +++ b/crates/ra_analysis/src/symbol_index.rs @@ -1,4 +1,4 @@ -use crate::{FileId, JobToken, Query}; +use crate::{FileId, Query}; use fst::{self, Streamer}; use ra_editor::{file_symbols, FileSymbol}; use ra_syntax::{ @@ -59,7 +59,6 @@ impl Query { pub(crate) fn search( self, indices: &[Arc], - token: &JobToken, ) -> Vec<(FileId, FileSymbol)> { let mut op = fst::map::OpBuilder::new(); for file_symbols in indices.iter() { @@ -69,7 +68,7 @@ impl Query { let mut stream = op.union(); let mut res = Vec::new(); while let Some((_, indexed_values)) = stream.next() { - if res.len() >= self.limit || token.is_canceled() { + if res.len() >= self.limit { break; } for indexed_value in indexed_values { diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs index b0b983d0c..9e76a51c1 100644 --- a/crates/ra_lsp_server/src/main_loop/handlers.rs +++ b/crates/ra_lsp_server/src/main_loop/handlers.rs @@ -161,7 +161,7 @@ pub fn handle_document_symbol( pub fn handle_workspace_symbol( world: ServerWorld, params: req::WorkspaceSymbolParams, - token: JobToken, + _token: JobToken, ) -> Result>> { let all_symbols = params.query.contains("#"); let libs = params.query.contains("*"); @@ -181,11 +181,11 @@ pub fn handle_workspace_symbol( q.limit(128); q }; - let mut res = exec_query(&world, query, &token)?; + let mut res = exec_query(&world, query)?; if res.is_empty() && !all_symbols { let mut query = Query::new(params.query); query.limit(128); - res = exec_query(&world, query, &token)?; + res = exec_query(&world, query)?; } return Ok(Some(res)); @@ -193,10 +193,9 @@ pub fn handle_workspace_symbol( fn exec_query( world: &ServerWorld, query: Query, - token: &JobToken, ) -> Result> { let mut res = Vec::new(); - for (file_id, symbol) in world.analysis().symbol_search(query, token) { + for (file_id, symbol) in world.analysis().symbol_search(query) { let line_index = world.analysis().file_line_index(file_id); let info = SymbolInformation { name: symbol.name.to_string(), @@ -214,7 +213,7 @@ pub fn handle_workspace_symbol( pub fn handle_goto_definition( world: ServerWorld, params: req::TextDocumentPositionParams, - token: JobToken, + _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -222,7 +221,7 @@ pub fn handle_goto_definition( let mut res = Vec::new(); for (file_id, symbol) in world .analysis() - .approximately_resolve_symbol(file_id, offset, &token) + .approximately_resolve_symbol(file_id, offset) { let line_index = world.analysis().file_line_index(file_id); let location = to_location(file_id, symbol.node_range, &world, &line_index)?; @@ -255,14 +254,14 @@ pub fn handle_runnables( let line_index = world.analysis().file_line_index(file_id); let offset = params.position.map(|it| it.conv_with(&line_index)); let mut res = Vec::new(); - for runnable in world.analysis().runnables(file_id) { + for runnable in world.analysis().runnables(file_id)? { if let Some(offset) = offset { if !contains_offset_nonstrict(runnable.range, offset) { continue; } } - let args = runnable_args(&world, file_id, &runnable.kind); + let args = runnable_args(&world, file_id, &runnable.kind)?; let r = req::Runnable { range: runnable.range.conv_with(&line_index), @@ -282,9 +281,9 @@ pub fn handle_runnables( } return Ok(res); - fn runnable_args(world: &ServerWorld, file_id: FileId, kind: &RunnableKind) -> Vec { - let spec = if let Some(&crate_id) = world.analysis().crate_for(file_id).first() { - let file_id = world.analysis().crate_root(crate_id); + fn runnable_args(world: &ServerWorld, file_id: FileId, kind: &RunnableKind) -> Result> { + let spec = if let Some(&crate_id) = world.analysis().crate_for(file_id)?.first() { + let file_id = world.analysis().crate_root(crate_id)?; let path = world.path_map.get_path(file_id); world .workspaces @@ -319,7 +318,7 @@ pub fn handle_runnables( } } } - res + Ok(res) } fn spec_args(pkg_name: &str, tgt_name: &str, tgt_kind: TargetKind, buf: &mut Vec) { @@ -356,7 +355,7 @@ pub fn handle_decorations( _token: JobToken, ) -> Result> { let file_id = params.try_conv_with(&world)?; - Ok(highlight(&world, file_id)) + highlight(&world, file_id) } pub fn handle_completion( @@ -367,7 +366,7 @@ pub fn handle_completion( let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); let offset = params.position.conv_with(&line_index); - let items = match world.analysis().completions(file_id, offset) { + let items = match world.analysis().completions(file_id, offset)? { None => return Ok(None), Some(items) => items, }; @@ -427,7 +426,7 @@ pub fn handle_folding_range( pub fn handle_signature_help( world: ServerWorld, params: req::TextDocumentPositionParams, - token: JobToken, + _token: JobToken, ) -> Result> { use languageserver_types::{ParameterInformation, SignatureInformation}; @@ -436,7 +435,7 @@ pub fn handle_signature_help( let offset = params.position.conv_with(&line_index); if let Some((descriptor, active_param)) = - world.analysis().resolve_callable(file_id, offset, &token) + world.analysis().resolve_callable(file_id, offset) { let parameters: Vec = descriptor .params @@ -466,7 +465,7 @@ pub fn handle_signature_help( pub fn handle_prepare_rename( world: ServerWorld, params: req::TextDocumentPositionParams, - token: JobToken, + _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -474,7 +473,7 @@ pub fn handle_prepare_rename( // We support renaming references like handle_rename does. // In the future we may want to reject the renaming of things like keywords here too. - let refs = world.analysis().find_all_refs(file_id, offset, &token); + let refs = world.analysis().find_all_refs(file_id, offset); if refs.is_empty() { return Ok(None); } @@ -488,7 +487,7 @@ pub fn handle_prepare_rename( pub fn handle_rename( world: ServerWorld, params: RenameParams, - token: JobToken, + _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -498,7 +497,7 @@ pub fn handle_rename( return Ok(None); } - let refs = world.analysis().find_all_refs(file_id, offset, &token); + let refs = world.analysis().find_all_refs(file_id, offset); if refs.is_empty() { return Ok(None); } @@ -525,13 +524,13 @@ pub fn handle_rename( pub fn handle_references( world: ServerWorld, params: req::ReferenceParams, - token: JobToken, + _token: JobToken, ) -> Result>> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); let offset = params.position.conv_with(&line_index); - let refs = world.analysis().find_all_refs(file_id, offset, &token); + let refs = world.analysis().find_all_refs(file_id, offset); Ok(Some(refs.into_iter() .filter_map(|r| to_location(r.0, r.1, &world, &line_index).ok()) @@ -547,10 +546,10 @@ pub fn handle_code_action( let line_index = world.analysis().file_line_index(file_id); let range = params.range.conv_with(&line_index); - let assists = world.analysis().assists(file_id, range).into_iter(); + let assists = world.analysis().assists(file_id, range)?.into_iter(); let fixes = world .analysis() - .diagnostics(file_id) + .diagnostics(file_id)? .into_iter() .filter_map(|d| Some((d.range, d.fix?))) .filter(|(range, _fix)| contains_offset_nonstrict(*range, range.start())) @@ -579,7 +578,7 @@ pub fn publish_diagnostics( let line_index = world.analysis().file_line_index(file_id); let diagnostics = world .analysis() - .diagnostics(file_id) + .diagnostics(file_id)? .into_iter() .map(|d| Diagnostic { range: d.range.conv_with(&line_index), @@ -600,19 +599,20 @@ pub fn publish_decorations( let uri = world.file_id_to_uri(file_id)?; Ok(req::PublishDecorationsParams { uri, - decorations: highlight(&world, file_id), + decorations: highlight(&world, file_id)?, }) } -fn highlight(world: &ServerWorld, file_id: FileId) -> Vec { +fn highlight(world: &ServerWorld, file_id: FileId) -> Result> { let line_index = world.analysis().file_line_index(file_id); - world + let res = world .analysis() - .highlight(file_id) + .highlight(file_id)? .into_iter() .map(|h| Decoration { range: h.range.conv_with(&line_index), tag: h.tag, }) - .collect() + .collect(); + Ok(res) } -- cgit v1.2.3 From 9fb41716de095fa365eecedab3427af7b5001644 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:09:12 +0300 Subject: make more things cancelable --- crates/ra_analysis/src/imp.rs | 2 +- crates/ra_analysis/src/lib.rs | 27 +++++++++++++------------- crates/ra_lsp_server/src/main_loop/handlers.rs | 12 ++++++------ 3 files changed, 20 insertions(+), 21 deletions(-) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index 4cfb681d8..d60fb8278 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -19,7 +19,7 @@ use rustc_hash::FxHashSet; use crate::{ descriptors::{FnDescriptor, ModuleTreeDescriptor, Problem}, roots::{ReadonlySourceRoot, SourceRoot, WritableSourceRoot}, - CrateGraph, CrateId, Diagnostic, FileId, FileResolver, FileSystemEdit, JobToken, Position, + CrateGraph, CrateId, Diagnostic, FileId, FileResolver, FileSystemEdit, Position, Query, SourceChange, SourceFileEdit, Cancelable, }; diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 7e9798c29..8595d7e03 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -219,19 +219,23 @@ impl Analysis { let file = self.imp.file_syntax(file_id); ra_editor::file_structure(&file) } - pub fn symbol_search(&self, query: Query) -> Vec<(FileId, FileSymbol)> { - self.imp.world_symbols(query) + pub fn folding_ranges(&self, file_id: FileId) -> Vec { + let file = self.imp.file_syntax(file_id); + ra_editor::folding_ranges(&file) + } + pub fn symbol_search(&self, query: Query) -> Cancelable> { + Ok(self.imp.world_symbols(query)) } pub fn approximately_resolve_symbol( &self, file_id: FileId, offset: TextUnit - ) -> Vec<(FileId, FileSymbol)> { - self.imp - .approximately_resolve_symbol(file_id, offset) + ) -> Cancelable> { + Ok(self.imp + .approximately_resolve_symbol(file_id, offset)) } - pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, ) -> Vec<(FileId, TextRange)> { - self.imp.find_all_refs(file_id, offset) + pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, ) -> Cancelable> { + Ok(self.imp.find_all_refs(file_id, offset)) } pub fn parent_module(&self, file_id: FileId) -> Cancelable> { self.imp.parent_module(file_id) @@ -260,17 +264,12 @@ impl Analysis { pub fn diagnostics(&self, file_id: FileId) -> Cancelable> { Ok(self.imp.diagnostics(file_id)) } - pub fn folding_ranges(&self, file_id: FileId) -> Vec { - let file = self.imp.file_syntax(file_id); - ra_editor::folding_ranges(&file) - } - pub fn resolve_callable( &self, file_id: FileId, offset: TextUnit, - ) -> Option<(FnDescriptor, Option)> { - self.imp.resolve_callable(file_id, offset) + ) -> Cancelable)>> { + Ok(self.imp.resolve_callable(file_id, offset)) } } diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs index 9e76a51c1..78a8ccfc5 100644 --- a/crates/ra_lsp_server/src/main_loop/handlers.rs +++ b/crates/ra_lsp_server/src/main_loop/handlers.rs @@ -195,7 +195,7 @@ pub fn handle_workspace_symbol( query: Query, ) -> Result> { let mut res = Vec::new(); - for (file_id, symbol) in world.analysis().symbol_search(query) { + for (file_id, symbol) in world.analysis().symbol_search(query)? { let line_index = world.analysis().file_line_index(file_id); let info = SymbolInformation { name: symbol.name.to_string(), @@ -221,7 +221,7 @@ pub fn handle_goto_definition( let mut res = Vec::new(); for (file_id, symbol) in world .analysis() - .approximately_resolve_symbol(file_id, offset) + .approximately_resolve_symbol(file_id, offset)? { let line_index = world.analysis().file_line_index(file_id); let location = to_location(file_id, symbol.node_range, &world, &line_index)?; @@ -435,7 +435,7 @@ pub fn handle_signature_help( let offset = params.position.conv_with(&line_index); if let Some((descriptor, active_param)) = - world.analysis().resolve_callable(file_id, offset) + world.analysis().resolve_callable(file_id, offset)? { let parameters: Vec = descriptor .params @@ -473,7 +473,7 @@ pub fn handle_prepare_rename( // We support renaming references like handle_rename does. // In the future we may want to reject the renaming of things like keywords here too. - let refs = world.analysis().find_all_refs(file_id, offset); + let refs = world.analysis().find_all_refs(file_id, offset)?; if refs.is_empty() { return Ok(None); } @@ -497,7 +497,7 @@ pub fn handle_rename( return Ok(None); } - let refs = world.analysis().find_all_refs(file_id, offset); + let refs = world.analysis().find_all_refs(file_id, offset)?; if refs.is_empty() { return Ok(None); } @@ -530,7 +530,7 @@ pub fn handle_references( let line_index = world.analysis().file_line_index(file_id); let offset = params.position.conv_with(&line_index); - let refs = world.analysis().find_all_refs(file_id, offset); + let refs = world.analysis().find_all_refs(file_id, offset)?; Ok(Some(refs.into_iter() .filter_map(|r| to_location(r.0, r.1, &world, &line_index).ok()) -- cgit v1.2.3 From e74bf6e56e45a26002ef2a77fb3ac27f523277fb Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:15:03 +0300 Subject: mark module queries as cacelable --- crates/ra_analysis/src/imp.rs | 26 +++++++++++++------------- crates/ra_analysis/src/lib.rs | 10 +++++----- crates/ra_analysis/src/module_map.rs | 15 ++++++++------- crates/ra_analysis/src/roots.rs | 9 +++++---- 4 files changed, 31 insertions(+), 29 deletions(-) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index d60fb8278..df5aacb2d 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -159,7 +159,7 @@ impl AnalysisImpl { } pub fn parent_module(&self, file_id: FileId) -> Cancelable> { let root = self.root(file_id); - let module_tree = root.module_tree(); + let module_tree = root.module_tree()?; let res = module_tree .parent_modules(file_id) .iter() @@ -177,8 +177,8 @@ impl AnalysisImpl { .collect(); Ok(res) } - pub fn crate_for(&self, file_id: FileId) -> Vec { - let module_tree = self.root(file_id).module_tree(); + pub fn crate_for(&self, file_id: FileId) -> Cancelable> { + let module_tree = self.root(file_id).module_tree()?; let crate_graph = &self.data.crate_graph; let mut res = Vec::new(); let mut work = VecDeque::new(); @@ -196,7 +196,7 @@ impl AnalysisImpl { .filter(|&id| visited.insert(id)); work.extend(parents); } - res + Ok(res) } pub fn crate_root(&self, crate_id: CrateId) -> FileId { self.data.crate_graph.crate_roots[&crate_id] @@ -205,9 +205,9 @@ impl AnalysisImpl { &self, file_id: FileId, offset: TextUnit, - ) -> Vec<(FileId, FileSymbol)> { + ) -> Cancelable> { let root = self.root(file_id); - let module_tree = root.module_tree(); + let module_tree = root.module_tree()?; let file = root.syntax(file_id); let syntax = file.syntax(); if let Some(name_ref) = find_node_at_offset::(syntax, offset) { @@ -223,10 +223,10 @@ impl AnalysisImpl { }, )); - return vec; + return Ok(vec); } else { // If that fails try the index based approach. - return self.index_resolve(name_ref); + return Ok(self.index_resolve(name_ref)); } } if let Some(name) = find_node_at_offset::(syntax, offset) { @@ -250,11 +250,11 @@ impl AnalysisImpl { }) .collect(); - return res; + return Ok(res); } } } - vec![] + Ok(vec![]) } pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit) -> Vec<(FileId, TextRange)> { @@ -289,9 +289,9 @@ impl AnalysisImpl { ret } - pub fn diagnostics(&self, file_id: FileId) -> Vec { + pub fn diagnostics(&self, file_id: FileId) -> Cancelable> { let root = self.root(file_id); - let module_tree = root.module_tree(); + let module_tree = root.module_tree()?; let syntax = root.syntax(file_id); let mut res = ra_editor::diagnostics(&syntax) @@ -346,7 +346,7 @@ impl AnalysisImpl { }; res.push(diag) } - res + Ok(res) } pub fn assists(&self, file_id: FileId, range: TextRange) -> Vec { diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 8595d7e03..6ce32894a 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -37,7 +37,7 @@ pub use ra_editor::{ RunnableKind, StructureNode, }; -#[derive(Clone, Copy, Debug)] +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord)] pub struct Cancel; pub type Cancelable = Result; @@ -231,8 +231,8 @@ impl Analysis { file_id: FileId, offset: TextUnit ) -> Cancelable> { - Ok(self.imp - .approximately_resolve_symbol(file_id, offset)) + self.imp + .approximately_resolve_symbol(file_id, offset) } pub fn find_all_refs(&self, file_id: FileId, offset: TextUnit, ) -> Cancelable> { Ok(self.imp.find_all_refs(file_id, offset)) @@ -241,7 +241,7 @@ impl Analysis { self.imp.parent_module(file_id) } pub fn crate_for(&self, file_id: FileId) -> Cancelable> { - Ok(self.imp.crate_for(file_id)) + self.imp.crate_for(file_id) } pub fn crate_root(&self, crate_id: CrateId) -> Cancelable { Ok(self.imp.crate_root(crate_id)) @@ -262,7 +262,7 @@ impl Analysis { Ok(self.imp.assists(file_id, range)) } pub fn diagnostics(&self, file_id: FileId) -> Cancelable> { - Ok(self.imp.diagnostics(file_id)) + self.imp.diagnostics(file_id) } pub fn resolve_callable( &self, diff --git a/crates/ra_analysis/src/module_map.rs b/crates/ra_analysis/src/module_map.rs index b15432498..0c413becd 100644 --- a/crates/ra_analysis/src/module_map.rs +++ b/crates/ra_analysis/src/module_map.rs @@ -1,4 +1,5 @@ use crate::{ + Cancelable, db::SyntaxDatabase, descriptors::{ModuleDescriptor, ModuleTreeDescriptor}, FileId, @@ -8,30 +9,30 @@ use std::sync::Arc; salsa::query_group! { pub(crate) trait ModulesDatabase: SyntaxDatabase { - fn module_tree() -> Arc { + fn module_tree() -> Cancelable> { type ModuleTreeQuery; } - fn module_descriptor(file_id: FileId) -> Arc { + fn module_descriptor(file_id: FileId) -> Cancelable> { type ModuleDescriptorQuery; } } } -fn module_descriptor(db: &impl ModulesDatabase, file_id: FileId) -> Arc { +fn module_descriptor(db: &impl ModulesDatabase, file_id: FileId) -> Cancelable> { let file = db.file_syntax(file_id); - Arc::new(ModuleDescriptor::new(file.ast())) + Ok(Arc::new(ModuleDescriptor::new(file.ast()))) } -fn module_tree(db: &impl ModulesDatabase) -> Arc { +fn module_tree(db: &impl ModulesDatabase) -> Cancelable> { let file_set = db.file_set(); let mut files = Vec::new(); for &file_id in file_set.files.iter() { - let module_descr = db.module_descriptor(file_id); + let module_descr = db.module_descriptor(file_id)?; files.push((file_id, module_descr)); } let res = ModuleTreeDescriptor::new( files.iter().map(|(file_id, descr)| (*file_id, &**descr)), &file_set.resolver, ); - Arc::new(res) + Ok(Arc::new(res)) } diff --git a/crates/ra_analysis/src/roots.rs b/crates/ra_analysis/src/roots.rs index 19c84df65..e950a75e2 100644 --- a/crates/ra_analysis/src/roots.rs +++ b/crates/ra_analysis/src/roots.rs @@ -8,6 +8,7 @@ use rustc_hash::{FxHashMap, FxHashSet}; use salsa::Database; use crate::{ + Cancelable, db::{self, FilesDatabase, SyntaxDatabase}, descriptors::{ModuleDescriptor, ModuleTreeDescriptor}, imp::FileResolverImp, @@ -18,7 +19,7 @@ use crate::{ pub(crate) trait SourceRoot { fn contains(&self, file_id: FileId) -> bool; - fn module_tree(&self) -> Arc; + fn module_tree(&self) -> Cancelable>; fn lines(&self, file_id: FileId) -> Arc; fn syntax(&self, file_id: FileId) -> File; fn symbols(&self, acc: &mut Vec>); @@ -64,7 +65,7 @@ impl WritableSourceRoot { } impl SourceRoot for WritableSourceRoot { - fn module_tree(&self) -> Arc { + fn module_tree(&self) -> Cancelable> { self.db.module_tree() } fn contains(&self, file_id: FileId) -> bool { @@ -167,8 +168,8 @@ impl ReadonlySourceRoot { } impl SourceRoot for ReadonlySourceRoot { - fn module_tree(&self) -> Arc { - Arc::clone(&self.module_tree) + fn module_tree(&self) -> Cancelable> { + Ok(Arc::clone(&self.module_tree)) } fn contains(&self, file_id: FileId) -> bool { self.file_map.contains_key(&file_id) -- cgit v1.2.3 From 71cbdddf1c6b6c34c05aea01b92bb8a105b32c71 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:29:26 +0300 Subject: make file-symbols query cancelable --- crates/ra_analysis/src/db.rs | 24 +++++++++++++----------- crates/ra_analysis/src/imp.rs | 39 +++++++++++++++++++++++---------------- crates/ra_analysis/src/lib.rs | 4 ++-- crates/ra_analysis/src/roots.rs | 21 ++++++++++----------- 4 files changed, 48 insertions(+), 40 deletions(-) diff --git a/crates/ra_analysis/src/db.rs b/crates/ra_analysis/src/db.rs index cce959669..d621b3b22 100644 --- a/crates/ra_analysis/src/db.rs +++ b/crates/ra_analysis/src/db.rs @@ -1,17 +1,19 @@ -use crate::{ - module_map::{ModuleDescriptorQuery, ModuleTreeQuery, ModulesDatabase}, - symbol_index::SymbolIndex, - FileId, FileResolverImp, +use std::{ + fmt, + hash::{Hash, Hasher}, + sync::Arc, }; + use ra_editor::LineIndex; use ra_syntax::File; use rustc_hash::FxHashSet; use salsa; -use std::{ - fmt, - hash::{Hash, Hasher}, - sync::Arc, +use crate::{ + Cancelable, + module_map::{ModuleDescriptorQuery, ModuleTreeQuery, ModulesDatabase}, + symbol_index::SymbolIndex, + FileId, FileResolverImp, }; #[derive(Default)] @@ -98,7 +100,7 @@ salsa::query_group! { fn file_lines(file_id: FileId) -> Arc { type FileLinesQuery; } - fn file_symbols(file_id: FileId) -> Arc { + fn file_symbols(file_id: FileId) -> Cancelable> { type FileSymbolsQuery; } } @@ -112,7 +114,7 @@ fn file_lines(db: &impl SyntaxDatabase, file_id: FileId) -> Arc { let text = db.file_text(file_id); Arc::new(LineIndex::new(&*text)) } -fn file_symbols(db: &impl SyntaxDatabase, file_id: FileId) -> Arc { +fn file_symbols(db: &impl SyntaxDatabase, file_id: FileId) -> Cancelable> { let syntax = db.file_syntax(file_id); - Arc::new(SymbolIndex::for_file(file_id, syntax)) + Ok(Arc::new(SymbolIndex::for_file(file_id, syntax))) } diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index df5aacb2d..32e9bb6d7 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -148,14 +148,16 @@ impl AnalysisImpl { pub fn file_line_index(&self, file_id: FileId) -> Arc { self.root(file_id).lines(file_id) } - pub fn world_symbols(&self, query: Query) -> Vec<(FileId, FileSymbol)> { + pub fn world_symbols(&self, query: Query) -> Cancelable> { let mut buf = Vec::new(); if query.libs { - self.data.libs.iter().for_each(|it| it.symbols(&mut buf)); + for lib in self.data.libs.iter() { + lib.symbols(&mut buf)?; + } } else { - self.data.root.symbols(&mut buf); + self.data.root.symbols(&mut buf)?; } - query.search(&buf) + Ok(query.search(&buf)) } pub fn parent_module(&self, file_id: FileId) -> Cancelable> { let root = self.root(file_id); @@ -212,7 +214,7 @@ impl AnalysisImpl { let syntax = file.syntax(); if let Some(name_ref) = find_node_at_offset::(syntax, offset) { // First try to resolve the symbol locally - if let Some((name, range)) = resolve_local_name(&file, offset, name_ref) { + return if let Some((name, range)) = resolve_local_name(&file, offset, name_ref) { let mut vec = vec![]; vec.push(( file_id, @@ -222,12 +224,11 @@ impl AnalysisImpl { kind: NAME, }, )); - - return Ok(vec); + Ok(vec) } else { // If that fails try the index based approach. - return Ok(self.index_resolve(name_ref)); - } + self.index_resolve(name_ref) + }; } if let Some(name) = find_node_at_offset::(syntax, offset) { if let Some(module) = name.syntax().parent().and_then(ast::Module::cast) { @@ -379,17 +380,23 @@ impl AnalysisImpl { &self, file_id: FileId, offset: TextUnit, - ) -> Option<(FnDescriptor, Option)> { + ) -> Cancelable)>> { let root = self.root(file_id); let file = root.syntax(file_id); let syntax = file.syntax(); // Find the calling expression and it's NameRef - let calling_node = FnCallNode::with_node(syntax, offset)?; - let name_ref = calling_node.name_ref()?; + let calling_node = match FnCallNode::with_node(syntax, offset) { + Some(node) => node, + None => return Ok(None), + }; + let name_ref = match calling_node.name_ref() { + Some(name) => name, + None => return Ok(None), + }; // Resolve the function's NameRef (NOTE: this isn't entirely accurate). - let file_symbols = self.index_resolve(name_ref); + let file_symbols = self.index_resolve(name_ref)?; for (_, fs) in file_symbols { if fs.kind == FN_DEF { if let Some(fn_def) = find_node_at_offset(syntax, fs.node_range.start()) { @@ -431,16 +438,16 @@ impl AnalysisImpl { } } - return Some((descriptor, current_parameter)); + return Ok(Some((descriptor, current_parameter))); } } } } - None + Ok(None) } - fn index_resolve(&self, name_ref: ast::NameRef) -> Vec<(FileId, FileSymbol)> { + fn index_resolve(&self, name_ref: ast::NameRef) -> Cancelable> { let name = name_ref.text(); let mut query = Query::new(name.to_string()); query.exact(); diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 6ce32894a..189dbd9c2 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -224,7 +224,7 @@ impl Analysis { ra_editor::folding_ranges(&file) } pub fn symbol_search(&self, query: Query) -> Cancelable> { - Ok(self.imp.world_symbols(query)) + self.imp.world_symbols(query) } pub fn approximately_resolve_symbol( &self, @@ -269,7 +269,7 @@ impl Analysis { file_id: FileId, offset: TextUnit, ) -> Cancelable)>> { - Ok(self.imp.resolve_callable(file_id, offset)) + self.imp.resolve_callable(file_id, offset) } } diff --git a/crates/ra_analysis/src/roots.rs b/crates/ra_analysis/src/roots.rs index e950a75e2..123c4acfa 100644 --- a/crates/ra_analysis/src/roots.rs +++ b/crates/ra_analysis/src/roots.rs @@ -22,7 +22,7 @@ pub(crate) trait SourceRoot { fn module_tree(&self) -> Cancelable>; fn lines(&self, file_id: FileId) -> Arc; fn syntax(&self, file_id: FileId) -> File; - fn symbols(&self, acc: &mut Vec>); + fn symbols(&self, acc: &mut Vec>) -> Cancelable<()>; } #[derive(Default, Debug, Clone)] @@ -77,14 +77,12 @@ impl SourceRoot for WritableSourceRoot { fn syntax(&self, file_id: FileId) -> File { self.db.file_syntax(file_id) } - fn symbols<'a>(&'a self, acc: &mut Vec>) { - let db = &self.db; - let symbols = db.file_set(); - let symbols = symbols - .files - .iter() - .map(|&file_id| db.file_symbols(file_id)); - acc.extend(symbols); + fn symbols<'a>(&'a self, acc: &mut Vec>) -> Cancelable<()> { + for &file_id in self.db.file_set().files.iter() { + let symbols = self.db.file_symbols(file_id)?; + acc.push(symbols) + } + Ok(()) } } @@ -180,7 +178,8 @@ impl SourceRoot for ReadonlySourceRoot { fn syntax(&self, file_id: FileId) -> File { self.data(file_id).syntax().clone() } - fn symbols(&self, acc: &mut Vec>) { - acc.push(Arc::clone(&self.symbol_index)) + fn symbols(&self, acc: &mut Vec>) -> Cancelable<()> { + acc.push(Arc::clone(&self.symbol_index)); + Ok(()) } } -- cgit v1.2.3 From 8eea10e3ab25111375a95990b93d1170d5fe8a9f Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:35:55 +0300 Subject: actually check for cancelation --- crates/ra_analysis/src/db.rs | 12 +++++++++++- crates/ra_analysis/src/lib.rs | 8 ++++---- crates/ra_analysis/src/module_map.rs | 7 +++++-- 3 files changed, 20 insertions(+), 7 deletions(-) diff --git a/crates/ra_analysis/src/db.rs b/crates/ra_analysis/src/db.rs index d621b3b22..09d74b9e7 100644 --- a/crates/ra_analysis/src/db.rs +++ b/crates/ra_analysis/src/db.rs @@ -10,7 +10,8 @@ use rustc_hash::FxHashSet; use salsa; use crate::{ - Cancelable, + db, + Cancelable, Canceled, module_map::{ModuleDescriptorQuery, ModuleTreeQuery, ModulesDatabase}, symbol_index::SymbolIndex, FileId, FileResolverImp, @@ -33,6 +34,14 @@ impl salsa::Database for RootDatabase { } } +pub(crate) fn check_canceled(db: &impl salsa::Database) -> Cancelable<()> { + if db.salsa_runtime().is_current_revision_canceled() { + Err(Canceled) + } else { + Ok(()) + } +} + impl salsa::ParallelDatabase for RootDatabase { fn fork(&self) -> Self { RootDatabase { @@ -115,6 +124,7 @@ fn file_lines(db: &impl SyntaxDatabase, file_id: FileId) -> Arc { Arc::new(LineIndex::new(&*text)) } fn file_symbols(db: &impl SyntaxDatabase, file_id: FileId) -> Cancelable> { + db::check_canceled(db)?; let syntax = db.file_syntax(file_id); Ok(Arc::new(SymbolIndex::for_file(file_id, syntax))) } diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 189dbd9c2..03708d450 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -38,17 +38,17 @@ pub use ra_editor::{ }; #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord)] -pub struct Cancel; +pub struct Canceled; -pub type Cancelable = Result; +pub type Cancelable = Result; -impl std::fmt::Display for Cancel { +impl std::fmt::Display for Canceled { fn fmt(&self, fmt: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { fmt.write_str("Canceled") } } -impl std::error::Error for Cancel { +impl std::error::Error for Canceled { } #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)] diff --git a/crates/ra_analysis/src/module_map.rs b/crates/ra_analysis/src/module_map.rs index 0c413becd..3c800265a 100644 --- a/crates/ra_analysis/src/module_map.rs +++ b/crates/ra_analysis/src/module_map.rs @@ -1,12 +1,13 @@ +use std::sync::Arc; + use crate::{ + db, Cancelable, db::SyntaxDatabase, descriptors::{ModuleDescriptor, ModuleTreeDescriptor}, FileId, }; -use std::sync::Arc; - salsa::query_group! { pub(crate) trait ModulesDatabase: SyntaxDatabase { fn module_tree() -> Cancelable> { @@ -19,11 +20,13 @@ salsa::query_group! { } fn module_descriptor(db: &impl ModulesDatabase, file_id: FileId) -> Cancelable> { + db::check_canceled(db)?; let file = db.file_syntax(file_id); Ok(Arc::new(ModuleDescriptor::new(file.ast()))) } fn module_tree(db: &impl ModulesDatabase) -> Cancelable> { + db::check_canceled(db)?; let file_set = db.file_set(); let mut files = Vec::new(); for &file_id in file_set.files.iter() { -- cgit v1.2.3 From 6e88aaef5d49c8ec7b6ffe6b41457c3a028b4eb0 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:38:47 +0300 Subject: use pythonic import order use std // blank line use extern crates // blank line use crate::{} --- crates/ra_analysis/src/descriptors.rs | 5 +++-- crates/ra_analysis/src/lib.rs | 3 ++- crates/ra_analysis/src/symbol_index.rs | 11 ++++++----- crates/ra_lsp_server/src/main_loop/handlers.rs | 5 ++--- crates/ra_lsp_server/src/path_map.rs | 4 ++-- crates/ra_lsp_server/src/project_model.rs | 4 ++-- crates/ra_lsp_server/src/thread_watcher.rs | 5 +++-- 7 files changed, 20 insertions(+), 17 deletions(-) diff --git a/crates/ra_analysis/src/descriptors.rs b/crates/ra_analysis/src/descriptors.rs index 6f26f9935..310bf1585 100644 --- a/crates/ra_analysis/src/descriptors.rs +++ b/crates/ra_analysis/src/descriptors.rs @@ -1,4 +1,5 @@ -use crate::{imp::FileResolverImp, FileId}; +use std::collections::BTreeMap; + use ra_syntax::{ ast::{self, AstNode, NameOwner}, text_utils::is_subrange, @@ -6,7 +7,7 @@ use ra_syntax::{ }; use relative_path::RelativePathBuf; -use std::collections::BTreeMap; +use crate::{imp::FileResolverImp, FileId}; #[derive(Debug, PartialEq, Eq, Hash)] pub struct ModuleDescriptor { diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 03708d450..750031093 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -23,11 +23,12 @@ mod symbol_index; use std::{fmt::Debug, sync::Arc}; -use crate::imp::{AnalysisHostImpl, AnalysisImpl, FileResolverImp}; use ra_syntax::{AtomEdit, File, TextRange, TextUnit}; use relative_path::{RelativePath, RelativePathBuf}; use rustc_hash::FxHashMap; +use crate::imp::{AnalysisHostImpl, AnalysisImpl, FileResolverImp}; + pub use crate::{ descriptors::FnDescriptor, job::{JobHandle, JobToken}, diff --git a/crates/ra_analysis/src/symbol_index.rs b/crates/ra_analysis/src/symbol_index.rs index 19f9ea47d..a0f3c0437 100644 --- a/crates/ra_analysis/src/symbol_index.rs +++ b/crates/ra_analysis/src/symbol_index.rs @@ -1,4 +1,8 @@ -use crate::{FileId, Query}; +use std::{ + hash::{Hash, Hasher}, + sync::Arc, +}; + use fst::{self, Streamer}; use ra_editor::{file_symbols, FileSymbol}; use ra_syntax::{ @@ -7,10 +11,7 @@ use ra_syntax::{ }; use rayon::prelude::*; -use std::{ - hash::{Hash, Hasher}, - sync::Arc, -}; +use crate::{FileId, Query}; #[derive(Debug)] pub(crate) struct SymbolIndex { diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs index 78a8ccfc5..673f1bf7d 100644 --- a/crates/ra_lsp_server/src/main_loop/handlers.rs +++ b/crates/ra_lsp_server/src/main_loop/handlers.rs @@ -1,5 +1,6 @@ -use rustc_hash::FxHashMap; +use std::collections::HashMap; +use rustc_hash::FxHashMap; use languageserver_types::{ CodeActionResponse, Command, CompletionItem, CompletionItemKind, Diagnostic, DiagnosticSeverity, DocumentSymbol, FoldingRange, FoldingRangeKind, FoldingRangeParams, @@ -18,8 +19,6 @@ use crate::{ Result, }; -use std::collections::HashMap; - pub fn handle_syntax_tree( world: ServerWorld, params: req::SyntaxTreeParams, diff --git a/crates/ra_lsp_server/src/path_map.rs b/crates/ra_lsp_server/src/path_map.rs index 585013acd..d32829382 100644 --- a/crates/ra_lsp_server/src/path_map.rs +++ b/crates/ra_lsp_server/src/path_map.rs @@ -1,9 +1,9 @@ +use std::path::{Component, Path, PathBuf}; + use im; use ra_analysis::{FileId, FileResolver}; use relative_path::RelativePath; -use std::path::{Component, Path, PathBuf}; - #[derive(Debug, Clone, Copy, PartialEq, Eq)] pub enum Root { Workspace, diff --git a/crates/ra_lsp_server/src/project_model.rs b/crates/ra_lsp_server/src/project_model.rs index d170ceb73..04e2ef9c8 100644 --- a/crates/ra_lsp_server/src/project_model.rs +++ b/crates/ra_lsp_server/src/project_model.rs @@ -1,9 +1,9 @@ +use std::path::{Path, PathBuf}; + use cargo_metadata::{metadata_run, CargoOpt}; use ra_syntax::SmolStr; use rustc_hash::{FxHashMap, FxHashSet}; -use std::path::{Path, PathBuf}; - use crate::{ thread_watcher::{ThreadWatcher, Worker}, Result, diff --git a/crates/ra_lsp_server/src/thread_watcher.rs b/crates/ra_lsp_server/src/thread_watcher.rs index 67952eb74..51b35fa66 100644 --- a/crates/ra_lsp_server/src/thread_watcher.rs +++ b/crates/ra_lsp_server/src/thread_watcher.rs @@ -1,8 +1,9 @@ -use crate::Result; +use std::thread; + use crossbeam_channel::{bounded, unbounded, Receiver, Sender}; use drop_bomb::DropBomb; -use std::thread; +use crate::Result; pub struct Worker { pub inp: Sender, -- cgit v1.2.3 From 8bb4380448f3ef5391beff1b9f64bf956c43b61f Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:43:36 +0300 Subject: Fix tests --- crates/ra_analysis/tests/tests.rs | 31 ++++++++++++++----------------- 1 file changed, 14 insertions(+), 17 deletions(-) diff --git a/crates/ra_analysis/tests/tests.rs b/crates/ra_analysis/tests/tests.rs index 0c2c69ea0..7ae3d0eeb 100644 --- a/crates/ra_analysis/tests/tests.rs +++ b/crates/ra_analysis/tests/tests.rs @@ -7,15 +7,15 @@ extern crate test_utils; use std::sync::Arc; -use ra_analysis::{ - Analysis, AnalysisHost, CrateGraph, CrateId, FileId, FileResolver, FnDescriptor, JobHandle, -}; use ra_syntax::TextRange; - use relative_path::{RelativePath, RelativePathBuf}; use rustc_hash::FxHashMap; use test_utils::{assert_eq_dbg, extract_offset}; +use ra_analysis::{ + Analysis, AnalysisHost, CrateGraph, CrateId, FileId, FileResolver, FnDescriptor, +}; + #[derive(Debug)] struct FileMap(Vec<(FileId, RelativePathBuf)>); @@ -64,24 +64,22 @@ fn get_signature(text: &str) -> (FnDescriptor, Option) { let (offset, code) = extract_offset(text); let code = code.as_str(); - let (_handle, token) = JobHandle::new(); let snap = analysis(&[("/lib.rs", code)]); - snap.resolve_callable(FileId(1), offset, &token).unwrap() + snap.resolve_callable(FileId(1), offset).unwrap().unwrap() } #[test] fn test_resolve_module() { let snap = analysis(&[("/lib.rs", "mod foo;"), ("/foo.rs", "")]); - let (_handle, token) = JobHandle::new(); - let symbols = snap.approximately_resolve_symbol(FileId(1), 4.into(), &token); + let symbols = snap.approximately_resolve_symbol(FileId(1), 4.into()).unwrap(); assert_eq_dbg( r#"[(FileId(2), FileSymbol { name: "foo", node_range: [0; 0), kind: MODULE })]"#, &symbols, ); let snap = analysis(&[("/lib.rs", "mod foo;"), ("/foo/mod.rs", "")]); - let symbols = snap.approximately_resolve_symbol(FileId(1), 4.into(), &token); + let symbols = snap.approximately_resolve_symbol(FileId(1), 4.into()).unwrap(); assert_eq_dbg( r#"[(FileId(2), FileSymbol { name: "foo", node_range: [0; 0), kind: MODULE })]"#, &symbols, @@ -91,7 +89,7 @@ fn test_resolve_module() { #[test] fn test_unresolved_module_diagnostic() { let snap = analysis(&[("/lib.rs", "mod foo;")]); - let diagnostics = snap.diagnostics(FileId(1)); + let diagnostics = snap.diagnostics(FileId(1)).unwrap(); assert_eq_dbg( r#"[Diagnostic { message: "unresolved module", @@ -108,14 +106,14 @@ fn test_unresolved_module_diagnostic() { #[test] fn test_unresolved_module_diagnostic_no_diag_for_inline_mode() { let snap = analysis(&[("/lib.rs", "mod foo {}")]); - let diagnostics = snap.diagnostics(FileId(1)); + let diagnostics = snap.diagnostics(FileId(1)).unwrap(); assert_eq_dbg(r#"[]"#, &diagnostics); } #[test] fn test_resolve_parent_module() { let snap = analysis(&[("/lib.rs", "mod foo;"), ("/foo.rs", "")]); - let symbols = snap.parent_module(FileId(2)); + let symbols = snap.parent_module(FileId(2)).unwrap(); assert_eq_dbg( r#"[(FileId(1), FileSymbol { name: "foo", node_range: [0; 8), kind: MODULE })]"#, &symbols, @@ -126,7 +124,7 @@ fn test_resolve_parent_module() { fn test_resolve_crate_root() { let mut host = analysis_host(&[("/lib.rs", "mod foo;"), ("/foo.rs", "")]); let snap = host.analysis(); - assert!(snap.crate_for(FileId(2)).is_empty()); + assert!(snap.crate_for(FileId(2)).unwrap().is_empty()); let crate_graph = CrateGraph { crate_roots: { @@ -138,7 +136,7 @@ fn test_resolve_crate_root() { host.set_crate_graph(crate_graph); let snap = host.analysis(); - assert_eq!(snap.crate_for(FileId(2)), vec![CrateId(1)],); + assert_eq!(snap.crate_for(FileId(2)).unwrap(), vec![CrateId(1)],); } #[test] @@ -232,10 +230,9 @@ fn get_all_refs(text: &str) -> Vec<(FileId, TextRange)> { let (offset, code) = extract_offset(text); let code = code.as_str(); - let (_handle, token) = JobHandle::new(); let snap = analysis(&[("/lib.rs", code)]); - snap.find_all_refs(FileId(1), offset, &token) + snap.find_all_refs(FileId(1), offset).unwrap() } #[test] @@ -266,4 +263,4 @@ fn test_find_all_refs_for_param_inside() { let refs = get_all_refs(code); assert_eq!(refs.len(), 2); -} \ No newline at end of file +} -- cgit v1.2.3 From 0102a01f76c855da447e25eb81191047a3ca79b8 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Sat, 20 Oct 2018 22:59:54 +0300 Subject: Remove job handle --- Cargo.lock | 1 - crates/ra_analysis/Cargo.toml | 1 - crates/ra_analysis/src/job.rs | 53 -------------------------- crates/ra_analysis/src/lib.rs | 4 -- crates/ra_lsp_server/src/main_loop/handlers.rs | 21 +--------- crates/ra_lsp_server/src/main_loop/mod.rs | 38 +++++++++--------- 6 files changed, 18 insertions(+), 100 deletions(-) delete mode 100644 crates/ra_analysis/src/job.rs diff --git a/Cargo.lock b/Cargo.lock index bb0feec2e..f51914883 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -609,7 +609,6 @@ dependencies = [ name = "ra_analysis" version = "0.1.0" dependencies = [ - "crossbeam-channel 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", "fst 0.3.2 (registry+https://github.com/rust-lang/crates.io-index)", "im 12.2.0 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.4.5 (registry+https://github.com/rust-lang/crates.io-index)", diff --git a/crates/ra_analysis/Cargo.toml b/crates/ra_analysis/Cargo.toml index dd4ec8375..d7ac69fe8 100644 --- a/crates/ra_analysis/Cargo.toml +++ b/crates/ra_analysis/Cargo.toml @@ -7,7 +7,6 @@ authors = ["Aleksey Kladov "] [dependencies] relative-path = "0.3.7" log = "0.4.2" -crossbeam-channel = "0.2.4" parking_lot = "0.6.3" once_cell = "0.1.5" rayon = "1.0.2" diff --git a/crates/ra_analysis/src/job.rs b/crates/ra_analysis/src/job.rs deleted file mode 100644 index 2871f9839..000000000 --- a/crates/ra_analysis/src/job.rs +++ /dev/null @@ -1,53 +0,0 @@ -use crossbeam_channel::{bounded, Receiver, Sender}; - -pub struct JobHandle { - job_alive: Receiver, - _job_canceled: Sender, -} - -pub struct JobToken { - _job_alive: Sender, - job_canceled: Receiver, -} - -impl JobHandle { - pub fn new() -> (JobHandle, JobToken) { - let (sender_alive, receiver_alive) = bounded(0); - let (sender_canceled, receiver_canceled) = bounded(0); - let token = JobToken { - _job_alive: sender_alive, - job_canceled: receiver_canceled, - }; - let handle = JobHandle { - job_alive: receiver_alive, - _job_canceled: sender_canceled, - }; - (handle, token) - } - pub fn has_completed(&self) -> bool { - is_closed(&self.job_alive) - } - pub fn cancel(self) {} -} - -impl JobToken { - pub fn is_canceled(&self) -> bool { - is_closed(&self.job_canceled) - } -} - -// We don't actually send messages through the channels, -// and instead just check if the channel is closed, -// so we use uninhabited enum as a message type -enum Never {} - -/// Nonblocking -fn is_closed(chan: &Receiver) -> bool { - select! { - recv(chan, msg) => match msg { - None => true, - Some(never) => match never {} - } - default => false, - } -} diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 750031093..28e0a12b2 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -7,8 +7,6 @@ extern crate ra_editor; extern crate ra_syntax; extern crate rayon; extern crate relative_path; -#[macro_use] -extern crate crossbeam_channel; extern crate im; extern crate rustc_hash; extern crate salsa; @@ -16,7 +14,6 @@ extern crate salsa; mod db; mod descriptors; mod imp; -mod job; mod module_map; mod roots; mod symbol_index; @@ -31,7 +28,6 @@ use crate::imp::{AnalysisHostImpl, AnalysisImpl, FileResolverImp}; pub use crate::{ descriptors::FnDescriptor, - job::{JobHandle, JobToken}, }; pub use ra_editor::{ CompletionItem, FileSymbol, Fold, FoldKind, HighlightedRange, LineIndex, Runnable, diff --git a/crates/ra_lsp_server/src/main_loop/handlers.rs b/crates/ra_lsp_server/src/main_loop/handlers.rs index 673f1bf7d..f5dff4c80 100644 --- a/crates/ra_lsp_server/src/main_loop/handlers.rs +++ b/crates/ra_lsp_server/src/main_loop/handlers.rs @@ -7,7 +7,7 @@ use languageserver_types::{ InsertTextFormat, Location, Position, SymbolInformation, TextDocumentIdentifier, TextEdit, RenameParams, WorkspaceEdit, PrepareRenameResponse }; -use ra_analysis::{FileId, FoldKind, JobToken, Query, RunnableKind}; +use ra_analysis::{FileId, FoldKind, Query, RunnableKind}; use ra_syntax::text_utils::contains_offset_nonstrict; use serde_json::to_value; @@ -22,7 +22,6 @@ use crate::{ pub fn handle_syntax_tree( world: ServerWorld, params: req::SyntaxTreeParams, - _token: JobToken, ) -> Result { let id = params.text_document.try_conv_with(&world)?; let res = world.analysis().syntax_tree(id); @@ -32,7 +31,6 @@ pub fn handle_syntax_tree( pub fn handle_extend_selection( world: ServerWorld, params: req::ExtendSelectionParams, - _token: JobToken, ) -> Result { let file_id = params.text_document.try_conv_with(&world)?; let file = world.analysis().file_syntax(file_id); @@ -50,7 +48,6 @@ pub fn handle_extend_selection( pub fn handle_find_matching_brace( world: ServerWorld, params: req::FindMatchingBraceParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let file = world.analysis().file_syntax(file_id); @@ -73,7 +70,6 @@ pub fn handle_find_matching_brace( pub fn handle_join_lines( world: ServerWorld, params: req::JoinLinesParams, - _token: JobToken, ) -> Result { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -87,7 +83,6 @@ pub fn handle_join_lines( pub fn handle_on_enter( world: ServerWorld, params: req::TextDocumentPositionParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -101,7 +96,6 @@ pub fn handle_on_enter( pub fn handle_on_type_formatting( world: ServerWorld, params: req::DocumentOnTypeFormattingParams, - _token: JobToken, ) -> Result>> { if params.ch != "=" { return Ok(None); @@ -121,7 +115,6 @@ pub fn handle_on_type_formatting( pub fn handle_document_symbol( world: ServerWorld, params: req::DocumentSymbolParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -160,7 +153,6 @@ pub fn handle_document_symbol( pub fn handle_workspace_symbol( world: ServerWorld, params: req::WorkspaceSymbolParams, - _token: JobToken, ) -> Result>> { let all_symbols = params.query.contains("#"); let libs = params.query.contains("*"); @@ -212,7 +204,6 @@ pub fn handle_workspace_symbol( pub fn handle_goto_definition( world: ServerWorld, params: req::TextDocumentPositionParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -232,7 +223,6 @@ pub fn handle_goto_definition( pub fn handle_parent_module( world: ServerWorld, params: TextDocumentIdentifier, - _token: JobToken, ) -> Result> { let file_id = params.try_conv_with(&world)?; let mut res = Vec::new(); @@ -247,7 +237,6 @@ pub fn handle_parent_module( pub fn handle_runnables( world: ServerWorld, params: req::RunnablesParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -351,7 +340,6 @@ pub fn handle_runnables( pub fn handle_decorations( world: ServerWorld, params: TextDocumentIdentifier, - _token: JobToken, ) -> Result> { let file_id = params.try_conv_with(&world)?; highlight(&world, file_id) @@ -360,7 +348,6 @@ pub fn handle_decorations( pub fn handle_completion( world: ServerWorld, params: req::CompletionParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -392,7 +379,6 @@ pub fn handle_completion( pub fn handle_folding_range( world: ServerWorld, params: FoldingRangeParams, - _token: JobToken, ) -> Result>> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -425,7 +411,6 @@ pub fn handle_folding_range( pub fn handle_signature_help( world: ServerWorld, params: req::TextDocumentPositionParams, - _token: JobToken, ) -> Result> { use languageserver_types::{ParameterInformation, SignatureInformation}; @@ -464,7 +449,6 @@ pub fn handle_signature_help( pub fn handle_prepare_rename( world: ServerWorld, params: req::TextDocumentPositionParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -486,7 +470,6 @@ pub fn handle_prepare_rename( pub fn handle_rename( world: ServerWorld, params: RenameParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -523,7 +506,6 @@ pub fn handle_rename( pub fn handle_references( world: ServerWorld, params: req::ReferenceParams, - _token: JobToken, ) -> Result>> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); @@ -539,7 +521,6 @@ pub fn handle_references( pub fn handle_code_action( world: ServerWorld, params: req::CodeActionParams, - _token: JobToken, ) -> Result> { let file_id = params.text_document.try_conv_with(&world)?; let line_index = world.analysis().file_line_index(file_id); diff --git a/crates/ra_lsp_server/src/main_loop/mod.rs b/crates/ra_lsp_server/src/main_loop/mod.rs index 165f2e78f..b35ebd38b 100644 --- a/crates/ra_lsp_server/src/main_loop/mod.rs +++ b/crates/ra_lsp_server/src/main_loop/mod.rs @@ -8,9 +8,9 @@ use gen_lsp_server::{ handle_shutdown, ErrorCode, RawMessage, RawNotification, RawRequest, RawResponse, }; use languageserver_types::NumberOrString; -use ra_analysis::{FileId, JobHandle, JobToken, LibraryData}; +use ra_analysis::{FileId, LibraryData}; use rayon::{self, ThreadPool}; -use rustc_hash::FxHashMap; +use rustc_hash::FxHashSet; use serde::{de::DeserializeOwned, Serialize}; use crate::{ @@ -47,7 +47,7 @@ pub fn main_loop( info!("server initialized, serving requests"); let mut state = ServerWorldState::new(); - let mut pending_requests = FxHashMap::default(); + let mut pending_requests = FxHashSet::default(); let mut subs = Subscriptions::new(); let main_res = main_loop_inner( internal_mode, @@ -92,7 +92,7 @@ fn main_loop_inner( fs_worker: Worker)>, ws_worker: Worker>, state: &mut ServerWorldState, - pending_requests: &mut FxHashMap, + pending_requests: &mut FxHashSet, subs: &mut Subscriptions, ) -> Result<()> { let (libdata_sender, libdata_receiver) = unbounded(); @@ -204,14 +204,13 @@ fn main_loop_inner( fn on_task( task: Task, msg_sender: &Sender, - pending_requests: &mut FxHashMap, + pending_requests: &mut FxHashSet, ) { match task { Task::Respond(response) => { - if let Some(handle) = pending_requests.remove(&response.id) { - assert!(handle.has_completed()); + if pending_requests.remove(&response.id) { + msg_sender.send(RawMessage::Response(response)) } - msg_sender.send(RawMessage::Response(response)) } Task::Notify(n) => msg_sender.send(RawMessage::Notification(n)), } @@ -219,7 +218,7 @@ fn on_task( fn on_request( world: &mut ServerWorldState, - pending_requests: &mut FxHashMap, + pending_requests: &mut FxHashSet, pool: &ThreadPool, sender: &Sender, req: RawRequest, @@ -253,8 +252,8 @@ fn on_request( .on::(handlers::handle_references)? .finish(); match req { - Ok((id, handle)) => { - let inserted = pending_requests.insert(id, handle).is_none(); + Ok(id) => { + let inserted = pending_requests.insert(id); assert!(inserted, "duplicate request: {}", id); Ok(None) } @@ -265,7 +264,7 @@ fn on_request( fn on_notification( msg_sender: &Sender, state: &mut ServerWorldState, - pending_requests: &mut FxHashMap, + pending_requests: &mut FxHashSet, subs: &mut Subscriptions, not: RawNotification, ) -> Result<()> { @@ -277,9 +276,7 @@ fn on_notification( panic!("string id's not supported: {:?}", id); } }; - if let Some(handle) = pending_requests.remove(&id) { - handle.cancel(); - } + pending_requests.remove(&id); return Ok(()); } Err(not) => not, @@ -336,7 +333,7 @@ fn on_notification( struct PoolDispatcher<'a> { req: Option, - res: Option<(u64, JobHandle)>, + res: Option, pool: &'a ThreadPool, world: &'a ServerWorldState, sender: &'a Sender, @@ -345,7 +342,7 @@ struct PoolDispatcher<'a> { impl<'a> PoolDispatcher<'a> { fn on<'b, R>( &'b mut self, - f: fn(ServerWorld, R::Params, JobToken) -> Result, + f: fn(ServerWorld, R::Params) -> Result, ) -> Result<&'b mut Self> where R: req::Request, @@ -358,11 +355,10 @@ impl<'a> PoolDispatcher<'a> { }; match req.cast::() { Ok((id, params)) => { - let (handle, token) = JobHandle::new(); let world = self.world.snapshot(); let sender = self.sender.clone(); self.pool.spawn(move || { - let resp = match f(world, params, token) { + let resp = match f(world, params) { Ok(resp) => RawResponse::ok::(id, &resp), Err(e) => { RawResponse::err(id, ErrorCode::InternalError as i32, e.to_string()) @@ -371,14 +367,14 @@ impl<'a> PoolDispatcher<'a> { let task = Task::Respond(resp); sender.send(task); }); - self.res = Some((id, handle)); + self.res = Some(id); } Err(req) => self.req = Some(req), } Ok(self) } - fn finish(&mut self) -> ::std::result::Result<(u64, JobHandle), RawRequest> { + fn finish(&mut self) -> ::std::result::Result { match (self.res.take(), self.req.take()) { (Some(res), None) => Ok(res), (None, Some(req)) => Err(req), -- cgit v1.2.3