Skip to content
This repository was archived by the owner on Aug 19, 2022. It is now read-only.

Commit 245646b

Browse files
ebkalderonsilvanshade
authored andcommitted
Wrap tree-sitter Node<'_> in scope to keep future Send
It appears that certain `tree-sitter` values are not considered `Send` (thread-safe) when retained across an `await` point. To fix this, we wrap `node` in a scope so that the variable is destroyed before reaching the `client.publish_diagnostics()` call, which must be `Send`.
1 parent 6b0ff5e commit 245646b

File tree

1 file changed

+71
-68
lines changed

1 file changed

+71
-68
lines changed

crates/server/src/service/auditor.rs

Lines changed: 71 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -14,83 +14,86 @@ pub(crate) mod tree {
1414
pub(crate) async fn change(session: Arc<Session>, uri: Url) -> Fallible<()> {
1515
if let Some(document) = session.get_document(&uri).await? {
1616
let tree = document.tree.lock().await.clone();
17-
let node = tree.root_node();
18-
let mut diagnostics = vec![];
19-
if node.has_error() {
20-
// prepare a query to match tree-sitter ERROR nodes
21-
let language = tree.language();
22-
let source = "((ERROR) @error)"; // query the tree for ERROR nodes
23-
let query = tree_sitter::Query::new(language, source).map_err(Error::TreeSitterQueryError)?;
17+
let diagnostics = {
18+
let mut diagnostics = vec![];
19+
let node = tree.root_node();
20+
if node.has_error() {
21+
// prepare a query to match tree-sitter ERROR nodes
22+
let language = tree.language();
23+
let source = "((ERROR) @error)"; // query the tree for ERROR nodes
24+
let query = tree_sitter::Query::new(language, source).map_err(Error::TreeSitterQueryError)?;
2425

25-
// prepare a query cursor
26-
let mut query_cursor = tree_sitter::QueryCursor::new();
27-
let text_callback = |node: tree_sitter::Node| &document.text[node.byte_range()];
28-
let matches = query_cursor.matches(&query, node, text_callback);
26+
// prepare a query cursor
27+
let mut query_cursor = tree_sitter::QueryCursor::new();
28+
let text_callback = |node: tree_sitter::Node| &document.text[node.byte_range()];
29+
let matches = query_cursor.matches(&query, node, text_callback);
2930

30-
// iterate the query cursor and construct appropriate lsp diagnostics
31-
for tree_sitter::QueryMatch { captures, .. } in matches {
32-
'captures: for tree_sitter::QueryCapture { node, .. } in captures {
33-
// create a cursor node starting from the capture node
34-
let mut cursor = *node;
31+
// iterate the query cursor and construct appropriate lsp diagnostics
32+
for tree_sitter::QueryMatch { captures, .. } in matches {
33+
'captures: for tree_sitter::QueryCapture { node, .. } in captures {
34+
// create a cursor node starting from the capture node
35+
let mut cursor = *node;
3536

36-
// traverse upward through the parent nodes
37-
'cursor: while let Some(parent) = cursor.parent() {
38-
cursor = parent;
39-
// ignore further processing if the first non-ERROR
40-
// parent node is a comment node; we do this in
41-
// order to avoid syntax errors due to encoding
42-
// issues (see "comments.wast" and issue #42)
43-
if !cursor.is_error() {
44-
match document.language {
45-
Language::Wast
46-
if [
47-
*wast::kind::COMMENT_BLOCK_ANNOT,
48-
*wast::kind::COMMENT_BLOCK,
49-
*wast::kind::COMMENT_LINE_ANNOT,
50-
*wast::kind::COMMENT_LINE,
51-
]
52-
.contains(&parent.kind_id()) =>
53-
{
54-
break 'captures;
37+
// traverse upward through the parent nodes
38+
'cursor: while let Some(parent) = cursor.parent() {
39+
cursor = parent;
40+
// ignore further processing if the first non-ERROR
41+
// parent node is a comment node; we do this in
42+
// order to avoid syntax errors due to encoding
43+
// issues (see "comments.wast" and issue #42)
44+
if !cursor.is_error() {
45+
match document.language {
46+
Language::Wast
47+
if [
48+
*wast::kind::COMMENT_BLOCK_ANNOT,
49+
*wast::kind::COMMENT_BLOCK,
50+
*wast::kind::COMMENT_LINE_ANNOT,
51+
*wast::kind::COMMENT_LINE,
52+
]
53+
.contains(&parent.kind_id()) =>
54+
{
55+
break 'captures;
56+
}
57+
Language::Wat
58+
if [
59+
*wat::kind::COMMENT_BLOCK_ANNOT,
60+
*wat::kind::COMMENT_BLOCK,
61+
*wat::kind::COMMENT_LINE_ANNOT,
62+
*wat::kind::COMMENT_LINE,
63+
]
64+
.contains(&parent.kind_id()) =>
65+
{
66+
break 'captures;
67+
}
68+
_ => {
69+
break 'cursor;
70+
},
5571
}
56-
Language::Wat
57-
if [
58-
*wat::kind::COMMENT_BLOCK_ANNOT,
59-
*wat::kind::COMMENT_BLOCK,
60-
*wat::kind::COMMENT_LINE_ANNOT,
61-
*wat::kind::COMMENT_LINE,
62-
]
63-
.contains(&parent.kind_id()) =>
64-
{
65-
break 'captures;
66-
}
67-
_ => {
68-
break 'cursor;
69-
},
7072
}
7173
}
72-
}
7374

74-
let start = node.start_position();
75-
let end = node.end_position();
76-
diagnostics.push({
77-
let range = {
78-
let start = Position::new(start.row as u64, start.column as u64);
79-
let end = Position::new(end.row as u64, end.column as u64);
80-
Range::new(start, end)
81-
};
82-
let severity = Some(DiagnosticSeverity::Error);
83-
let code = None;
84-
let source = Some(String::from("wasm-lsp"));
85-
let message = String::from("syntax error");
86-
let related_information = None;
87-
let tags = None;
88-
Diagnostic::new(range, severity, code, source, message, related_information, tags)
89-
});
75+
let start = node.start_position();
76+
let end = node.end_position();
77+
diagnostics.push({
78+
let range = {
79+
let start = Position::new(start.row as u64, start.column as u64);
80+
let end = Position::new(end.row as u64, end.column as u64);
81+
Range::new(start, end)
82+
};
83+
let severity = Some(DiagnosticSeverity::Error);
84+
let code = None;
85+
let source = Some(String::from("wasm-lsp"));
86+
let message = String::from("syntax error");
87+
let related_information = None;
88+
let tags = None;
89+
Diagnostic::new(range, severity, code, source, message, related_information, tags)
90+
});
91+
}
9092
}
9193
}
92-
}
93-
// NOTE: else let elaborator handle
94+
// NOTE: else let elaborator handle
95+
diagnostics
96+
};
9497
let version = None;
9598
session.client.publish_diagnostics(uri, diagnostics, version).await;
9699
}

0 commit comments

Comments
 (0)