Generate the TextMate sample renderings (#7762)

The images beside the samples were screenshots taken by hand, so they
drifted: they still showed `package Carbon api;`, syntax the language
dropped in 2024.

`render_sample.py` renders a sample the way the grammar in this
repository actually highlights it, using `tmlanguage.py`, a small
TextMate tokenizer. VS Code runs grammars under Oniguruma, which we
cannot depend on here, but this grammar uses no Oniguruma-only syntax,
so `re` runs its regexes unchanged and the two agree on every character
of every Carbon file in the repository. The output is SVG, so
regenerating needs nothing but Python, and a later grammar change gets a
same-path image diff showing what it did to real code.

The samples change where a construct left the language (`api`, `Carbon`
as the package name, `StringView`, `destructor`), refresh the
`keywords.carbon` inventory against `token_kind.def`, and add sections
for octal, raw and block literals, character literals, lambdas, and raw
identifiers. `interop.carbon` is new, covering inline C++. These are
highlighting fixtures rather than programs, so the deliberately invalid
lines stay.

Assisted-by: Claude Code

---------

Co-authored-by: Dana Jansens <danakj@orodu.net>
This commit is contained in:
Chandler Carruth
2026-09-15 20:29:22 +00:00
committed by GitHub
co-authored by Dana Jansens
parent e962b12e53
commit 37949a2066
27 changed files with 1051 additions and 11 deletions
+14
View File
@@ -33,3 +33,17 @@ If you are using Atom, you can convert the bundle to an Atom-compatible one. See
For other editors that support TextMate bundles you can consult your editors
documentation to see how to use the bundle.
## Samples
`Samples/` holds Carbon sources that exercise the grammar, each with an SVG
rendering of how this bundle highlights it. Some deliberately contain invalid
code, to show that highlighting stays sensible while something is being typed.
The renderings are generated, not screenshotted, so they always reflect the
grammar in this repository. Regenerate them in the same commit as any change to
the grammar, so a reviewer can see what the change does to real code:
```shell
utils/textmate/render_sample.py utils/textmate/Samples/*.carbon
```
Binary file not shown.

Before

Width:  |  Height:  |  Size: 18 KiB

+13
View File
@@ -0,0 +1,13 @@
<svg xmlns="http://www.w3.org/2000/svg" width="712" height="195" viewBox="0 0 712 195">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681">1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681">2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681">3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681">4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681">5 </tspan><tspan fill="#569cd6">choice</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">SomeChoice</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#9cdcfe">T</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">) {</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681">6 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4fc1ff">Val1</tspan><tspan fill="#d4d4d4">,</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681">7 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4fc1ff">Val2</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4fc1ff">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#4fc1ff">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">array</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4fc1ff">T</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#b5cea8">5</tspan><tspan fill="#d4d4d4">), </tspan><tspan fill="#4fc1ff">t</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4fc1ff">T</tspan><tspan fill="#d4d4d4">),</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681">8 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4fc1ff">Val3</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681">9 </tspan><tspan fill="#d4d4d4">}</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

+2
View File
@@ -7,8 +7,10 @@
// class C; fn F[T: A](a: T) -> i32 { return 86; }
//@dump-sem-ir-begin
//@dump-sem-ir-end
//@include-in-dumps
//@dump-sem-ir-
//no whitespace after double slash
/* invalid comment pattern. */
/// invalid comment pattern.
class C; // Comment after a statement/expression/declaration.
var x: i32 = 1;// Trailing, with no space before the introducer.
Binary file not shown.

Before

Width:  |  Height:  |  Size: 31 KiB

+20
View File
@@ -0,0 +1,20 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="328" viewBox="0 0 721 328">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#6a9955">// This is a comment.</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan><tspan fill="#6a9955"> // Comment with whitespace.</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#6a9955">// class C; fn F[T: A](a: T) -&gt; i32 { return 86; }</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#6a9955">//@dump-sem-ir-begin</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#6a9955">//@dump-sem-ir-end</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#6a9955">//@include-in-dumps</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#d4d4d4">//@</tspan><tspan fill="#9cdcfe">dump</tspan><tspan fill="#d4d4d4">-</tspan><tspan fill="#9cdcfe">sem</tspan><tspan fill="#d4d4d4">-</tspan><tspan fill="#9cdcfe">ir</tspan><tspan fill="#d4d4d4">-</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan><tspan fill="#d4d4d4">//</tspan><tspan fill="#9cdcfe">no</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">whitespace</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">after</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">double</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">slash</tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#d4d4d4">/* </tspan><tspan fill="#9cdcfe">invalid</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">comment</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">pattern</tspan><tspan fill="#d4d4d4">. */</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#d4d4d4">/// </tspan><tspan fill="#9cdcfe">invalid</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">comment</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">pattern</tspan><tspan fill="#d4d4d4">.</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4">; // </tspan><tspan fill="#9cdcfe">Comment</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">after</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">statement</tspan><tspan fill="#d4d4d4">/</tspan><tspan fill="#9cdcfe">expression</tspan><tspan fill="#d4d4d4">/</tspan><tspan fill="#9cdcfe">declaration</tspan><tspan fill="#d4d4d4">.</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">;// </tspan><tspan fill="#9cdcfe">Trailing</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">with</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">no</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">space</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">before</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">the</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">introducer</tspan><tspan fill="#d4d4d4">.</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 4.5 KiB

+1 -1
View File
@@ -2,7 +2,7 @@
// Exceptions. See /LICENSE for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
package SomePackage api;
package SomePackage;
Core SomeCore;
import SomePackage;
Binary file not shown.

Before

Width:  |  Height:  |  Size: 20 KiB

+15
View File
@@ -0,0 +1,15 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="233" viewBox="0 0 721 233">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#569cd6">package</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">SomePackage</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan><tspan fill="#9cdcfe">Core</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">SomeCore</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">SomePackage</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#dcdcaa">CallFunction(</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">c</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#9cdcfe">d</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#9cdcfe">unidentified</tspan><tspan fill="#d4d4d4">;</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 2.2 KiB

@@ -37,3 +37,16 @@ fn F(ref a: A, const ref b: B);
fn F() -> T;
fn F() -> T.U { return val; }
fn F() -> i32 => return val;
// --- lambdas and positional parameters
var explicit: auto = fn (x: i32) -> i32 { return x + 1; };
var expression: auto = fn (x: i32) => x + 1;
var positional: auto = fn { Print($0, $1, $42); };
// --- raw identifiers
r#class
r#if
r#i32
var r#var: i32 = r#class;
Binary file not shown.

Before

Width:  |  Height:  |  Size: 46 KiB

@@ -0,0 +1,56 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="1012" viewBox="0 0 721 1012">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F1</tspan><tspan fill="#d4d4d4">();</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Func</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Generic</tspan><tspan fill="#d4d4d4">[</tspan><tspan fill="#9cdcfe">T</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">U</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">](</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">U</tspan><tspan fill="#d4d4d4">) -&gt; </tspan><tspan fill="#4ec9b0">U</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Lambda</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">) -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> =&gt; </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4"> + </tspan><tspan fill="#b5cea8">5</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#569cd6">fn</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">MultiLine</tspan><tspan fill="#d4d4d4">[</tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">A</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">,</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">B</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">C1</tspan><tspan fill="#d4d4d4">,</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">C</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">C2</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan><tspan fill="#d4d4d4"> ](</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">C</tspan><tspan fill="#d4d4d4">),</tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4">,</tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">c</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Invalid</tspan><tspan fill="#d4d4d4">#+?</tspan><tspan fill="#dcdcaa">Name</tspan><tspan fill="#d4d4d4">();</tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4">.(</tspan><tspan fill="#9cdcfe">I</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#9cdcfe">F</tspan><tspan fill="#d4d4d4">)();</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4"> = (</tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">array</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#b5cea8">5</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan><tspan fill="#c586c0">generic</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan><tspan fill="#c586c0">generic</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">in</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">some_list</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="577"><tspan fill="#6e7681">30 </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="596"><tspan fill="#6e7681">31 </tspan><tspan fill="#9cdcfe">binding</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="615"><tspan fill="#6e7681">32 </tspan><tspan fill="#c586c0">generic</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">binding</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="634"><tspan fill="#6e7681">33 </tspan><tspan fill="#569cd6">var</tspan></text>
<text style="white-space:pre" x="12" y="653"><tspan fill="#6e7681">34 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">multiline</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="672"><tspan fill="#6e7681">35 </tspan></text>
<text style="white-space:pre" x="12" y="691"><tspan fill="#6e7681">36 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#c586c0">ref</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#569cd6">const</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">ref</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="710"><tspan fill="#6e7681">37 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="729"><tspan fill="#6e7681">38 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">U</tspan><tspan fill="#d4d4d4"> { </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">val</tspan><tspan fill="#d4d4d4">; }</tspan></text>
<text style="white-space:pre" x="12" y="748"><tspan fill="#6e7681">39 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">F</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> =&gt; </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">val</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="767"><tspan fill="#6e7681">40 </tspan></text>
<text style="white-space:pre" x="12" y="786"><tspan fill="#6e7681">41 </tspan><tspan fill="#6a9955">// --- lambdas and positional parameters</tspan></text>
<text style="white-space:pre" x="12" y="805"><tspan fill="#6e7681">42 </tspan></text>
<text style="white-space:pre" x="12" y="824"><tspan fill="#6e7681">43 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">explicit</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">auto</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">) -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> { </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4"> + </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">; };</tspan></text>
<text style="white-space:pre" x="12" y="843"><tspan fill="#6e7681">44 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">expression</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">auto</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">) =&gt; </tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4"> + </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="862"><tspan fill="#6e7681">45 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">positional</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">auto</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> { </tspan><tspan fill="#dcdcaa">Print</tspan><tspan fill="#d4d4d4">($</tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">, $</tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">, $</tspan><tspan fill="#b5cea8">42</tspan><tspan fill="#d4d4d4">); };</tspan></text>
<text style="white-space:pre" x="12" y="881"><tspan fill="#6e7681">46 </tspan></text>
<text style="white-space:pre" x="12" y="900"><tspan fill="#6e7681">47 </tspan><tspan fill="#6a9955">// --- raw identifiers</tspan></text>
<text style="white-space:pre" x="12" y="919"><tspan fill="#6e7681">48 </tspan></text>
<text style="white-space:pre" x="12" y="938"><tspan fill="#6e7681">49 </tspan><tspan fill="#9cdcfe">r</tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#569cd6">class</tspan></text>
<text style="white-space:pre" x="12" y="957"><tspan fill="#6e7681">50 </tspan><tspan fill="#4ec9b0">r</tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#c586c0">if</tspan></text>
<text style="white-space:pre" x="12" y="976"><tspan fill="#6e7681">51 </tspan><tspan fill="#4ec9b0">r</tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#569cd6">i32</tspan></text>
<text style="white-space:pre" x="12" y="995"><tspan fill="#6e7681">52 </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">r</tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#4ec9b0">r</tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4">;</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 15 KiB

+29
View File
@@ -0,0 +1,29 @@
// Part of the Carbon Language project, under the Apache License v2.0 with LLVM
// Exceptions. See /LICENSE for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
// Inline C++ is scoped `meta.embedded.block.cpp`, so an editor that has a C++
// grammar highlights them as C++; these renderings come from the Carbon grammar
// alone, so that content shows plain.
package Sample library "interop";
import Cpp library "<cstdio>";
import Cpp library "<string_view>";
import Cpp inline '''c++
int FromImport() { return 1; }
''';
import Cpp inline "int OneLiner() { return 2; }";
inline Cpp '''
int FromBlock() { return 3; }
''';
fn Uses() {
var value: Cpp.int = 1 as Cpp.int;
var widened: Cpp.size_t = value as Cpp.size_t;
var back: i32 = value unsafe as i32;
Cpp.printf("%d\n", value);
}
+33
View File
@@ -0,0 +1,33 @@
<svg xmlns="http://www.w3.org/2000/svg" width="730" height="575" viewBox="0 0 730 575">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan><tspan fill="#6a9955">//</tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#6a9955">// Inline C++ is scoped `meta.embedded.block.cpp`, so an editor that has a C++</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan><tspan fill="#6a9955">// grammar highlights them as C++; these renderings come from the Carbon grammar</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#6a9955">// alone, so that content shows plain.</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#569cd6">package</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Sample</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">library</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">"interop"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">library</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">"&lt;cstdio&gt;"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">library</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">"&lt;string_view&gt;"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">inline</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">'''</tspan><tspan fill="#d7ba7d">c++</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#d4d4d4">int FromImport() { return 1; }</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan><tspan fill="#ce9178">'''</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">inline</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">"</tspan><tspan fill="#d4d4d4">int OneLiner() { return 2; }</tspan><tspan fill="#ce9178">"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#569cd6">inline</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#ce9178">'''</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan><tspan fill="#d4d4d4">int FromBlock() { return 3; }</tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#ce9178">'''</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Uses</tspan><tspan fill="#d4d4d4">() {</tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">value</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">Cpp</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#9cdcfe">int</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Cpp</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">int</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">widened</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">Cpp</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">size_t</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#9cdcfe">value</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Cpp</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">size_t</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">back</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#9cdcfe">value</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">unsafe</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Cpp</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#dcdcaa">printf(</tspan><tspan fill="#ce9178">"%d</tspan><tspan fill="#d7ba7d">\n</tspan><tspan fill="#ce9178">"</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">value</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#d4d4d4">}</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 7.1 KiB

+12 -5
View File
@@ -4,8 +4,9 @@
// --- operators
>>= <=> <<= &= == != >= >> <= << -= -> -- %= \ = += ++ /= *= & ^ = > < - % . | + / *
and as impls in like not or partial ref template where
>>= <=> <<= ->? &= ^= := :? == => != >= >> <= <> << <- -= -> -- %= |= += ++ /=
*= ~= & @ ^ : = ! > < - % . | + ? / * ~ \
and as impls in like not or where
// --- special-keywords
@@ -14,7 +15,8 @@ default =>
// --- introducer-keywords
adapt alias choice class constraint fn import interface let library namespace var
adapt alias choice class constraint fn import inline interface let library
match_first namespace observe require var
base
export
impl
@@ -22,7 +24,8 @@ package
// --- modifier-keywords
abstract const extend extern final private protected virtual
abstract const eval extend extern final generic musteval override partial
private protected ref runtime static template unsafe unused val virtual
base class
default
export import
@@ -32,13 +35,17 @@ impl package
// --- misc-keywords
auto destructor forall friend observe override require
forall form friend
.base
// --- self-keywords
self Self
// --- package-roots
Core Cpp
// --- underscore
;
Binary file not shown.

Before

Width:  |  Height:  |  Size: 55 KiB

+57
View File
@@ -0,0 +1,57 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="1031" viewBox="0 0 721 1031">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#6a9955">// --- operators</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#d4d4d4">&gt;&gt;= &lt;=&gt; &lt;&lt;= -&gt;? &amp;= ^= := :? == =&gt; != &gt;= &gt;&gt; &lt;= &lt;&gt; &lt;&lt; &lt;- -= -&gt; -- %= |= += ++ /=</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#d4d4d4">*= ~= &amp; @ ^ : = ! &gt; &lt; - % . | + ? / * ~ \</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#c586c0">and</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">impls</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">in</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">like</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">not</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">or</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">where</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#6a9955">// --- special-keywords</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#c586c0">break</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">case</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">continue</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">else</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">if</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">for</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">match</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">returned</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">then</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">while</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#c586c0">default</tspan><tspan fill="#d4d4d4"> =&gt;</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan><tspan fill="#6a9955">// --- introducer-keywords</tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#569cd6">adapt</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">alias</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">choice</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">constraint</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">import</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">inline</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">interface</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">library</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan><tspan fill="#4ec9b0">match_first</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">namespace</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">observe</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">require</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#569cd6">base</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan><tspan fill="#569cd6">export</tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#569cd6">impl</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan><tspan fill="#569cd6">package</tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan><tspan fill="#6a9955">// --- modifier-keywords</tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan><tspan fill="#569cd6">abstract</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">const</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">eval</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">extend</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">extern</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">final</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">generic</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">musteval</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">override</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">partial</tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan><tspan fill="#569cd6">private</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">protected</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">ref</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">runtime</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">static</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">template</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">unsafe</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">unused</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">val</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">virtual</tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#569cd6">base</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">class</tspan></text>
<text style="white-space:pre" x="12" y="577"><tspan fill="#6e7681">30 </tspan><tspan fill="#569cd6">default</tspan></text>
<text style="white-space:pre" x="12" y="596"><tspan fill="#6e7681">31 </tspan><tspan fill="#569cd6">export</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">import</tspan></text>
<text style="white-space:pre" x="12" y="615"><tspan fill="#6e7681">32 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">fn</tspan></text>
<text style="white-space:pre" x="12" y="634"><tspan fill="#6e7681">33 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">library</tspan></text>
<text style="white-space:pre" x="12" y="653"><tspan fill="#6e7681">34 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">package</tspan></text>
<text style="white-space:pre" x="12" y="672"><tspan fill="#6e7681">35 </tspan></text>
<text style="white-space:pre" x="12" y="691"><tspan fill="#6e7681">36 </tspan><tspan fill="#6a9955">// --- misc-keywords</tspan></text>
<text style="white-space:pre" x="12" y="710"><tspan fill="#6e7681">37 </tspan></text>
<text style="white-space:pre" x="12" y="729"><tspan fill="#6e7681">38 </tspan><tspan fill="#569cd6">forall</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">form</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">friend</tspan></text>
<text style="white-space:pre" x="12" y="748"><tspan fill="#6e7681">39 </tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#569cd6">base</tspan></text>
<text style="white-space:pre" x="12" y="767"><tspan fill="#6e7681">40 </tspan></text>
<text style="white-space:pre" x="12" y="786"><tspan fill="#6e7681">41 </tspan><tspan fill="#6a9955">// --- self-keywords</tspan></text>
<text style="white-space:pre" x="12" y="805"><tspan fill="#6e7681">42 </tspan></text>
<text style="white-space:pre" x="12" y="824"><tspan fill="#6e7681">43 </tspan><tspan fill="#569cd6">self</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">Self</tspan></text>
<text style="white-space:pre" x="12" y="843"><tspan fill="#6e7681">44 </tspan></text>
<text style="white-space:pre" x="12" y="862"><tspan fill="#6e7681">45 </tspan><tspan fill="#6a9955">// --- package-roots</tspan></text>
<text style="white-space:pre" x="12" y="881"><tspan fill="#6e7681">46 </tspan></text>
<text style="white-space:pre" x="12" y="900"><tspan fill="#6e7681">47 </tspan><tspan fill="#4ec9b0">Core</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Cpp</tspan></text>
<text style="white-space:pre" x="12" y="919"><tspan fill="#6e7681">48 </tspan></text>
<text style="white-space:pre" x="12" y="938"><tspan fill="#6e7681">49 </tspan><tspan fill="#6a9955">// --- underscore</tspan></text>
<text style="white-space:pre" x="12" y="957"><tspan fill="#6e7681">50 </tspan></text>
<text style="white-space:pre" x="12" y="976"><tspan fill="#6e7681">51 </tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="995"><tspan fill="#6e7681">52 </tspan><tspan fill="#569cd6">_</tspan></text>
<text style="white-space:pre" x="12" y="1014"><tspan fill="#6e7681">53 </tspan><tspan fill="#9cdcfe">_some_var</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 10 KiB

+23 -1
View File
@@ -11,6 +11,24 @@
''' Multi line
string
'''
'''py
Block literal with a file type indicator.
'''
#"a raw \n literal, where \#n is the escape"#
##"nested "# stays inside, and \##n is the escape"##
#'''
A raw block literal.
'''#
"unterminated
// --- characters
'a' '\n' '\0' '\u{1F600}'
'\x70'
''
'abcde'
// --- true-false
@@ -18,7 +36,7 @@ true false
// --- type-literals
array bool char str type ;
array auto bool char str type
i8 i16 i32 i64 i128 i10
u8 u16 u32 u64 u128 u11
f8 f16 f32 f64 f128 f12
@@ -34,6 +52,10 @@ f8 f16 f32 f64 f128 f12
.123
.1e3
0o755
0o_17
0o8
0b1011_0010
0b_010
0b2345
Binary file not shown.

Before

Width:  |  Height:  |  Size: 45 KiB

+72
View File
@@ -0,0 +1,72 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="1316" viewBox="0 0 721 1316">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#6a9955">// --- string</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#d4d4d4">'</tspan><tspan fill="#9cdcfe">C</tspan><tspan fill="#d4d4d4">'</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#ce9178">"Hello</tspan><tspan fill="#d7ba7d">\n</tspan><tspan fill="#ce9178">World</tspan><tspan fill="#d7ba7d">\n</tspan><tspan fill="#ce9178">"</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#ce9178">"</tspan><tspan fill="#d7ba7d">\"\'\t\r\n</tspan><tspan fill="#ce9178">"</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#ce9178">'''Single line string'''</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#ce9178">''' Multi line</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan><tspan fill="#ce9178"> string</tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#ce9178">'''</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#ce9178">'''</tspan><tspan fill="#d7ba7d">py</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#ce9178"> Block literal with a file type indicator.</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan><tspan fill="#ce9178">'''</tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#d4d4d4">#</tspan><tspan fill="#ce9178">"a raw </tspan><tspan fill="#d7ba7d">\n</tspan><tspan fill="#ce9178"> literal, where \#n is the escape"</tspan><tspan fill="#d4d4d4">#</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan><tspan fill="#d4d4d4">##</tspan><tspan fill="#ce9178">"nested "</tspan><tspan fill="#d4d4d4"># </tspan><tspan fill="#9cdcfe">stays</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">inside</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#c586c0">and</tspan><tspan fill="#d4d4d4"> \##</tspan><tspan fill="#9cdcfe">n</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">is</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">the</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">escape</tspan><tspan fill="#ce9178">"##</tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#ce9178">#'''</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan><tspan fill="#ce9178"> A raw block literal.</tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#ce9178">'''#</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan><tspan fill="#ce9178">"</tspan><tspan fill="#9cdcfe">unterminated</tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan><tspan fill="#6a9955">// --- characters</tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan><tspan fill="#d4d4d4">'</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">' '\</tspan><tspan fill="#9cdcfe">n</tspan><tspan fill="#d4d4d4">' '\</tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">' '\</tspan><tspan fill="#9cdcfe">u</tspan><tspan fill="#d4d4d4">{</tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">F</tspan><tspan fill="#b5cea8">600</tspan><tspan fill="#d4d4d4">}'</tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#d4d4d4">'\</tspan><tspan fill="#9cdcfe">x70</tspan><tspan fill="#d4d4d4">'</tspan></text>
<text style="white-space:pre" x="12" y="577"><tspan fill="#6e7681">30 </tspan><tspan fill="#d4d4d4">''</tspan></text>
<text style="white-space:pre" x="12" y="596"><tspan fill="#6e7681">31 </tspan><tspan fill="#d4d4d4">'</tspan><tspan fill="#9cdcfe">abcde</tspan><tspan fill="#d4d4d4">'</tspan></text>
<text style="white-space:pre" x="12" y="615"><tspan fill="#6e7681">32 </tspan></text>
<text style="white-space:pre" x="12" y="634"><tspan fill="#6e7681">33 </tspan><tspan fill="#6a9955">// --- true-false</tspan></text>
<text style="white-space:pre" x="12" y="653"><tspan fill="#6e7681">34 </tspan></text>
<text style="white-space:pre" x="12" y="672"><tspan fill="#6e7681">35 </tspan><tspan fill="#569cd6">true</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">false</tspan></text>
<text style="white-space:pre" x="12" y="691"><tspan fill="#6e7681">36 </tspan></text>
<text style="white-space:pre" x="12" y="710"><tspan fill="#6e7681">37 </tspan><tspan fill="#6a9955">// --- type-literals</tspan></text>
<text style="white-space:pre" x="12" y="729"><tspan fill="#6e7681">38 </tspan></text>
<text style="white-space:pre" x="12" y="748"><tspan fill="#6e7681">39 </tspan><tspan fill="#569cd6">array</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">auto</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">bool</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">char</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">str</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">type</tspan></text>
<text style="white-space:pre" x="12" y="767"><tspan fill="#6e7681">40 </tspan><tspan fill="#569cd6">i8</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i16</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i64</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i128</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">i10</tspan></text>
<text style="white-space:pre" x="12" y="786"><tspan fill="#6e7681">41 </tspan><tspan fill="#569cd6">u8</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">u16</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">u32</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">u64</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">u128</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">u11</tspan></text>
<text style="white-space:pre" x="12" y="805"><tspan fill="#6e7681">42 </tspan><tspan fill="#569cd6">f8</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">f16</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">f32</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">f64</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">f128</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">f12</tspan></text>
<text style="white-space:pre" x="12" y="824"><tspan fill="#6e7681">43 </tspan></text>
<text style="white-space:pre" x="12" y="843"><tspan fill="#6e7681">44 </tspan><tspan fill="#6a9955">// --- numbers</tspan></text>
<text style="white-space:pre" x="12" y="862"><tspan fill="#6e7681">45 </tspan></text>
<text style="white-space:pre" x="12" y="881"><tspan fill="#6e7681">46 </tspan><tspan fill="#b5cea8">12345</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#b5cea8">6789</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#b5cea8">00012345</tspan></text>
<text style="white-space:pre" x="12" y="900"><tspan fill="#6e7681">47 </tspan></text>
<text style="white-space:pre" x="12" y="919"><tspan fill="#6e7681">48 </tspan><tspan fill="#b5cea8">1234.56789</tspan></text>
<text style="white-space:pre" x="12" y="938"><tspan fill="#6e7681">49 </tspan><tspan fill="#b5cea8">0.875</tspan></text>
<text style="white-space:pre" x="12" y="957"><tspan fill="#6e7681">50 </tspan><tspan fill="#b5cea8">0.3e5</tspan></text>
<text style="white-space:pre" x="12" y="976"><tspan fill="#6e7681">51 </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">e</tspan><tspan fill="#b5cea8">5</tspan></text>
<text style="white-space:pre" x="12" y="995"><tspan fill="#6e7681">52 </tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#b5cea8">123</tspan></text>
<text style="white-space:pre" x="12" y="1014"><tspan fill="#6e7681">53 </tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">e</tspan><tspan fill="#b5cea8">3</tspan></text>
<text style="white-space:pre" x="12" y="1033"><tspan fill="#6e7681">54 </tspan></text>
<text style="white-space:pre" x="12" y="1052"><tspan fill="#6e7681">55 </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">o</tspan><tspan fill="#b5cea8">755</tspan></text>
<text style="white-space:pre" x="12" y="1071"><tspan fill="#6e7681">56 </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">o_</tspan><tspan fill="#b5cea8">17</tspan></text>
<text style="white-space:pre" x="12" y="1090"><tspan fill="#6e7681">57 </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">o</tspan><tspan fill="#b5cea8">8</tspan></text>
<text style="white-space:pre" x="12" y="1109"><tspan fill="#6e7681">58 </tspan></text>
<text style="white-space:pre" x="12" y="1128"><tspan fill="#6e7681">59 </tspan><tspan fill="#b5cea8">0b1011_0010</tspan></text>
<text style="white-space:pre" x="12" y="1147"><tspan fill="#6e7681">60 </tspan><tspan fill="#b5cea8">0b_010</tspan></text>
<text style="white-space:pre" x="12" y="1166"><tspan fill="#6e7681">61 </tspan><tspan fill="#b5cea8">0b2345</tspan></text>
<text style="white-space:pre" x="12" y="1185"><tspan fill="#6e7681">62 </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">B</tspan><tspan fill="#b5cea8">011</tspan></text>
<text style="white-space:pre" x="12" y="1204"><tspan fill="#6e7681">63 </tspan></text>
<text style="white-space:pre" x="12" y="1223"><tspan fill="#6e7681">64 </tspan><tspan fill="#b5cea8">0x2AE5</tspan></text>
<text style="white-space:pre" x="12" y="1242"><tspan fill="#6e7681">65 </tspan><tspan fill="#b5cea8">0x_F109</tspan></text>
<text style="white-space:pre" x="12" y="1261"><tspan fill="#6e7681">66 </tspan><tspan fill="#b5cea8">0xD8_E2.5F_7Bp8</tspan></text>
<text style="white-space:pre" x="12" y="1280"><tspan fill="#6e7681">67 </tspan><tspan fill="#b5cea8">0xabcdef.abcdef</tspan></text>
<text style="white-space:pre" x="12" y="1299"><tspan fill="#6e7681">68 </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">XA</tspan><tspan fill="#b5cea8">85</tspan><tspan fill="#d4d4d4">CE</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 12 KiB

+4 -4
View File
@@ -4,7 +4,7 @@
// More single line comments
package Carbon api;
package Carbon;
interface HasValueParam(T: type, V: T) {
fn Go(self) -> T;
@@ -25,7 +25,7 @@ class Point {
fn Procedure() -> i32 {
returned var zoop: i32 = 0;
while (DoSomeJob() {
while (DoSomeJob()) {
zoop += 1;
}
@@ -38,9 +38,9 @@ fn Main() -> i32 {
let bin = 0b0000111001010010;
let dec = 123456789012345678;
let big: Carbon.Int(1024) = 1234;
let big: Core.Int(1024) = 1234;
let aaa: auto = "Carbon";
let view: StringView = "Carbon";
let view: str = "Carbon";
return Procedure();
}
Binary file not shown.

Before

Width:  |  Height:  |  Size: 56 KiB

+50
View File
@@ -0,0 +1,50 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="898" viewBox="0 0 721 898">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#6a9955">// More single line comments</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#569cd6">package</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Carbon</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#569cd6">interface</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">HasValueParam</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#9cdcfe">T</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">V</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">) {</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Go</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#569cd6">self</tspan><tspan fill="#d4d4d4">) -&gt; </tspan><tspan fill="#4ec9b0">T</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> () </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">HasValueParam</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#b5cea8">5</tspan><tspan fill="#d4d4d4">) {</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Go</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#569cd6">self</tspan><tspan fill="#d4d4d4">) -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> { </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#b5cea8">42</tspan><tspan fill="#d4d4d4">; }</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Point</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Origin</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#569cd6">Self</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> {.</tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">, .</tspan><tspan fill="#9cdcfe">y</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">};</tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#d4d4d4"> }</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">x</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">y</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Procedure</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">returned</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">zoop</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">0</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">while</tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#dcdcaa">DoSomeJob(</tspan><tspan fill="#d4d4d4">)) {</tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">zoop</tspan><tspan fill="#d4d4d4"> += </tspan><tspan fill="#b5cea8">1</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="577"><tspan fill="#6e7681">30 </tspan><tspan fill="#d4d4d4"> }</tspan></text>
<text style="white-space:pre" x="12" y="596"><tspan fill="#6e7681">31 </tspan></text>
<text style="white-space:pre" x="12" y="615"><tspan fill="#6e7681">32 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">var</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="634"><tspan fill="#6e7681">33 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="653"><tspan fill="#6e7681">34 </tspan></text>
<text style="white-space:pre" x="12" y="672"><tspan fill="#6e7681">35 </tspan><tspan fill="#569cd6">fn</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">Main</tspan><tspan fill="#d4d4d4">() -&gt; </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="691"><tspan fill="#6e7681">36 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">str</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#ce9178">"Hello world"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="710"><tspan fill="#6e7681">37 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">hex</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">0xABCDEF1234567890</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="729"><tspan fill="#6e7681">38 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">bin</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">0b0000111001010010</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="748"><tspan fill="#6e7681">39 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">dec</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#b5cea8">123456789012345678</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="767"><tspan fill="#6e7681">40 </tspan></text>
<text style="white-space:pre" x="12" y="786"><tspan fill="#6e7681">41 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">big</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">Core</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">Int</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#b5cea8">1024</tspan><tspan fill="#d4d4d4">) = </tspan><tspan fill="#b5cea8">1234</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="805"><tspan fill="#6e7681">42 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">aaa</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">auto</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#ce9178">"Carbon"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="824"><tspan fill="#6e7681">43 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">let</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">view</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">str</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#ce9178">"Carbon"</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="843"><tspan fill="#6e7681">44 </tspan></text>
<text style="white-space:pre" x="12" y="862"><tspan fill="#6e7681">45 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">return</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#dcdcaa">Procedure(</tspan><tspan fill="#d4d4d4">);</tspan></text>
<text style="white-space:pre" x="12" y="881"><tspan fill="#6e7681">46 </tspan><tspan fill="#d4d4d4">}</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 50 KiB

+45
View File
@@ -0,0 +1,45 @@
<svg xmlns="http://www.w3.org/2000/svg" width="721" height="803" viewBox="0 0 721 803">
<rect width="100%" height="100%" fill="#1f1f1f"/>
<g xml:space="preserve" font-family="ui-monospace, SFMono-Regular, Menlo, Consolas, monospace" font-size="14">
<text style="white-space:pre" x="12" y="26"><tspan fill="#6e7681"> 1 </tspan><tspan fill="#6a9955">// Part of the Carbon Language project, under the Apache License v2.0 with LLVM</tspan></text>
<text style="white-space:pre" x="12" y="45"><tspan fill="#6e7681"> 2 </tspan><tspan fill="#6a9955">// Exceptions. See /LICENSE for license information.</tspan></text>
<text style="white-space:pre" x="12" y="64"><tspan fill="#6e7681"> 3 </tspan><tspan fill="#6a9955">// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception</tspan></text>
<text style="white-space:pre" x="12" y="83"><tspan fill="#6e7681"> 4 </tspan></text>
<text style="white-space:pre" x="12" y="102"><tspan fill="#6e7681"> 5 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C1</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="121"><tspan fill="#6e7681"> 6 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C2</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#9cdcfe">T1</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#9cdcfe">T2</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">C1</tspan><tspan fill="#d4d4d4">) {}</tspan></text>
<text style="white-space:pre" x="12" y="140"><tspan fill="#6e7681"> 7 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C3</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="159"><tspan fill="#6e7681"> 8 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">extend</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">base</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">C1</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="178"><tspan fill="#6e7681"> 9 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="197"><tspan fill="#6e7681">10 </tspan><tspan fill="#569cd6">class</tspan></text>
<text style="white-space:pre" x="12" y="216"><tspan fill="#6e7681">11 </tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#4ec9b0">C4</tspan><tspan fill="#d4d4d4">(</tspan></text>
<text style="white-space:pre" x="12" y="235"><tspan fill="#6e7681">12 </tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#9cdcfe">T1</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">type</tspan><tspan fill="#d4d4d4">),</tspan></text>
<text style="white-space:pre" x="12" y="254"><tspan fill="#6e7681">13 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">T2</tspan><tspan fill="#d4d4d4">:</tspan></text>
<text style="white-space:pre" x="12" y="273"><tspan fill="#6e7681">14 </tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">.(</tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">E</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#4ec9b0">F</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">G</tspan><tspan fill="#d4d4d4">)).</tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4">)</tspan></text>
<text style="white-space:pre" x="12" y="292"><tspan fill="#6e7681">15 </tspan><tspan fill="#d4d4d4"> .</tspan><tspan fill="#4ec9b0">D</tspan><tspan fill="#d4d4d4">))) ;</tspan></text>
<text style="white-space:pre" x="12" y="311"><tspan fill="#6e7681">16 </tspan></text>
<text style="white-space:pre" x="12" y="330"><tspan fill="#6e7681">17 </tspan><tspan fill="#569cd6">class</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C5</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="349"><tspan fill="#6e7681">18 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="368"><tspan fill="#6e7681">19 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">extend</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="387"><tspan fill="#6e7681">20 </tspan><tspan fill="#d4d4d4">}</tspan></text>
<text style="white-space:pre" x="12" y="406"><tspan fill="#6e7681">21 </tspan></text>
<text style="white-space:pre" x="12" y="425"><tspan fill="#6e7681">22 </tspan><tspan fill="#569cd6">alias</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">a1</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#4ec9b0">C1</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="444"><tspan fill="#6e7681">23 </tspan><tspan fill="#569cd6">alias</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">a2</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="463"><tspan fill="#6e7681">24 </tspan></text>
<text style="white-space:pre" x="12" y="482"><tspan fill="#6e7681">25 </tspan><tspan fill="#569cd6">adapt</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">SomeClass</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="501"><tspan fill="#6e7681">26 </tspan><tspan fill="#569cd6">adapt</tspan><tspan fill="#d4d4d4"> {.</tspan><tspan fill="#9cdcfe">a</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#4ec9b0">SomeClass</tspan><tspan fill="#d4d4d4">, .</tspan><tspan fill="#9cdcfe">b</tspan><tspan fill="#d4d4d4">: </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">};</tspan></text>
<text style="white-space:pre" x="12" y="520"><tspan fill="#6e7681">27 </tspan><tspan fill="#569cd6">adapt</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">i32</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="539"><tspan fill="#6e7681">28 </tspan></text>
<text style="white-space:pre" x="12" y="558"><tspan fill="#6e7681">29 </tspan><tspan fill="#569cd6">interface</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="577"><tspan fill="#6e7681">30 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> (</tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4">.(</tspan><tspan fill="#4ec9b0">D</tspan><tspan fill="#d4d4d4">.</tspan><tspan fill="#4ec9b0">E</tspan><tspan fill="#d4d4d4">(</tspan><tspan fill="#4ec9b0">F</tspan><tspan fill="#d4d4d4">, </tspan><tspan fill="#4ec9b0">G</tspan><tspan fill="#d4d4d4">)).</tspan><tspan fill="#4ec9b0">H</tspan><tspan fill="#d4d4d4">)) {}</tspan></text>
<text style="white-space:pre" x="12" y="596"><tspan fill="#6e7681">31 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">where</tspan><tspan fill="#d4d4d4"> .</tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4"> = (</tspan><tspan fill="#4ec9b0">B</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">where</tspan><tspan fill="#d4d4d4"> .</tspan><tspan fill="#569cd6">Self</tspan><tspan fill="#d4d4d4"> = {}) {}</tspan></text>
<text style="white-space:pre" x="12" y="615"><tspan fill="#6e7681">32 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">C</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">where</tspan><tspan fill="#d4d4d4"> .</tspan><tspan fill="#4ec9b0">A</tspan><tspan fill="#d4d4d4"> = {} </tspan><tspan fill="#c586c0">and</tspan><tspan fill="#d4d4d4"> .</tspan><tspan fill="#9cdcfe">B</tspan><tspan fill="#d4d4d4"> = </tspan><tspan fill="#9cdcfe">C</tspan><tspan fill="#d4d4d4"> {}</tspan></text>
<text style="white-space:pre" x="12" y="634"><tspan fill="#6e7681">33 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">Self</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="653"><tspan fill="#6e7681">34 </tspan><tspan fill="#569cd6">impl</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">as</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="672"><tspan fill="#6e7681">35 </tspan></text>
<text style="white-space:pre" x="12" y="691"><tspan fill="#6e7681">36 </tspan><tspan fill="#569cd6">constraint</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">Constraint</tspan><tspan fill="#d4d4d4"> {</tspan></text>
<text style="white-space:pre" x="12" y="710"><tspan fill="#6e7681">37 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">require</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#9cdcfe">T</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">impls</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="729"><tspan fill="#6e7681">38 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">require</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">Self</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">impls</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="748"><tspan fill="#6e7681">39 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">require</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">impls</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="767"><tspan fill="#6e7681">40 </tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">extern</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#569cd6">require</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#c586c0">impls</tspan><tspan fill="#d4d4d4"> </tspan><tspan fill="#4ec9b0">I</tspan><tspan fill="#d4d4d4">;</tspan></text>
<text style="white-space:pre" x="12" y="786"><tspan fill="#6e7681">41 </tspan><tspan fill="#d4d4d4">}</tspan></text>
</g></svg>

After

Width:  |  Height:  |  Size: 11 KiB

+187
View File
@@ -0,0 +1,187 @@
#!/usr/bin/env -S uv run --script
# /// script
# requires-python = ">=3.12"
# ///
"""Renders Carbon sources as highlighted SVG.
This regenerates the renderings next to the TextMate samples, so they show what
the grammar in this repository actually produces rather than whatever an editor
looked like when someone last took a screenshot by hand.
The SVG holds the source as text rather than as outlines, so whatever displays
it lays the text out and draws the glyphs; nothing here rasterizes. Colors are
VS Code's Dark+. A scope the theme does not style resolves outward through the
scope stack, which is what makes a string's quotes take the string color and a
comment's `//` take the comment color.
"""
__copyright__ = """
Part of the Carbon Language project, under the Apache License v2.0 with LLVM
Exceptions. See /LICENSE for license information.
SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
"""
import argparse
import sys
from pathlib import Path
from typing import Optional
import tmlanguage
# The grammar is part of the VS Code extension, which must all be contained
# under the extension's root directory.
_GRAMMAR_PATH = (
Path(__file__).resolve().parents[1] / "vscode" / "carbon.tmLanguage.json"
)
# VS Code's Dark+, keyed by the selectors the theme itself uses. Matching is by
# longest dotted prefix, as a real theme does, so this stays correct for any
# grammar rather than only the scope names in use today.
_THEME = {
"comment": "#6a9955",
"constant.character.escape": "#d7ba7d",
"constant.language": "#569cd6",
"constant.numeric": "#b5cea8",
"entity.name.function": "#dcdcaa",
"entity.name.namespace": "#4ec9b0",
"entity.name.tag": "#569cd6",
"entity.name.type": "#4ec9b0",
"keyword.control": "#c586c0",
"keyword.operator": "#d4d4d4",
"keyword.other": "#569cd6",
"meta.embedded": "#d4d4d4",
"storage.modifier": "#569cd6",
"storage.type": "#569cd6",
"string": "#ce9178",
"support.class": "#4ec9b0",
"support.function": "#dcdcaa",
"support.type": "#4ec9b0",
"support.type.property-name": "#9cdcfe",
"support.variable": "#9cdcfe",
"variable.language": "#569cd6",
"variable.other": "#9cdcfe",
"variable.other.enummember": "#4fc1ff",
"variable.parameter": "#9cdcfe",
}
_BACKGROUND = "#1f1f1f"
_FOREGROUND = "#d4d4d4"
_GUTTER = "#6e7681"
# Whatever monospace font the viewer has: nothing can be fetched, because
# GitHub serves SVG under `default-src 'none'` and a web font would be blocked.
# The text simply flows, so the font's own metrics lay each line out.
_FONT = "ui-monospace, SFMono-Regular, Menlo, Consolas, monospace"
_FONT_SIZE = 14
# Only used to size the canvas. Monospace advances cluster near 0.6em, so a
# font a little wider than this just runs closer to the right edge.
_CHAR_WIDTH = 8.5
_LINE_HEIGHT = 19
# How far above the bottom of its line the baseline sits, leaving room for the
# descenders of `g` and `y` at this line height.
_DESCENT = 5
_PAD = 12
def _color_for(scopes: list[str]) -> str:
"""Resolves a scope stack to a color, innermost scope first.
Within a scope the longest matching prefix wins, so that a selector such as
`variable.other.enummember` beats `variable.other`. A scope the theme does
not style resolves outward to its enclosing scope, which is what gives a
string's quotes the string color.
"""
for scope in reversed(scopes):
parts = scope.split(".")
for end in range(len(parts), 0, -1):
color = _THEME.get(".".join(parts[:end]))
if color:
return color
return _FOREGROUND
def _escape(text: str) -> str:
"""Escapes source text for an SVG text node, as one would for HTML."""
return text.replace("&", "&amp;").replace("<", "&lt;").replace(">", "&gt;")
def _runs(colors: list[str]) -> list[tuple[int, int, str]]:
"""Merges a per-character color list into `(start, end, color)` runs."""
runs: list[tuple[int, int, str]] = []
for index, color in enumerate(colors):
if runs and runs[-1][2] == color:
runs[-1] = (runs[-1][0], index + 1, color)
else:
runs.append((index, index + 1, color))
return runs
def render(grammar: tmlanguage.Grammar, source: str) -> str:
"""Renders a Carbon source as a standalone SVG document."""
lines = tmlanguage.split_lines(source)
colored = [[_FOREGROUND] * len(line) for line in lines]
for token in tmlanguage.tokenize(grammar, source):
color = _color_for(token.scopes)
row = colored[token.line]
# A token runs one past the line, over the newline it was tokenized
# with, and there is no column there to color.
for column in range(token.start, min(token.end, len(row))):
row[column] = color
# Trailing blank lines would only pad the bottom of the image.
while lines and not lines[-1].strip():
lines.pop()
colored.pop()
digits = len(str(len(lines))) if lines else 1
longest = max((len(line) for line in lines), default=0)
width = round(_PAD * 2 + (digits + 1 + longest) * _CHAR_WIDTH)
height = _PAD * 2 + len(lines) * _LINE_HEIGHT
out = [
f'<svg xmlns="http://www.w3.org/2000/svg" width="{width}"'
f' height="{height}" viewBox="0 0 {width} {height}">',
f'<rect width="100%" height="100%" fill="{_BACKGROUND}"/>',
# Indentation has to survive two eras of the spec. SVG 1.1 renderers
# read `xml:space`, and honor it here on the group. Browsers follow
# SVG 2, where whitespace is a CSS property and neither form is
# inherited into text from an ancestor, so each `text` repeats it.
f'<g xml:space="preserve" font-family="{_FONT}"'
f' font-size="{_FONT_SIZE}">',
]
for linenum, linetext in enumerate(lines):
baseline = _PAD + (linenum + 1) * _LINE_HEIGHT - _DESCENT
spans = [
f'<tspan fill="{_GUTTER}">{str(linenum + 1).rjust(digits)} </tspan>'
] + [
f'<tspan fill="{color}">{_escape(linetext[start:end])}</tspan>'
for start, end, color in _runs(colored[linenum])
]
out.append(
f'<text style="white-space:pre" x="{_PAD}" y="{baseline}">'
f"{''.join(spans)}</text>"
)
out.append("</g></svg>")
return "\n".join(out) + "\n"
def main(argv: Optional[list[str]] = None) -> int:
parser = argparse.ArgumentParser(description=__doc__)
parser.add_argument("sources", nargs="+", type=Path)
parser.add_argument("--grammar", type=Path, default=_GRAMMAR_PATH)
args = parser.parse_args(argv)
grammar = tmlanguage.Grammar.load(args.grammar)
for source_path in args.sources:
out_path = source_path.with_suffix(".svg")
out_path.write_text(
render(grammar, source_path.read_text(encoding="utf-8")),
encoding="utf-8",
)
print(f"wrote {out_path}")
return 0
if __name__ == "__main__":
sys.exit(main())
+405
View File
@@ -0,0 +1,405 @@
#!/usr/bin/env python3
"""A minimal TextMate grammar tokenizer.
TextMate grammars are normally run by Oniguruma, which we cannot depend on
hermetically. Carbon's grammar happens to use no Oniguruma-only regex syntax,
so `re` compiles its regexes unchanged. That is necessary but not sufficient,
since the two engines can still read shared syntax differently, so what
establishes that this reproduces VS Code's output is `conformance_test.py`,
which tokenizes the repository with both and compares. `check_regex_dialect`
catches the half of that a hermetic test can reach: if it fails, the grammar
has left the shared subset and this tokenizer can no longer be trusted.
Only the grammar features Carbon uses are implemented: `match`, `begin`/`end`
with captures and `contentName`, `include` into the repository, and `\\N`
backreferences from `begin` into `end`.
"""
__copyright__ = """
Part of the Carbon Language project, under the Apache License v2.0 with LLVM
Exceptions. See /LICENSE for license information.
SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
"""
import json
import re
from pathlib import Path
from typing import Any, Iterator, NamedTuple, Optional
# Regex constructs Oniguruma supports and `re` either rejects or interprets
# differently. A grammar using any of these would invalidate this tokenizer.
_FOREIGN_SYNTAX = {
"possessive quantifier": r"(?:[*+?}])\+",
"atomic group": r"\(\?>",
r"\G anchor": r"\\G",
r"\h horizontal space": r"\\[hH]",
"conditional": r"\(\?\(",
"named backreference": r"\\k<",
"variable-length lookbehind": r"\(\?<[=!][^)]*[*+]",
}
# Every key a TextMate grammar can put a regex under. `match`, `begin`, and
# `end` are the three this tokenizer runs; an editor also runs the folding
# markers, so they are checked for dialect even though nothing here reads them.
_REGEX_KEYS = (
"match",
"begin",
"end",
"foldingStartMarker",
"foldingStopMarker",
)
class Token(NamedTuple):
"""A scope assignment covering `[start, end)` of line `line`.
`scopes` runs outermost first, starting with the grammar's own scope name,
so the last entry is the most specific. A theme matches from there
outward, taking the first entry it has a color for.
"""
line: int
start: int
end: int
scopes: list[str]
class Rule(NamedTuple):
"""An entry of the region stack: an open `begin`/`end`, or the grammar.
The grammar's own entry sits at the bottom with an `end_re` of `None`,
since nothing closes it.
"""
scopes: list[str]
content_scopes: list[str]
end_re: Optional[re.Pattern[str]]
end_captures: dict[str, Any]
patterns: list[dict[str, Any]]
class _RuleMatch(NamedTuple):
"""A rule that matched, and where it matched.
`kind` names the grammar key the matching regex came from: `"end"` for
the open region's own `end`, in which case `pattern` is empty, or
`"match"` or `"begin"` for one of the rules in the region's `patterns`.
`match` is always a real match; it is what `kind` describes.
"""
kind: str
pattern: dict[str, Any]
match: re.Match[str]
class Grammar:
"""A parsed TextMate grammar, ready to tokenize with."""
def __init__(self, raw: dict[str, Any]) -> None:
self.raw = raw
self.scope_name: str = raw.get("scopeName", "")
self._repository: dict[str, Any] = raw.get("repository", {})
self._compiled: dict[str, re.Pattern[str]] = {}
@staticmethod
def load(path: Path) -> "Grammar":
with path.open(encoding="utf-8") as f:
return Grammar(json.load(f))
def compile(self, regex: str) -> re.Pattern[str]:
compiled = self._compiled.get(regex)
if compiled is None:
compiled = self._compiled[regex] = re.compile(regex)
return compiled
def resolve(
self,
patterns: Optional[list[dict[str, Any]]],
active: frozenset[str] = frozenset(),
) -> list[dict[str, Any]]:
"""Flattens `include` directives into a list of concrete rules.
A `name` on the repository entry itself is deliberately dropped: VS
Code inlines an include-only rule's patterns without pushing its scope,
so honoring it here would disagree with the real tokenizer. `active`
breaks a cycle between mutually including entries.
An include of a different grammar, such as `source.cpp`, contributes
nothing: we tokenize Carbon, and embedded regions are left to whatever
scope their `contentName` assigns.
"""
resolved: list[dict[str, Any]] = []
for pattern in patterns or []:
target = pattern.get("include")
if target is None:
resolved.append(pattern)
elif target.startswith("#"):
name = target[1:]
if name in active:
continue
entry = self._repository.get(name, {})
resolved.extend(
self.resolve(entry.get("patterns"), active | {name})
)
elif target == "$self":
resolved.extend(self.resolve(self.raw.get("patterns"), active))
return resolved
def initial_stack(self) -> list[Rule]:
base = [self.scope_name]
return [
Rule(base, base, None, {}, self.resolve(self.raw.get("patterns")))
]
def all_regexes(self) -> Iterator[tuple[str, str]]:
"""Yields every `(key, regex)` the grammar holds, for validation.
A grammar keeps regexes only under the keys in `_REGEX_KEYS`, so
finding them all means walking every dictionary in it and picking
those keys out. `key` says which one it was, which is all a message
needs to point at the right place.
"""
def walk(node: Any) -> Iterator[tuple[str, str]]:
if isinstance(node, dict):
for key in _REGEX_KEYS:
value = node.get(key)
if isinstance(value, str):
yield key, value
for value in node.values():
yield from walk(value)
elif isinstance(node, list):
for value in node:
yield from walk(value)
yield from walk(self.raw)
def check_regex_dialect(grammar: Grammar) -> list[str]:
"""Returns a message per regex `re` cannot stand in for Oniguruma on."""
problems: list[str] = []
for key, regex in grammar.all_regexes():
# A `\N` backreference is substituted before compiling, so do the
# same here with an arbitrary value before validating.
probe = re.sub(r"\\\d", "x", regex)
try:
re.compile(probe)
except re.error as e:
problems.append(f"`{key}` regex does not compile: {regex}: {e}")
continue
for name, foreign in _FOREIGN_SYNTAX.items():
if re.search(foreign, regex):
problems.append(
f"`{key}` regex uses {name}, which `re` does not share "
f"with Oniguruma: {regex}"
)
return problems
def _substitute_backrefs(regex: str, begin_match: re.Match[str]) -> str:
"""Replaces `\\N` in an `end` with the text `begin` captured, as VS Code
does before compiling the `end` regex."""
def replace(ref: re.Match[str]) -> str:
return re.escape(begin_match.group(int(ref.group(1))) or "")
return re.sub(r"\\(\d)", replace, regex)
def _append_token(
tokens: list[Token], linenum: int, start: int, end: int, scopes: list[str]
) -> None:
"""Appends a token, unless it would be empty.
Callers append the text between two things without first checking that
there is any, and about a quarter of the time there is none, so the check
lives here rather than at every call.
"""
if end > start:
tokens.append(Token(linenum, start, end, scopes))
def _append_capture_tokens(
tokens: list[Token],
linenum: int,
match: re.Match[str],
captures: dict[str, Any],
scopes: list[str],
) -> None:
"""Appends the tokens for one match, splitting it at its capture groups.
`captures` maps a group number, written as a string, to the scope the
group's text takes on top of `scopes`; group `"0"` is the whole match. The
tokens tile the match with no gaps: text not covered by a listed group is
still appended, under `scopes` alone.
"""
if not captures:
_append_token(tokens, linenum, match.start(), match.end(), scopes)
return
pos = match.start()
for group in range((match.re.groups or 0) + 1):
spec = captures.get(str(group))
# Skip a group the grammar does not name, one that did not
# participate in the match (`start` is then -1), and one that lies
# behind text already appended, since tokens come out in order.
if spec is None or match.start(group) < pos:
continue
if match.start(group) == match.end(group):
continue
_append_token(tokens, linenum, pos, match.start(group), scopes)
_append_token(
tokens,
linenum,
match.start(group),
match.end(group),
scopes + [spec["name"]],
)
pos = match.end(group)
_append_token(tokens, linenum, pos, match.end(), scopes)
def _push_scope(
scopes: list[str], pattern: dict[str, Any], key: str
) -> list[str]:
"""Adds the scope `pattern[key]` names, if it names one."""
name = pattern.get(key)
return scopes + [name] if name is not None else scopes
def _find_earliest(
grammar: Grammar, rule: Rule, text: str, pos: int
) -> Optional[_RuleMatch]:
"""Finds which of `rule`'s regexes matches soonest at or after `pos`.
The open region's own `end` is tried first and ties are broken towards
whatever was tried earlier, which gives TextMate's two ordering rules: a
region that can close here closes here, and otherwise the first rule
listed in the grammar wins.
"""
best: Optional[_RuleMatch] = None
if rule.end_re is not None:
match = rule.end_re.search(text, pos)
if match is not None:
best = _RuleMatch("end", {}, match)
for pattern in rule.patterns:
# The key a regex came from is what the rule does with it, so take
# both from the same lookup.
if (regex := pattern.get("match")) is not None:
kind = "match"
elif (regex := pattern.get("begin")) is not None:
kind = "begin"
else:
continue
match = grammar.compile(regex).search(text, pos)
if match is None:
continue
if best is not None and match.start() >= best.match.start():
continue
best = _RuleMatch(kind, pattern, match)
return best
def tokenize_line(
grammar: Grammar, linenum: int, text: str, stack: list[Rule]
) -> tuple[list[Token], list[Rule]]:
"""Tokenizes one line, given the regions open when it starts.
`text` must carry its trailing newline: VS Code tokenizes a line together
with its terminator, so that newline gets a token of its own, and carrying
it is what keeps the two token streams identical. `stack` is the chain of
`begin`/`end` regions open at the start of the line, outermost first and
never empty: its first entry is the grammar itself. The stack returned is
the one open at the start of the next line, which is how a region spans
lines.
"""
tokens: list[Token] = []
pos = 0
# Counts region transitions that consumed nothing, which make no progress.
stalls = 0
while pos <= len(text):
rule = stack[-1]
found = _find_earliest(grammar, rule, text, pos)
if found is None:
break
# Text before the match belongs to the region containing it.
_append_token(
tokens, linenum, pos, found.match.start(), rule.content_scopes
)
if found.kind == "end":
_append_capture_tokens(
tokens, linenum, found.match, rule.end_captures, rule.scopes
)
stack = stack[:-1]
else:
scopes = _push_scope(rule.content_scopes, found.pattern, "name")
captures = "captures" if found.kind == "match" else "beginCaptures"
_append_capture_tokens(
tokens,
linenum,
found.match,
found.pattern.get(captures, {}),
scopes,
)
if found.kind == "begin":
stack = stack + [
Rule(
scopes,
_push_scope(scopes, found.pattern, "contentName"),
grammar.compile(
_substitute_backrefs(
found.pattern["end"], found.match
)
),
found.pattern.get("endCaptures", {}),
grammar.resolve(found.pattern.get("patterns")),
)
]
if found.match.end() > found.match.start():
pos = found.match.end()
elif found.kind == "match":
# A `match` that consumed nothing would match there forever, so
# step over a character.
pos = found.match.start() + 1
else:
# Entering or leaving a region is progress in itself, and the
# character stays available to the region now on top: a lookahead
# `end` such as `(?=[\[\(])` depends on that.
pos = found.match.start()
stalls += 1
# The bound is arbitrary; it only has to exceed the transitions a
# real line could ask for. Reaching it means a rule opens and
# closes forever, which is a grammar bug: say so rather than
# silently truncating the line.
if stalls > len(text) + 64:
raise RuntimeError(
f"line {linenum} stopped making progress at offset {pos}: "
f"rule {found.pattern!r} neither consumes nor terminates"
)
# Whatever is left over, including the newline, belongs to the region the
# line ends inside of.
_append_token(tokens, linenum, pos, len(text), stack[-1].content_scopes)
return tokens, stack
def split_lines(text: str) -> list[str]:
"""Splits a file into lines the way an editor numbers them.
Terminators are not kept on the lines, and a file ending in a newline
yields an empty final line, which is the blank line an editor shows there.
Not `str.splitlines`: that also breaks on `\\f`, `\\v`, and a handful of
Unicode separators, which a TextMate grammar sees as ordinary characters
within a line, and it drops that final empty line.
"""
return text.split("\n")
def tokenize(grammar: Grammar, text: str) -> Iterator[Token]:
"""Tokenizes a whole file."""
stack = grammar.initial_stack()
for linenum, line in enumerate(split_lines(text)):
tokens, stack = tokenize_line(grammar, linenum, line + "\n", stack)
yield from tokens