Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 12 additions & 6 deletions grammars/csharp.tmLanguage
Original file line number Diff line number Diff line change
Expand Up @@ -4799,13 +4799,13 @@
<key>begin</key>
<string>(?x)
(?:
(?:(\bscoped)\s+(?:(\bref)\s+)?)? # scoped local
(?:(\bref)\s+(?:(\breadonly)\s+)?)? # ref local
(?:(\bscoped)\s+(?:(\bref)\s+)?)? # scoped ref local
(?:(\bref)\s+(?:(\breadonly|scoped)\s+)?)? # ref readonly or ref scoped local
(\bvar\b)|
(?&lt;type_name&gt;
(?:
(?:scoped\s+(?:ref\s+)?)? # scoped local
(?:ref\s+(?:readonly\s+)?)? # ref local
(?:scoped\s+(?:ref\s+)?)? # scoped ref local
(?:ref\s+(?:(?:readonly|scoped)\s+)?)? # ref, optionally followed by readonly or scoped
(?:
(?:(?&lt;identifier&gt;@?[_[:alpha:]][_[:alnum:]]*)\s*\:\:\s*)? # alias-qualification
(?&lt;name_and_type_args&gt; # identifier + type arguments (if any)
Expand Down Expand Up @@ -4850,7 +4850,7 @@
<key>4</key>
<dict>
<key>name</key>
<string>storage.modifier.readonly.cs</string>
<string>storage.modifier.$4.cs</string>
</dict>
<key>5</key>
<dict>
Expand Down Expand Up @@ -7298,6 +7298,7 @@
<key>match</key>
<string>(?x)
(?:(?:\b(scoped|ref|params|out|in|this)\b)\s+)?
(?:(?:\b(ref|scoped|readonly)\b)\s+)?
(?&lt;type_name&gt;
(?:
(?:ref\s+)? # ref return
Expand Down Expand Up @@ -7330,6 +7331,11 @@
<string>storage.modifier.$1.cs</string>
</dict>
<key>2</key>
<dict>
<key>name</key>
<string>storage.modifier.$2.cs</string>
</dict>
<key>3</key>
<dict>
<key>patterns</key>
<array>
Expand All @@ -7339,7 +7345,7 @@
</dict>
</array>
</dict>
<key>7</key>
<key>8</key>
<dict>
<key>name</key>
<string>entity.name.variable.parameter.cs</string>
Expand Down
15 changes: 9 additions & 6 deletions grammars/csharp.tmLanguage.cson
Original file line number Diff line number Diff line change
Expand Up @@ -2931,13 +2931,13 @@ repository:
begin: '''
(?x)
(?:
(?:(\\bscoped)\\s+(?:(\\bref)\\s+)?)? # scoped local
(?:(\\bref)\\s+(?:(\\breadonly)\\s+)?)? # ref local
(?:(\\bscoped)\\s+(?:(\\bref)\\s+)?)? # scoped ref local
(?:(\\bref)\\s+(?:(\\breadonly|scoped)\\s+)?)? # ref readonly or ref scoped local
(\\bvar\\b)|
(?<type_name>
(?:
(?:scoped\\s+(?:ref\\s+)?)? # scoped local
(?:ref\\s+(?:readonly\\s+)?)? # ref local
(?:scoped\\s+(?:ref\\s+)?)? # scoped ref local
(?:ref\\s+(?:(?:readonly|scoped)\\s+)?)? # ref, optionally followed by readonly or scoped
(?:
(?:(?<identifier>@?[_[:alpha:]][_[:alnum:]]*)\\s*\\:\\:\\s*)? # alias-qualification
(?<name_and_type_args> # identifier + type arguments (if any)
Expand Down Expand Up @@ -2971,7 +2971,7 @@ repository:
"3":
name: "storage.modifier.ref.cs"
"4":
name: "storage.modifier.readonly.cs"
name: "storage.modifier.$4.cs"
"5":
name: "storage.type.var.cs"
"6":
Expand Down Expand Up @@ -4401,6 +4401,7 @@ repository:
match: '''
(?x)
(?:(?:\\b(scoped|ref|params|out|in|this)\\b)\\s+)?
(?:(?:\\b(ref|scoped|readonly)\\b)\\s+)?
(?<type_name>
(?:
(?:ref\\s+)? # ref return
Expand Down Expand Up @@ -4430,12 +4431,14 @@ repository:
"1":
name: "storage.modifier.$1.cs"
"2":
name: "storage.modifier.$2.cs"
"3":
patterns: [
{
include: "#type"
}
]
"7":
"8":
name: "entity.name.variable.parameter.cs"
"argument-list":
begin: "\\("
Expand Down
24 changes: 13 additions & 11 deletions src/csharp.tmLanguage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -1739,13 +1739,13 @@ repository:
begin: |-
(?x)
(?:
(?:(\bscoped)\s+(?:(\bref)\s+)?)? # scoped local
(?:(\bref)\s+(?:(\breadonly)\s+)?)? # ref local
(?:(\bscoped)\s+(?:(\bref)\s+)?)? # scoped ref local
(?:(\bref)\s+(?:(\breadonly|scoped)\s+)?)? # ref readonly or ref scoped local
(\bvar\b)|
(?<type_name>
(?:
(?:scoped\s+(?:ref\s+)?)? # scoped local
(?:ref\s+(?:readonly\s+)?)? # ref local
(?:scoped\s+(?:ref\s+)?)? # scoped ref local
(?:ref\s+(?:(?:readonly|scoped)\s+)?)? # ref, optionally followed by readonly or scoped
(?:
(?:(?<identifier>@?[_[:alpha:]][_[:alnum:]]*)\s*\:\:\s*)? # alias-qualification
(?<name_and_type_args> # identifier + type arguments (if any)
Expand Down Expand Up @@ -1774,7 +1774,7 @@ repository:
1: { name: storage.modifier.scoped.cs }
2: { name: storage.modifier.ref.cs }
3: { name: storage.modifier.ref.cs }
4: { name: storage.modifier.readonly.cs }
4: { name: storage.modifier.$4.cs }
5: { name: storage.type.var.cs }
6:
patterns:
Expand Down Expand Up @@ -2835,6 +2835,7 @@ repository:
match: |-
(?x)
(?:(?:\b(scoped|ref|params|out|in|this)\b)\s+)?
(?:(?:\b(ref|scoped|readonly)\b)\s+)?
(?<type_name>
(?:
(?:ref\s+)? # ref return
Expand All @@ -2861,14 +2862,15 @@ repository:
(\g<identifier>)
captures:
1: { name: storage.modifier.$1.cs }
2:
2: { name: storage.modifier.$2.cs }
3:
patterns:
- include: '#type'
# '3': ?<identifier> is a sub-expression. It's final value is not considered.
# '4': ?<name_and_type_args> is a sub-expression. It's final value is not considered.
# '5': ?<type_args> is a sub-expression. It's final value is not considered.
# '6': ?<tuple> is a sub-expression. It's final value is not considered.
7: { name: entity.name.variable.parameter.cs }
# '4': ?<identifier> is a sub-expression. It's final value is not considered.
# '5': ?<name_and_type_args> is a sub-expression. It's final value is not considered.
# '6': ?<type_args> is a sub-expression. It's final value is not considered.
# '7': ?<tuple> is a sub-expression. It's final value is not considered.
8: { name: entity.name.variable.parameter.cs }

argument-list:
begin: \(
Expand Down
38 changes: 38 additions & 0 deletions test/local.tests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -169,6 +169,44 @@ describe("Locals", () => {
]);
});

it("ref scoped local", async () => {
const input = Input.InMethod(`ref scoped Span<int> x = stackalloc int[42];`);
const tokens = await tokenize(input);

tokens.should.deep.equal([
Token.Keyword.Modifier.Ref,
Token.Keyword.Modifier.Scoped,
Token.Type("Span"),
Token.Punctuation.TypeParameter.Begin,
Token.PrimitiveType.Int,
Token.Punctuation.TypeParameter.End,
Token.Identifier.LocalName("x"),
Token.Operator.Assignment,
Token.Operator.Expression.StackAlloc,
Token.PrimitiveType.Int,
Token.Punctuation.OpenBracket,
Token.Literal.Numeric.Decimal("42"),
Token.Punctuation.CloseBracket,
Token.Punctuation.Semicolon
]);
});

it("ref scoped local var", async () => {
const input = Input.InMethod(`ref scoped var x = ref y;`);
const tokens = await tokenize(input);

tokens.should.deep.equal([
Token.Keyword.Modifier.Ref,
Token.Keyword.Modifier.Scoped,
Token.Keyword.Definition.Var,
Token.Identifier.LocalName("x"),
Token.Operator.Assignment,
Token.Keyword.Modifier.Ref,
Token.Variable.ReadWrite("y"),
Token.Punctuation.Semicolon
]);
});

it("ref local", async () => {
const input = Input.InMethod(`ref int x;`);
const tokens = await tokenize(input);
Expand Down
31 changes: 31 additions & 0 deletions test/method.tests.ts
Original file line number Diff line number Diff line change
Expand Up @@ -857,6 +857,37 @@ public static Span<T> CreateSpan<T>(scoped ref T reference, int length) {}
]);
});

it("ref scoped parameter in parameter list (#306)", async () => {
const input = Input.InClass(`
public static Span<T> CreateSpan<T>(ref scoped T reference, int length) {}
`);
const tokens = await tokenize(input);

tokens.should.deep.equal([
Token.Keyword.Modifier.Public,
Token.Keyword.Modifier.Static,
Token.Type("Span"),
Token.Punctuation.TypeParameter.Begin,
Token.Type("T"),
Token.Punctuation.TypeParameter.End,
Token.Identifier.MethodName("CreateSpan"),
Token.Punctuation.TypeParameter.Begin,
Token.Identifier.TypeParameterName("T"),
Token.Punctuation.TypeParameter.End,
Token.Punctuation.OpenParen,
Token.Keyword.Modifier.Ref,
Token.Keyword.Modifier.Scoped,
Token.Type("T"),
Token.Identifier.ParameterName("reference"),
Token.Punctuation.Comma,
Token.PrimitiveType.Int,
Token.Identifier.ParameterName("length"),
Token.Punctuation.CloseParen,
Token.Punctuation.OpenBrace,
Token.Punctuation.CloseBrace
]);
});

it("expression body and type constraint (issue #74)", async () => {
const input = Input.InClass(`
T id1<T>(T a) => a;
Expand Down