diff --git a/lib/src/stack.c b/lib/src/stack.c index 73c06454..3e842c99 100644 --- a/lib/src/stack.c +++ b/lib/src/stack.c @@ -583,6 +583,7 @@ int ts_stack_dynamic_precedence(Stack *self, StackVersion version) { bool ts_stack_has_advanced_since_error(const Stack *self, StackVersion version) { const StackHead *head = array_get(&self->heads, version); const StackNode *node = head->node; + if (node->error_cost == 0) return true; while (node) { if (node->link_count > 0) { Subtree subtree = node->links[0].subtree; diff --git a/test/fixtures/test_grammars/epsilon_external_tokens/corpus.txt b/test/fixtures/test_grammars/epsilon_external_tokens/corpus.txt new file mode 100644 index 00000000..6d16133b --- /dev/null +++ b/test/fixtures/test_grammars/epsilon_external_tokens/corpus.txt @@ -0,0 +1,9 @@ +========================== +A leading zero-width token +========================== + +hello + +--- + +(document (zero_width)) diff --git a/test/fixtures/test_grammars/epsilon_external_tokens/grammar.json b/test/fixtures/test_grammars/epsilon_external_tokens/grammar.json new file mode 100644 index 00000000..89be042a --- /dev/null +++ b/test/fixtures/test_grammars/epsilon_external_tokens/grammar.json @@ -0,0 +1,21 @@ +{ + "name": "epsilon_external_tokens", + + "externals": [ + {"type": "SYMBOL", "name": "zero_width"} + ], + + "extras": [ + {"type": "PATTERN", "value": "\\s"} + ], + + "rules": { + "document": { + "type": "SEQ", + "members": [ + {"type": "SYMBOL", "name": "zero_width"}, + {"type": "STRING", "value": "hello"} + ] + } + } +} diff --git a/test/fixtures/test_grammars/epsilon_external_tokens/scanner.c b/test/fixtures/test_grammars/epsilon_external_tokens/scanner.c new file mode 100644 index 00000000..85bc7c60 --- /dev/null +++ b/test/fixtures/test_grammars/epsilon_external_tokens/scanner.c @@ -0,0 +1,33 @@ +#include + +enum TokenType { + ZERO_WIDTH_TOKEN +}; + +void *tree_sitter_epsilon_external_tokens_external_scanner_create() { + return NULL; +} + +bool tree_sitter_epsilon_external_tokens_external_scanner_scan( + void *payload, + TSLexer *lexer, + const bool *valid_symbols +) { + lexer->result_symbol = ZERO_WIDTH_TOKEN; + return true; +} + +unsigned tree_sitter_epsilon_external_tokens_external_scanner_serialize( + void *payload, + char *buffer +) { + return 0; +} + +void tree_sitter_epsilon_external_tokens_external_scanner_deserialize( + void *payload, + const char *buffer, + unsigned length +) {} + +void tree_sitter_epsilon_external_tokens_external_scanner_destroy(void *payload) {}