]> git.eshelyaron.com Git - emacs.git/commitdiff
Fix tree-sitter assertion error (bug#59574)
authorYuan Fu <casouri@gmail.com>
Sat, 26 Nov 2022 02:50:26 +0000 (18:50 -0800)
committerYuan Fu <casouri@gmail.com>
Sat, 26 Nov 2022 03:00:22 +0000 (19:00 -0800)
* src/treesit.c (treesit_sync_visible_region): Initialize
visible_beg/end when tree is NULL.

src/treesit.c

index d18e77a35317c7130c8d4eb05a80d0b3b92d648f..c910aea1da2b8fdb84cf209d391fc2ce16bd345b 100644 (file)
@@ -782,13 +782,13 @@ treesit_record_change (ptrdiff_t start_byte, ptrdiff_t old_end_byte,
    matches that of the buffer, and update visible_beg/end.
 
    That is, the whole purpose of visible_beg/end (and
-   treesit_record_change and treesit_sync_visible_region) is to
-   update the tree (by ts_tree_edit).  So if the tree is NULL, we
-   don't update the tree and there is no need to keep tracking of
-   them.  Only when we already have a tree, do we need to keep track
-   of position changes and update it correctly, so it can be feed into
-   ts_parser_parse as the old tree, so that tree-sitter only parses
-   the changed part (aka incremental).
+   treesit_record_change and treesit_sync_visible_region) is to update
+   the tree (by ts_tree_edit).  So if the tree is NULL,
+   visible_beg/end are considered uninitialized.  Only when we already
+   have a tree, do we need to keep track of position changes and
+   update it correctly, so it can be feed into ts_parser_parse as the
+   old tree, so that tree-sitter only parses the changed part (aka
+   incremental).
 
    In a nutshell, tree-sitter incremental parsing in Emacs looks like:
 
@@ -815,11 +815,17 @@ static void
 treesit_sync_visible_region (Lisp_Object parser)
 {
   TSTree *tree = XTS_PARSER (parser)->tree;
+  struct buffer *buffer = XBUFFER (XTS_PARSER (parser)->buffer);
 
+  /* If we are setting visible_beg/end for the first time, we can skip
+  the offset acrobatics and updating the tree below.  */
   if (tree == NULL)
-    return;
+    {
+      XTS_PARSER (parser)->visible_beg = BUF_BEGV_BYTE (buffer);
+      XTS_PARSER (parser)->visible_end = BUF_ZV_BYTE (buffer);
+      return;
+    }
 
-  struct buffer *buffer = XBUFFER (XTS_PARSER (parser)->buffer);
   ptrdiff_t visible_beg = XTS_PARSER (parser)->visible_beg;
   ptrdiff_t visible_end = XTS_PARSER (parser)->visible_end;
   eassert (0 <= visible_beg);