tree-sitter-delphi13 1.2.1 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +53 -9
- package/grammar.js +23 -1
- package/package.json +7 -2
- package/prebuilds/win32-x64/tree-sitter-delphi13.node +0 -0
- package/queries/folds.scm +56 -0
- package/queries/highlights.scm +328 -0
- package/queries/indents.scm +58 -0
- package/queries/injections.scm +34 -0
- package/queries/outline.scm +35 -0
- package/queries/tags.scm +183 -0
- package/src/grammar.json +72 -2
- package/src/parser.c +346693 -345532
- package/tree-sitter-delphi13.wasm +0 -0
- package/tree-sitter.json +39 -0
package/README.md
CHANGED
|
@@ -2,15 +2,22 @@
|
|
|
2
2
|
|
|
3
3
|
[](https://www.npmjs.com/package/tree-sitter-delphi13)
|
|
4
4
|
[](LICENSE)
|
|
5
|
+
[](CORPUS-CEILING-REPORT.md)
|
|
6
|
+
[](CORPUS-CEILING-REPORT.md)
|
|
5
7
|
|
|
6
8
|
Tree-sitter grammar pipeline focused on **Delphi 13 (RAD Studio 37.0 / Florence)** and the surrounding modern Delphi ecosystem.
|
|
7
9
|
|
|
8
|
-
**v1.2.
|
|
9
|
-
on
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
remains is individually diagnosed, dcc32-cross-checked, and *supposed*
|
|
13
|
-
(see [CORPUS-CEILING-REPORT.md](CORPUS-CEILING-REPORT.md)).
|
|
10
|
+
**v1.2.2: 100.000% pass rate on compilable Delphi 13** (zero ERROR nodes), measured
|
|
11
|
+
on a corpus spanning the RAD Studio 13 RTL/VCL (including `System.pas`), DevExpress,
|
|
12
|
+
Spring4D, EurekaLog, Indy, FireDAC, AsyncPro/Orpheus, **JCL/JVCL (JEDI)**, mORMot-era
|
|
13
|
+
community code and a full production application — 23,385 deduplicated files. Every
|
|
14
|
+
failure that remains is individually diagnosed, dcc32-cross-checked, and *supposed*
|
|
15
|
+
to fail (see [CORPUS-CEILING-REPORT.md](CORPUS-CEILING-REPORT.md)).
|
|
16
|
+
|
|
17
|
+
v1.2.2 added the JEDI (JCL + JVCL) libraries to the corpus and closed the three
|
|
18
|
+
valid-Delphi-13 gaps they surfaced: a subrange bound that is a nested constant-expr
|
|
19
|
+
call (`2..Succ(High(T))`), the `at` soft keyword as an `inherited` method name
|
|
20
|
+
(`inherited At(...)`), and `Operator` used as a record/class field name.
|
|
14
21
|
|
|
15
22
|
| measurement basis | pass rate |
|
|
16
23
|
|---|---|
|
|
@@ -31,9 +38,9 @@ watchlist).
|
|
|
31
38
|
|---|---|
|
|
32
39
|
| **`tree-sitter-delphi13`** *(this directory)* | Master grammar — Delphi-13 syntax, all proven fixes from upstream merged + new extensions. Self-contained "THEN-wins" parser (98.6% raw on its own). |
|
|
33
40
|
| **[`tree-sitter-delphi13-pure`](pure/)** | Simpler sub-grammar that drops `pp_*` tokens entirely. Expects preprocessor-resolved source. |
|
|
34
|
-
| **[`delphi13-preprocessor`](preprocessor/)** | Standalone JavaScript library that resolves `{$IFDEF}` / `{$IF}` / `{$DEFINE}` / `{$I X.inc}` directives as a text transformation. |
|
|
41
|
+
| **[`delphi13-preprocessor`](preprocessor/)** | Standalone JavaScript library that resolves `{$IFDEF}` / `{$IF}` / `{$DEFINE}` / `{$I X.inc}` directives as a text transformation. The **canonical** preprocessor is now a pure-Delphi port of this library (shipping inside drag-lint); this JS package remains the byte-for-byte oracle and the drop-in choice for JavaScript consumers. |
|
|
35
42
|
|
|
36
|
-
The full pipeline `preprocessor → pure → AST` is what reaches **
|
|
43
|
+
The full pipeline `preprocessor → pure → AST` is what reaches **100.000%** on valid
|
|
37
44
|
Delphi 13. Use the master grammar alone (98.6% raw) if you don't need
|
|
38
45
|
conditional-compilation awareness; use the pipeline if you do.
|
|
39
46
|
|
|
@@ -134,11 +141,48 @@ npm install --ignore-scripts
|
|
|
134
141
|
node-gyp rebuild
|
|
135
142
|
```
|
|
136
143
|
|
|
144
|
+
## WASM and editor queries
|
|
145
|
+
|
|
146
|
+
Each package ships a prebuilt **tree-sitter ABI 14** `.wasm` alongside the native
|
|
147
|
+
binding, so browser and Electron hosts (`web-tree-sitter`) can load the parser with
|
|
148
|
+
no toolchain:
|
|
149
|
+
|
|
150
|
+
```js
|
|
151
|
+
const Parser = require('web-tree-sitter');
|
|
152
|
+
await Parser.init();
|
|
153
|
+
const L = await Parser.Language.load('node_modules/tree-sitter-delphi13/tree-sitter-delphi13.wasm');
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
Rebuilding it needs a pinned Emscripten -- see [WASM-BUILD.md](WASM-BUILD.md).
|
|
157
|
+
|
|
158
|
+
The full standard query set lives in `queries/`:
|
|
159
|
+
|
|
160
|
+
| File | Used for |
|
|
161
|
+
|---|---|
|
|
162
|
+
| `highlights.scm` | syntax highlighting |
|
|
163
|
+
| `injections.scm` | SQL-in-string and inline `asm` embedding |
|
|
164
|
+
| `indents.scm` | auto-indent |
|
|
165
|
+
| `folds.scm` | code folding |
|
|
166
|
+
| `outline.scm` | outline / breadcrumb panel |
|
|
167
|
+
| `tags.scm` | symbol extraction for codebase indexers (GitHub, Cursor, Sourcegraph) |
|
|
168
|
+
|
|
169
|
+
Validate them after any edit -- against the **WASM**, because the native CLI and the
|
|
170
|
+
WASM host do not run the same regex engine and a query can compile in one and throw
|
|
171
|
+
in the other:
|
|
172
|
+
|
|
173
|
+
```sh
|
|
174
|
+
npm run build-wasm
|
|
175
|
+
npm run validate-queries
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
See [DISTRIBUTION.md](DISTRIBUTION.md) for the state of editor integrations.
|
|
137
179
|
## Known limitations
|
|
138
180
|
|
|
139
181
|
- **Inline `asm` blocks** treated as opaque text by design. Not tree-sitter-asm.
|
|
140
182
|
- **`{$IF declared(SymName)}`** always evaluates to `false` — no symbol table. ~10 corpus files use this. A lightweight symbol pre-scan would address most cases.
|
|
141
|
-
- **Include
|
|
183
|
+
- **Include resolution** is nearest-first (same directory, its subdirectories, then
|
|
184
|
+
up to 3 parent levels with their subdirectories — v1.1.0 of the preprocessor).
|
|
185
|
+
Arbitrary project search paths still need the `includePaths` option.
|
|
142
186
|
- **FreePascal-specific extensions** (operator overloading variants, `{$mode ObjFPC}` directives, macOS PasCocoa namespaces) are not covered. A separate `tree-sitter-delphi-plus-fp` repo is planned.
|
|
143
187
|
|
|
144
188
|
## Acknowledgements
|
package/grammar.js
CHANGED
|
@@ -756,7 +756,16 @@ module.exports = grammar({
|
|
|
756
756
|
field('body', choice(tr($, 'block'), tr($, 'asm'))),
|
|
757
757
|
),
|
|
758
758
|
|
|
759
|
-
inherited: $ => prec.right(seq($.kInherited, optional(
|
|
759
|
+
inherited: $ => prec.right(seq($.kInherited, optional(choice(
|
|
760
|
+
$.identifier,
|
|
761
|
+
// Soft keyword `at` (the raise-with-address `raise E at Addr`
|
|
762
|
+
// keyword) used as an INHERITED method name: `inherited At(Offset)`
|
|
763
|
+
// (JCL JclCLR.pas). `At` already works as a plain/dotted call and a
|
|
764
|
+
// field name; only the inherited slot lost it to the kAtWord token.
|
|
765
|
+
// Aliased to identifier so the call-args attach exactly as for
|
|
766
|
+
// `inherited Foo(x)`. Narrow — only the corpus-confirmed kAtWord.
|
|
767
|
+
alias($.kAtWord, $.identifier),
|
|
768
|
+
)))),
|
|
760
769
|
|
|
761
770
|
exprDot: $ => choice(
|
|
762
771
|
op.infix(5, $._ref, $.kDot, $._ref),
|
|
@@ -1288,6 +1297,13 @@ module.exports = grammar({
|
|
|
1288
1297
|
// conflicts with typerefDot in this position.)
|
|
1289
1298
|
seq($.identifier, '.', $.identifier),
|
|
1290
1299
|
seq($.identifier, '(', $.identifier, ')'),
|
|
1300
|
+
// Iter 2026-07-17: nested const-expr call bound —
|
|
1301
|
+
// `2 .. Succ(High(TDigitValue))` (JCL JclSysUtils TNumericSystemBase).
|
|
1302
|
+
// dcc accepts any constant ordinal expression as a bound; the grammar
|
|
1303
|
+
// stays with the narrow corpus-driven enumeration (a wide `_expr`
|
|
1304
|
+
// bound blows the parser tables, see above), adding just the one
|
|
1305
|
+
// real shape: `Ident( Ident(Ident) )`, one level of call nesting.
|
|
1306
|
+
seq($.identifier, '(', seq($.identifier, '(', $.identifier, ')'), ')'),
|
|
1291
1307
|
// `hid - 1`, `MaxN + 2` — narrow `identifier OP integer` form for
|
|
1292
1308
|
// real-corpus patterns like `TNmbrRange = 0 .. hid - 1;`.
|
|
1293
1309
|
// Kept narrow (no full _expr) to avoid the conflict cascade hit
|
|
@@ -1663,6 +1679,12 @@ module.exports = grammar({
|
|
|
1663
1679
|
field('name', delimited1(choice(
|
|
1664
1680
|
$.identifier,
|
|
1665
1681
|
alias($.kRegister, $.identifier),
|
|
1682
|
+
// Iter 2026-07-17: `Operator` as a FIELD NAME
|
|
1683
|
+
// (`Operator: TJvXmlSQLOperator;` — JVCL JvXmlDatabase). The
|
|
1684
|
+
// `operator` token otherwise starts _declOperator; GLR splits
|
|
1685
|
+
// on the follow token (`:` -> field, operator-name -> class
|
|
1686
|
+
// operator). Same narrow one-keyword alias as kRegister above.
|
|
1687
|
+
alias($.kOperator, $.identifier),
|
|
1666
1688
|
))),
|
|
1667
1689
|
':',
|
|
1668
1690
|
// Iter 2026-07-06: a record/class field type may be a subrange, same
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "tree-sitter-delphi13",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "Tree-sitter grammar focused on Delphi 13 (RAD Studio 37.0)",
|
|
5
5
|
"main": "bindings/node",
|
|
6
6
|
"types": "bindings/node",
|
|
@@ -23,21 +23,26 @@
|
|
|
23
23
|
"license": "MIT",
|
|
24
24
|
"devDependencies": {
|
|
25
25
|
"prebuildify": "^6.0.1",
|
|
26
|
+
"web-tree-sitter": "^0.24.7",
|
|
26
27
|
"tree-sitter-cli": "^0.24.5"
|
|
27
28
|
},
|
|
28
29
|
"scripts": {
|
|
29
30
|
"build": "tree-sitter generate && node-gyp build",
|
|
31
|
+
"build-wasm": "tree-sitter build --wasm -o tree-sitter-delphi13.wasm .",
|
|
30
32
|
"test": "tree-sitter test && tree-sitter parse examples/* --quiet --time",
|
|
31
33
|
"install": "node-gyp-build",
|
|
34
|
+
"validate-queries": "node tools/validate-queries.js",
|
|
32
35
|
"prebuildify": "prebuildify --napi --strip"
|
|
33
36
|
},
|
|
34
37
|
"files": [
|
|
35
38
|
"grammar.js",
|
|
36
39
|
"binding.gyp",
|
|
40
|
+
"tree-sitter.json",
|
|
37
41
|
"prebuilds/**",
|
|
38
42
|
"bindings/node/*",
|
|
39
43
|
"queries/*",
|
|
40
|
-
"src/**"
|
|
44
|
+
"src/**",
|
|
45
|
+
"tree-sitter-delphi13.wasm"
|
|
41
46
|
],
|
|
42
47
|
"dependencies": {
|
|
43
48
|
"node-gyp-build": "^4.8.4"
|
|
Binary file
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
; folds.scm -- tree-sitter-delphi13
|
|
2
|
+
;
|
|
3
|
+
; Nodes that may be collapsed to a single line. The `@fold` capture is the
|
|
4
|
+
; convention read by nvim-treesitter, Helix and Zed; editors that compute folds
|
|
5
|
+
; from the syntax tree use the captured node's span as the foldable region.
|
|
6
|
+
;
|
|
7
|
+
; Rule of thumb: fold anything with its own `end`, plus the declaration groups
|
|
8
|
+
; that routinely run to hundreds of lines in real Delphi units (a `uses` clause,
|
|
9
|
+
; a `type` section, a visibility section of a large form class).
|
|
10
|
+
|
|
11
|
+
[
|
|
12
|
+
; --- module structure ---
|
|
13
|
+
(interface)
|
|
14
|
+
(implementation)
|
|
15
|
+
(initialization)
|
|
16
|
+
(finalization)
|
|
17
|
+
|
|
18
|
+
; --- declaration groups ---
|
|
19
|
+
(declUses)
|
|
20
|
+
(declTypes)
|
|
21
|
+
(declConsts)
|
|
22
|
+
(declVars)
|
|
23
|
+
(declExports)
|
|
24
|
+
(declLabels)
|
|
25
|
+
(declArgs)
|
|
26
|
+
|
|
27
|
+
; --- type bodies ---
|
|
28
|
+
(declClass)
|
|
29
|
+
(declIntf)
|
|
30
|
+
(declHelper)
|
|
31
|
+
(declEnum)
|
|
32
|
+
(declSection)
|
|
33
|
+
(declVariant)
|
|
34
|
+
|
|
35
|
+
; --- routines ---
|
|
36
|
+
(defProc)
|
|
37
|
+
(block)
|
|
38
|
+
(asm)
|
|
39
|
+
|
|
40
|
+
; --- statements with an `end` / closing keyword ---
|
|
41
|
+
(try)
|
|
42
|
+
(exceptionHandler)
|
|
43
|
+
(case)
|
|
44
|
+
(caseCase)
|
|
45
|
+
(if)
|
|
46
|
+
(ifElse)
|
|
47
|
+
(while)
|
|
48
|
+
(for)
|
|
49
|
+
(foreach)
|
|
50
|
+
(repeat)
|
|
51
|
+
(with)
|
|
52
|
+
(lambda)
|
|
53
|
+
|
|
54
|
+
; --- conditional compilation ---
|
|
55
|
+
(pp_block)
|
|
56
|
+
] @fold
|
|
@@ -0,0 +1,328 @@
|
|
|
1
|
+
; highlights.scm -- tree-sitter-delphi13
|
|
2
|
+
;
|
|
3
|
+
; Syntax highlighting queries for Delphi 13 (Object Pascal).
|
|
4
|
+
; Consumed by Zed, Neovim, Helix and anything else using tree-sitter-highlight.
|
|
5
|
+
;
|
|
6
|
+
; Capture names follow the common tree-sitter highlight vocabulary that Zed's
|
|
7
|
+
; theme syntax keys map directly (keyword, type, function, string, number,
|
|
8
|
+
; boolean, comment, operator, property, attribute, preproc, punctuation.*).
|
|
9
|
+
;
|
|
10
|
+
; NOTE ON ORDER: tree-sitter-highlight resolves the FIRST matching pattern for a
|
|
11
|
+
; node, so specific patterns are listed before general ones.
|
|
12
|
+
|
|
13
|
+
; ---------------------------------------------------------------------------
|
|
14
|
+
; Comments
|
|
15
|
+
; ---------------------------------------------------------------------------
|
|
16
|
+
|
|
17
|
+
(comment) @comment
|
|
18
|
+
|
|
19
|
+
; ---------------------------------------------------------------------------
|
|
20
|
+
; Preprocessor / conditional compilation {$IFDEF} {$R} {$I} ...
|
|
21
|
+
; ---------------------------------------------------------------------------
|
|
22
|
+
|
|
23
|
+
(pp) @preproc
|
|
24
|
+
(pp_open) @preproc
|
|
25
|
+
(pp_else_tail) @preproc
|
|
26
|
+
(pp_end_only) @preproc
|
|
27
|
+
|
|
28
|
+
; ---------------------------------------------------------------------------
|
|
29
|
+
; Literals
|
|
30
|
+
; ---------------------------------------------------------------------------
|
|
31
|
+
|
|
32
|
+
(literalString) @string
|
|
33
|
+
(literalChar) @string.special
|
|
34
|
+
(char_literal) @string.special
|
|
35
|
+
(literalNumber) @number
|
|
36
|
+
(trailing_dot_float) @number
|
|
37
|
+
(guid) @string.special
|
|
38
|
+
|
|
39
|
+
[
|
|
40
|
+
(kTrue)
|
|
41
|
+
(kFalse)
|
|
42
|
+
] @boolean
|
|
43
|
+
|
|
44
|
+
(kNil) @constant
|
|
45
|
+
|
|
46
|
+
; ---------------------------------------------------------------------------
|
|
47
|
+
; Attributes -- [Weak], [Ref], custom RTTI attributes
|
|
48
|
+
; ---------------------------------------------------------------------------
|
|
49
|
+
|
|
50
|
+
(rttiAttributes) @attribute
|
|
51
|
+
(declAssemblyAttribute) @attribute
|
|
52
|
+
|
|
53
|
+
; ---------------------------------------------------------------------------
|
|
54
|
+
; Module structure
|
|
55
|
+
; ---------------------------------------------------------------------------
|
|
56
|
+
|
|
57
|
+
[
|
|
58
|
+
(kUnit)
|
|
59
|
+
(kProgram)
|
|
60
|
+
(kLibrary)
|
|
61
|
+
(kPackage)
|
|
62
|
+
(kInterface)
|
|
63
|
+
(kImplementation)
|
|
64
|
+
(kInitialization)
|
|
65
|
+
(kFinalization)
|
|
66
|
+
(kUses)
|
|
67
|
+
(kExports)
|
|
68
|
+
(kContains)
|
|
69
|
+
(kRequires)
|
|
70
|
+
] @keyword
|
|
71
|
+
|
|
72
|
+
(moduleName) @type
|
|
73
|
+
|
|
74
|
+
; ---------------------------------------------------------------------------
|
|
75
|
+
; Declaration introducers
|
|
76
|
+
; ---------------------------------------------------------------------------
|
|
77
|
+
|
|
78
|
+
[
|
|
79
|
+
(kType)
|
|
80
|
+
(kVar)
|
|
81
|
+
(kConst)
|
|
82
|
+
(kThreadvar)
|
|
83
|
+
(kResourcestring)
|
|
84
|
+
(kLabel)
|
|
85
|
+
(kAbsolute)
|
|
86
|
+
] @keyword
|
|
87
|
+
|
|
88
|
+
; ---------------------------------------------------------------------------
|
|
89
|
+
; Routines
|
|
90
|
+
; ---------------------------------------------------------------------------
|
|
91
|
+
|
|
92
|
+
[
|
|
93
|
+
(kProcedure)
|
|
94
|
+
(kFunction)
|
|
95
|
+
(kConstructor)
|
|
96
|
+
(kDestructor)
|
|
97
|
+
(kOperator)
|
|
98
|
+
(kProperty)
|
|
99
|
+
(kRead)
|
|
100
|
+
(kWrite)
|
|
101
|
+
(kReadonly)
|
|
102
|
+
(kWriteonly)
|
|
103
|
+
(kStored)
|
|
104
|
+
(kDefault)
|
|
105
|
+
(kNodefault)
|
|
106
|
+
(kIndex)
|
|
107
|
+
(kImplements)
|
|
108
|
+
] @keyword
|
|
109
|
+
|
|
110
|
+
; ---------------------------------------------------------------------------
|
|
111
|
+
; Type-forming keywords
|
|
112
|
+
; ---------------------------------------------------------------------------
|
|
113
|
+
|
|
114
|
+
[
|
|
115
|
+
(kClass)
|
|
116
|
+
(kRecord)
|
|
117
|
+
(kObject)
|
|
118
|
+
(kArray)
|
|
119
|
+
(kSet)
|
|
120
|
+
(kFile)
|
|
121
|
+
(kString)
|
|
122
|
+
(kHelper)
|
|
123
|
+
(kDispInterface)
|
|
124
|
+
(kPacked)
|
|
125
|
+
(kGeneric)
|
|
126
|
+
(kReference)
|
|
127
|
+
(kOf)
|
|
128
|
+
] @keyword
|
|
129
|
+
|
|
130
|
+
; ---------------------------------------------------------------------------
|
|
131
|
+
; Visibility
|
|
132
|
+
; ---------------------------------------------------------------------------
|
|
133
|
+
|
|
134
|
+
[
|
|
135
|
+
(kPrivate)
|
|
136
|
+
(kProtected)
|
|
137
|
+
(kPublic)
|
|
138
|
+
(kPublished)
|
|
139
|
+
(kStrict)
|
|
140
|
+
] @keyword
|
|
141
|
+
|
|
142
|
+
; ---------------------------------------------------------------------------
|
|
143
|
+
; Control flow
|
|
144
|
+
; ---------------------------------------------------------------------------
|
|
145
|
+
|
|
146
|
+
[
|
|
147
|
+
(kBegin)
|
|
148
|
+
(kEnd)
|
|
149
|
+
(kEndDot)
|
|
150
|
+
(kIf)
|
|
151
|
+
(kThen)
|
|
152
|
+
(kElse)
|
|
153
|
+
(kCase)
|
|
154
|
+
(kFor)
|
|
155
|
+
(kTo)
|
|
156
|
+
(kDownto)
|
|
157
|
+
(kDo)
|
|
158
|
+
(kWhile)
|
|
159
|
+
(kRepeat)
|
|
160
|
+
(kUntil)
|
|
161
|
+
(kWith)
|
|
162
|
+
(kGoto)
|
|
163
|
+
(kTry)
|
|
164
|
+
(kExcept)
|
|
165
|
+
(kFinally)
|
|
166
|
+
(kRaise)
|
|
167
|
+
(kOn)
|
|
168
|
+
(kInherited)
|
|
169
|
+
(kAsm)
|
|
170
|
+
(kAssembler)
|
|
171
|
+
] @keyword
|
|
172
|
+
|
|
173
|
+
; ---------------------------------------------------------------------------
|
|
174
|
+
; Routine directives / modifiers
|
|
175
|
+
; ---------------------------------------------------------------------------
|
|
176
|
+
|
|
177
|
+
[
|
|
178
|
+
(kVirtual)
|
|
179
|
+
(kOverride)
|
|
180
|
+
(kAbstract)
|
|
181
|
+
(kSealed)
|
|
182
|
+
(kFinal)
|
|
183
|
+
(kStatic)
|
|
184
|
+
(kOverload)
|
|
185
|
+
(kReintroduce)
|
|
186
|
+
(kInline)
|
|
187
|
+
(kForward)
|
|
188
|
+
(kExternal)
|
|
189
|
+
(kDynamic)
|
|
190
|
+
(kDelayed)
|
|
191
|
+
(kDispId)
|
|
192
|
+
(kMessage)
|
|
193
|
+
(kName)
|
|
194
|
+
(kDeprecated)
|
|
195
|
+
(kExperimental)
|
|
196
|
+
(kPlatform)
|
|
197
|
+
(kNoreturn)
|
|
198
|
+
(kUnsafe)
|
|
199
|
+
(kVarargs)
|
|
200
|
+
(kLocal)
|
|
201
|
+
(kAlign)
|
|
202
|
+
(kDependency)
|
|
203
|
+
(kOut)
|
|
204
|
+
(kConstref)
|
|
205
|
+
] @keyword
|
|
206
|
+
|
|
207
|
+
; ---------------------------------------------------------------------------
|
|
208
|
+
; Calling conventions
|
|
209
|
+
; ---------------------------------------------------------------------------
|
|
210
|
+
|
|
211
|
+
[
|
|
212
|
+
(kCdecl)
|
|
213
|
+
(kStdcall)
|
|
214
|
+
(kSafecall)
|
|
215
|
+
(kRegister)
|
|
216
|
+
(kPascal)
|
|
217
|
+
(kWinapi)
|
|
218
|
+
(kFar)
|
|
219
|
+
(kNear)
|
|
220
|
+
(kExport)
|
|
221
|
+
(kInterrupt)
|
|
222
|
+
] @keyword
|
|
223
|
+
|
|
224
|
+
; ---------------------------------------------------------------------------
|
|
225
|
+
; Operator keywords
|
|
226
|
+
; ---------------------------------------------------------------------------
|
|
227
|
+
|
|
228
|
+
[
|
|
229
|
+
(kAnd)
|
|
230
|
+
(kOr)
|
|
231
|
+
(kNot)
|
|
232
|
+
(kXor)
|
|
233
|
+
(kDiv)
|
|
234
|
+
(kMod)
|
|
235
|
+
(kShl)
|
|
236
|
+
(kShr)
|
|
237
|
+
(kIn)
|
|
238
|
+
(kIs)
|
|
239
|
+
(kAs)
|
|
240
|
+
(kAt)
|
|
241
|
+
] @operator
|
|
242
|
+
|
|
243
|
+
; ---------------------------------------------------------------------------
|
|
244
|
+
; Symbolic operators
|
|
245
|
+
; ---------------------------------------------------------------------------
|
|
246
|
+
|
|
247
|
+
[
|
|
248
|
+
(kAssign)
|
|
249
|
+
(kAssignAdd)
|
|
250
|
+
(kAssignSub)
|
|
251
|
+
(kAssignMul)
|
|
252
|
+
(kAssignDiv)
|
|
253
|
+
(kEq)
|
|
254
|
+
(kNeq)
|
|
255
|
+
(kLt)
|
|
256
|
+
(kLte)
|
|
257
|
+
(kGt)
|
|
258
|
+
(kGte)
|
|
259
|
+
(kAdd)
|
|
260
|
+
(kSub)
|
|
261
|
+
(kMul)
|
|
262
|
+
(kFdiv)
|
|
263
|
+
(kHat)
|
|
264
|
+
(kAtWord)
|
|
265
|
+
] @operator
|
|
266
|
+
|
|
267
|
+
(kDot) @punctuation.delimiter
|
|
268
|
+
|
|
269
|
+
; ---------------------------------------------------------------------------
|
|
270
|
+
; Types
|
|
271
|
+
; ---------------------------------------------------------------------------
|
|
272
|
+
|
|
273
|
+
(typeref) @type
|
|
274
|
+
(typerefDot) @type
|
|
275
|
+
(typerefPtr) @type
|
|
276
|
+
(typerefTpl) @type
|
|
277
|
+
(genericTpl) @type
|
|
278
|
+
(genericDot) @type
|
|
279
|
+
(declEnumValue) @constant
|
|
280
|
+
|
|
281
|
+
; ---------------------------------------------------------------------------
|
|
282
|
+
; Labels
|
|
283
|
+
; ---------------------------------------------------------------------------
|
|
284
|
+
|
|
285
|
+
(label) @label
|
|
286
|
+
(declLabel) @label
|
|
287
|
+
(caseLabel) @label
|
|
288
|
+
|
|
289
|
+
; ---------------------------------------------------------------------------
|
|
290
|
+
; Punctuation
|
|
291
|
+
; ---------------------------------------------------------------------------
|
|
292
|
+
|
|
293
|
+
[
|
|
294
|
+
"("
|
|
295
|
+
")"
|
|
296
|
+
"["
|
|
297
|
+
"]"
|
|
298
|
+
] @punctuation.bracket
|
|
299
|
+
|
|
300
|
+
[
|
|
301
|
+
","
|
|
302
|
+
";"
|
|
303
|
+
":"
|
|
304
|
+
"."
|
|
305
|
+
".."
|
|
306
|
+
] @punctuation.delimiter
|
|
307
|
+
|
|
308
|
+
; ---------------------------------------------------------------------------
|
|
309
|
+
; Declaration names -- more specific than the bare identifier rule below, so
|
|
310
|
+
; they must be listed first (tree-sitter-highlight takes the first match).
|
|
311
|
+
; ---------------------------------------------------------------------------
|
|
312
|
+
|
|
313
|
+
(declProc name: (identifier) @function)
|
|
314
|
+
(declProc name: (genericDot) @function)
|
|
315
|
+
(declProc name: (genericTpl) @function)
|
|
316
|
+
|
|
317
|
+
(declType name: (identifier) @type)
|
|
318
|
+
(declType name: (genericDot) @type)
|
|
319
|
+
(declType name: (genericTpl) @type)
|
|
320
|
+
|
|
321
|
+
(declProp name: (identifier) @property)
|
|
322
|
+
(declField name: (identifier) @property)
|
|
323
|
+
|
|
324
|
+
; ---------------------------------------------------------------------------
|
|
325
|
+
; Identifiers -- least specific, listed last
|
|
326
|
+
; ---------------------------------------------------------------------------
|
|
327
|
+
|
|
328
|
+
(identifier) @variable
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
; indents.scm -- tree-sitter-delphi13
|
|
2
|
+
;
|
|
3
|
+
; Auto-indent behaviour. This is the query users actually *feel*: it decides
|
|
4
|
+
; where the caret lands after `begin`, `case`, `try`, `record`, `class`.
|
|
5
|
+
;
|
|
6
|
+
; Convention (matches Zed's own language extensions):
|
|
7
|
+
; @indent the node whose body should be indented
|
|
8
|
+
; @start the token that opens the indented region
|
|
9
|
+
; @end the token that closes it (dedents the line it appears on)
|
|
10
|
+
|
|
11
|
+
; --- begin ... end -------------------------------------------------------
|
|
12
|
+
(block
|
|
13
|
+
(kBegin) @start
|
|
14
|
+
(kEnd)? @end) @indent
|
|
15
|
+
|
|
16
|
+
; --- try ... except / finally ... end ------------------------------------
|
|
17
|
+
(try
|
|
18
|
+
(kTry) @start
|
|
19
|
+
(kEnd)? @end) @indent
|
|
20
|
+
|
|
21
|
+
; --- case ... of ... end -------------------------------------------------
|
|
22
|
+
(case
|
|
23
|
+
(kCase) @start
|
|
24
|
+
(kEnd)? @end) @indent
|
|
25
|
+
|
|
26
|
+
; --- record ... end ------------------------------------------------------
|
|
27
|
+
(declClass
|
|
28
|
+
(kEnd)? @end) @indent
|
|
29
|
+
|
|
30
|
+
(declIntf
|
|
31
|
+
(kEnd)? @end) @indent
|
|
32
|
+
|
|
33
|
+
(declHelper
|
|
34
|
+
(kEnd)? @end) @indent
|
|
35
|
+
|
|
36
|
+
; --- asm ... end ---------------------------------------------------------
|
|
37
|
+
(asm
|
|
38
|
+
(kAsm) @start
|
|
39
|
+
(kEnd)? @end) @indent
|
|
40
|
+
|
|
41
|
+
; --- repeat ... until ----------------------------------------------------
|
|
42
|
+
(repeat
|
|
43
|
+
(kRepeat) @start
|
|
44
|
+
(kUntil)? @end) @indent
|
|
45
|
+
|
|
46
|
+
; --- declaration sections: the names under type/var/const line up --------
|
|
47
|
+
(declTypes) @indent
|
|
48
|
+
(declVars) @indent
|
|
49
|
+
(declConsts) @indent
|
|
50
|
+
|
|
51
|
+
; --- bracketed continuations --------------------------------------------
|
|
52
|
+
(exprParens
|
|
53
|
+
"(" @start
|
|
54
|
+
")" @end) @indent
|
|
55
|
+
|
|
56
|
+
(declArgs
|
|
57
|
+
"(" @start
|
|
58
|
+
")" @end) @indent
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
; injections.scm -- tree-sitter-delphi13
|
|
2
|
+
;
|
|
3
|
+
; Embeds other languages inside Delphi source.
|
|
4
|
+
;
|
|
5
|
+
; SQL-in-string is the high-value case for this codebase: FireDAC/Firebird
|
|
6
|
+
; projects carry a lot of SQL in string literals and assembling it by hand is
|
|
7
|
+
; where the bugs live. Highlighting it as SQL makes malformed statements
|
|
8
|
+
; visible without running them.
|
|
9
|
+
;
|
|
10
|
+
; Matching is deliberately conservative -- anchored at the start of the literal
|
|
11
|
+
; on a leading SQL verb. A loose pattern would paint ordinary prose strings as
|
|
12
|
+
; SQL, which is worse than no injection at all: it makes correct code look
|
|
13
|
+
; broken.
|
|
14
|
+
|
|
15
|
+
; A LEADING VERB ALONE IS NOT ENOUGH. `'Select a file to continue'` starts with
|
|
16
|
+
; "Select " and is obviously prose -- an early draft of this query painted it as
|
|
17
|
+
; SQL. Every branch below therefore demands a PAIRED keyword (SELECT..FROM,
|
|
18
|
+
; UPDATE..SET, INSERT INTO, ...), which prose effectively never satisfies.
|
|
19
|
+
;
|
|
20
|
+
; NO INLINE `(?i)` FLAG -- THIS IS LOAD-BEARING, DO NOT "SIMPLIFY" IT.
|
|
21
|
+
; Native tree-sitter matches #match? with the Rust regex crate, which supports
|
|
22
|
+
; the inline `(?i)` group. web-tree-sitter (the WASM build that VS Code, Cursor
|
|
23
|
+
; and every browser host use) hands the pattern to JavaScript's RegExp, which
|
|
24
|
+
; rejects `(?i)` outright with "Invalid group" -- and a query that throws on
|
|
25
|
+
; compile takes the WHOLE injections file down with it, silently, in exactly
|
|
26
|
+
; the editors this grammar is meant to ship in. Case-insensitivity is therefore
|
|
27
|
+
; spelled out as [Ss][Ee][Ll]... character classes, which both engines accept.
|
|
28
|
+
((literalString) @injection.content
|
|
29
|
+
(#match? @injection.content "^'\\s*([Ss][Ee][Ll][Ee][Cc][Tt]\\b[\\s\\S]*\\b[Ff][Rr][Oo][Mm]\\b|[Ii][Nn][Ss][Ee][Rr][Tt]\\s+[Ii][Nn][Tt][Oo]\\b|[Uu][Pp][Dd][Aa][Tt][Ee]\\b[\\s\\S]*\\b[Ss][Ee][Tt]\\b|[Dd][Ee][Ll][Ee][Tt][Ee]\\s+[Ff][Rr][Oo][Mm]\\b|[Cc][Rr][Ee][Aa][Tt][Ee]\\s+([Oo][Rr]\\s+[Aa][Ll][Tt][Ee][Rr]\\s+)?([Tt][Aa][Bb][Ll][Ee]|[Vv][Ii][Ee][Ww]|[Ii][Nn][Dd][Ee][Xx]|[Pp][Rr][Oo][Cc][Ee][Dd][Uu][Rr][Ee]|[Tt][Rr][Ii][Gg][Gg][Ee][Rr]|[Gg][Ee][Nn][Ee][Rr][Aa][Tt][Oo][Rr]|[Ss][Ee][Qq][Uu][Ee][Nn][Cc][Ee]|[Dd][Oo][Mm][Aa][Ii][Nn]|[Ee][Xx][Cc][Ee][Pp][Tt][Ii][Oo][Nn])\\b|[Aa][Ll][Tt][Ee][Rr]\\s+([Tt][Aa][Bb][Ll][Ee]|[Vv][Ii][Ee][Ww]|[Ii][Nn][Dd][Ee][Xx]|[Pp][Rr][Oo][Cc][Ee][Dd][Uu][Rr][Ee]|[Tt][Rr][Ii][Gg][Gg][Ee][Rr]|[Dd][Aa][Tt][Aa][Bb][Aa][Ss][Ee])\\b|[Dd][Rr][Oo][Pp]\\s+([Tt][Aa][Bb][Ll][Ee]|[Vv][Ii][Ee][Ww]|[Ii][Nn][Dd][Ee][Xx]|[Pp][Rr][Oo][Cc][Ee][Dd][Uu][Rr][Ee]|[Tt][Rr][Ii][Gg][Gg][Ee][Rr]|[Gg][Ee][Nn][Ee][Rr][Aa][Tt][Oo][Rr]|[Ss][Ee][Qq][Uu][Ee][Nn][Cc][Ee]|[Dd][Oo][Mm][Aa][Ii][Nn]|[Ee][Xx][Cc][Ee][Pp][Tt][Ii][Oo][Nn])\\b|[Ee][Xx][Ee][Cc][Uu][Tt][Ee]\\s+([Pp][Rr][Oo][Cc][Ee][Dd][Uu][Rr][Ee]|[Bb][Ll][Oo][Cc][Kk]|[Ss][Tt][Aa][Tt][Ee][Mm][Ee][Nn][Tt])\\b|[Mm][Ee][Rr][Gg][Ee]\\s+[Ii][Nn][Tt][Oo]\\b)")
|
|
30
|
+
(#set! injection.language "sql"))
|
|
31
|
+
|
|
32
|
+
; Inline assembler blocks.
|
|
33
|
+
((asmBody) @injection.content
|
|
34
|
+
(#set! injection.language "asm"))
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
; outline.scm -- tree-sitter-delphi13
|
|
2
|
+
;
|
|
3
|
+
; Drives Zed's outline panel (Ctrl-Shift-O / the breadcrumb symbol list).
|
|
4
|
+
;
|
|
5
|
+
; Convention:
|
|
6
|
+
; @item the whole entry
|
|
7
|
+
; @name the text shown for it
|
|
8
|
+
; @context surrounding keywords shown greyed next to the name
|
|
9
|
+
|
|
10
|
+
; Types: type TFoo = class ... end;
|
|
11
|
+
(declType
|
|
12
|
+
(kType)? @context
|
|
13
|
+
name: [(identifier) (genericDot) (genericTpl)] @name) @item
|
|
14
|
+
|
|
15
|
+
; Routines in the interface section and standalone declarations:
|
|
16
|
+
; procedure Foo(const X: Integer);
|
|
17
|
+
(declProc
|
|
18
|
+
[
|
|
19
|
+
(kProcedure)
|
|
20
|
+
(kFunction)
|
|
21
|
+
(kConstructor)
|
|
22
|
+
(kDestructor)
|
|
23
|
+
(kOperator)
|
|
24
|
+
] @context
|
|
25
|
+
name: [(identifier) (genericDot) (genericTpl)] @name) @item
|
|
26
|
+
|
|
27
|
+
; NOTE: implemented routines (procedure TFoo.Bar; begin ... end;) are NOT given
|
|
28
|
+
; their own pattern. A defProc's `header:` IS a declProc, so the pattern above
|
|
29
|
+
; already matches it -- adding a defProc pattern here produced every
|
|
30
|
+
; implementation twice in the outline.
|
|
31
|
+
|
|
32
|
+
; Properties: property Count: Integer read FCount;
|
|
33
|
+
(declProp
|
|
34
|
+
(kProperty) @context
|
|
35
|
+
name: (identifier) @name) @item
|