Skip to content
Closed
Show file tree
Hide file tree
Changes from 1 commit
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
Prev Previous commit
Next Next commit
Zig: Add error state for unterminated string
  • Loading branch information
techee committed May 13, 2025
commit 65c3fd9b10774b242ca17eb99b2e4b6a2f82820b
1 change: 1 addition & 0 deletions include/LexicalStyles.iface
Original file line number Diff line number Diff line change
Expand Up @@ -2430,6 +2430,7 @@ val SCE_ZIG_KW_SECONDARY=14
val SCE_ZIG_KW_TERTIARY=15
val SCE_ZIG_KW_TYPE=16
val SCE_ZIG_IDENTIFIER_STRING=17
val SCE_ZIG_STRINGEOL=18
# Lexical states for SCLEX_NIX
lex Nix=SCLEX_NIX SCE_NIX_
val SCE_NIX_DEFAULT=0
Expand Down
1 change: 1 addition & 0 deletions include/SciLexer.h
Original file line number Diff line number Diff line change
Expand Up @@ -2170,6 +2170,7 @@
#define SCE_ZIG_KW_TERTIARY 15
#define SCE_ZIG_KW_TYPE 16
#define SCE_ZIG_IDENTIFIER_STRING 17
#define SCE_ZIG_STRINGEOL 18
#define SCE_NIX_DEFAULT 0
#define SCE_NIX_COMMENTLINE 1
#define SCE_NIX_COMMENTBLOCK 2
Expand Down
13 changes: 13 additions & 0 deletions lexers/LexZig.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,7 @@ LexicalClass lexicalClasses[] = {
15, "SCE_ZIG_KW_TERTIARY", "identifier", "Tertiary keywords",
16, "SCE_ZIG_KW_TYPE", "identifier", "Global types",
17, "SCE_ZIG_IDENTIFIER_STRING", "identifier", "Identifier using @\"\" syntax",
18, "SCE_ZIG_STRINGEOL", "error literal string", "End of line where string is not closed",
};

class LexerZig : public DefaultLexer {
Expand Down Expand Up @@ -262,6 +263,10 @@ void LexerZig::Lex(Sci_PositionU startPos, Sci_Position lengthDoc, int initStyle
int lineState = 0;
EscapeSequence escSeq;

if (initStyle == SCE_ZIG_STRINGEOL) {
initStyle = SCE_ZIG_DEFAULT;
}

StyleContext sc(startPos, lengthDoc, initStyle, styler);

while (sc.More()) {
Expand Down Expand Up @@ -311,6 +316,8 @@ void LexerZig::Lex(Sci_PositionU startPos, Sci_Position lengthDoc, int initStyle
case SCE_ZIG_IDENTIFIER_STRING:
if (sc.atLineStart) {
sc.SetState(SCE_ZIG_DEFAULT);
} else if (sc.atLineEnd && sc.state != SCE_ZIG_MULTISTRING) {
sc.ChangeState(SCE_ZIG_STRINGEOL);
} else if (sc.ch == '\\' && sc.state != SCE_ZIG_MULTISTRING) {
escSeq.resetEscapeState(sc.state, sc.chNext);
sc.SetState(SCE_ZIG_ESCAPECHAR);
Expand All @@ -326,6 +333,12 @@ void LexerZig::Lex(Sci_PositionU startPos, Sci_Position lengthDoc, int initStyle
}
break;

case SCE_ZIG_STRINGEOL:
if (sc.atLineStart) {
sc.SetState(SCE_ZIG_DEFAULT);
}
break;

case SCE_ZIG_ESCAPECHAR:
if (escSeq.atEscapeEnd(sc.ch)) {
if (escSeq.brace && sc.ch == '}') {
Expand Down
4 changes: 4 additions & 0 deletions test/examples/zig/AllStyles.zig
Original file line number Diff line number Diff line change
Expand Up @@ -288,3 +288,7 @@ const Color = enum {
@"really red",
};
const color: Color = .@"really red";

const s1 = "Unterminated string
const s2 = 'Unterminated character
const s3 = @"Unterminated identifier string
4 changes: 4 additions & 0 deletions test/examples/zig/AllStyles.zig.folded
Original file line number Diff line number Diff line change
Expand Up @@ -288,4 +288,8 @@
0 401 401 | @"really red",
0 401 400 | };
0 400 400 const color: Color = .@"really red";
0 400 400
0 400 400 const s1 = "Unterminated string
0 400 400 const s2 = 'Unterminated character
0 400 400 const s3 = @"Unterminated identifier string
0 400 0
4 changes: 4 additions & 0 deletions test/examples/zig/AllStyles.zig.styled
Original file line number Diff line number Diff line change
Expand Up @@ -288,3 +288,7 @@
{17}@"really red"{5},{0}
{5}};{0}
{13}const{0} {10}color{5}:{0} {10}Color{0} {5}={0} {5}.{17}@"really red"{5};{0}

{13}const{0} {10}s1{0} {5}={0} {18}"Unterminated string
{13}const{0} {10}s2{0} {5}={0} {18}'Unterminated character
{13}const{0} {10}s3{0} {5}={0} {18}@"Unterminated identifier string