Fix query match failure when indefinite steps have no captures
Fixes #937
This commit is contained in:
parent
48584c7cad
commit
c25fa9910e
2 changed files with 51 additions and 1 deletions
|
|
@ -1861,6 +1861,56 @@ fn test_query_matches_with_repeated_fields() {
|
|||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_query_matches_with_indefinite_step_containing_no_captures() {
|
||||
allocations::record(|| {
|
||||
// This pattern depends on the field declarations within the
|
||||
// struct's body, but doesn't capture anything within the body.
|
||||
// It demonstrates that internally, state-splitting needs to occur
|
||||
// for each field declaration within the body, in order to avoid
|
||||
// prematurely failing if the first field does not match.
|
||||
//
|
||||
// https://github.com/tree-sitter/tree-sitter/issues/937
|
||||
let language = get_language("c");
|
||||
let query = Query::new(
|
||||
language,
|
||||
"(struct_specifier
|
||||
name: (type_identifier) @name
|
||||
body: (field_declaration_list
|
||||
(field_declaration
|
||||
type: (union_specifier))))",
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
assert_query_matches(
|
||||
language,
|
||||
&query,
|
||||
"
|
||||
struct LacksUnionField {
|
||||
int a;
|
||||
struct {
|
||||
B c;
|
||||
} d;
|
||||
G *h;
|
||||
};
|
||||
|
||||
struct HasUnionField {
|
||||
int a;
|
||||
struct {
|
||||
B c;
|
||||
} d;
|
||||
union {
|
||||
bool e;
|
||||
float f;
|
||||
} g;
|
||||
G *h;
|
||||
};
|
||||
",
|
||||
&[(0, vec![("name", "HasUnionField")])],
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_query_captures_basic() {
|
||||
allocations::record(|| {
|
||||
|
|
|
|||
|
|
@ -2676,7 +2676,7 @@ static inline bool ts_query_cursor__advance(
|
|||
// parent, then this query state cannot simply be updated in place. It must be
|
||||
// split into two states: one that matches this node, and one which skips over
|
||||
// this node, to preserve the possibility of matching later siblings.
|
||||
if (later_sibling_can_match && step->contains_captures) {
|
||||
if (later_sibling_can_match && (step->contains_captures || !step->is_definite)) {
|
||||
if (ts_query_cursor__copy_state(self, &state)) {
|
||||
LOG(
|
||||
" split state for capture. pattern:%u, step:%u\n",
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue