nixd
Toggle main menu visibility
Loading...
Searching...
No Matches
libnixf
src
Parse
ParseStrings.cpp
Go to the documentation of this file.
1
#include "
Parser.h
"
2
3
using namespace
nixf
;
4
using namespace
nixf::detail
;
5
6
std::shared_ptr<Interpolation>
Parser::parseInterpolation
() {
7
Token
TokDollarCurly = peek();
8
assert(TokDollarCurly.
kind
() == tok_dollar_curly);
9
consume();
// ${
10
auto
Sync = withSync(tok_r_curly);
11
assert(LastToken);
12
/* with(PS_Expr) */
{
13
auto
ExprState = withState(
PS_Expr
);
14
auto
Expr
=
parseExpr
();
15
if
(!
Expr
)
16
diagNullExpr
(Diags, LastToken->rCur(),
"interpolation"
);
17
if
(ExpectResult ER = expect(tok_r_curly); ER.ok()) {
18
consume();
// }
19
}
else
{
20
ER.diag().note(Note::NK_ToMachThis, TokDollarCurly.
range
())
21
<< std::string(tok::spelling(tok_dollar_curly));
22
}
23
return
std::make_shared<Interpolation>(
24
LexerCursorRange
{TokDollarCurly.
lCur
(), LastToken->rCur()},
25
std::move(
Expr
));
26
}
// with(PS_Expr)
27
}
28
29
std::shared_ptr<Expr>
Parser::parseExprPath
() {
30
Token
Begin = peek();
31
std::vector<InterpolablePart> Fragments;
32
assert(Begin.
kind
() == tok_path_fragment);
33
LexerCursor
End;
34
/* with(PS_Path) */
{
35
auto
PathState = withState(
PS_Path
);
36
do
{
37
Token
Current = peek();
38
Fragments.emplace_back(std::string(Current.
view
()));
39
consume();
40
End = Current.
rCur
();
41
Token
Next = peek();
42
if
(Next.
kind
() == tok_path_end)
43
break
;
44
if
(Next.
kind
() == tok_dollar_curly) {
45
if
(
auto
Expr
=
parseInterpolation
())
46
Fragments.emplace_back(std::move(
Expr
));
47
continue
;
48
}
49
assert(
false
&&
"should be path_end or ${"
);
50
}
while
(
true
);
51
}
52
auto
Parts = std::make_shared<InterpolatedParts>(
53
LexerCursorRange
{Begin.
lCur
(), End}, std::move(Fragments));
54
return
std::make_shared<ExprPath>(
LexerCursorRange
{Begin.
lCur
(), End},
55
std::move(Parts));
56
}
57
58
std::shared_ptr<InterpolatedParts>
Parser::parseStringParts
() {
59
std::vector<InterpolablePart> Parts;
60
LexerCursor
PartsBegin = peek().lCur();
61
while
(
true
) {
62
switch
(
Token
Tok = peek(0); Tok.
kind
()) {
63
case
tok_dollar_curly: {
64
if
(
auto
Expr
=
parseInterpolation
())
65
Parts.emplace_back(std::move(
Expr
));
66
continue
;
67
}
68
case
tok_string_part: {
69
// If this is a part of string, just push it.
70
Parts.emplace_back(std::string(Tok.view()));
71
consume();
72
continue
;
73
}
74
case
tok_string_escape: {
75
// Process escape sequence and add the unescaped character to Parts.
76
// The token view contains the full escape sequence (e.g., "\\n", "\\\"")
77
std::string_view EscapeSeq = Tok.view();
78
std::string Unescaped;
79
if
(EscapeSeq.size() >= 2) {
80
char
Escaped = EscapeSeq[1];
81
switch
(Escaped) {
82
case
'n'
:
83
Unescaped =
"\n"
;
84
break
;
85
case
'r'
:
86
Unescaped =
"\r"
;
87
break
;
88
case
't'
:
89
Unescaped =
"\t"
;
90
break
;
91
default
:
92
// For \\, \", \$, and any other escape, just use the character itself
93
Unescaped = Escaped;
94
break
;
95
}
96
}
97
if
(!Unescaped.empty())
98
Parts.emplace_back(std::move(Unescaped));
99
consume();
100
continue
;
101
}
102
default
:
103
assert(LastToken &&
"LastToken should be set in `parseString`"
);
104
return
std::make_shared<InterpolatedParts>(
105
LexerCursorRange
{PartsBegin, LastToken->rCur()},
106
std::move(Parts));
// TODO!
107
}
108
}
109
}
110
111
std::shared_ptr<ExprString>
Parser::parseString
(
bool
IsIndented) {
112
Token
Quote = peek();
113
TokenKind QuoteKind = IsIndented ? tok_quote2 : tok_dquote;
114
std::string QuoteSpel(tok::spelling(QuoteKind));
115
assert(Quote.
kind
() == QuoteKind &&
"should be a quote"
);
116
// Consume the quote and so make the look-ahead buf empty.
117
consume();
118
auto
Sync = withSync(QuoteKind);
119
assert(LastToken &&
"LastToken should be set after consume()"
);
120
/* with(PS_String / PS_IndString) */
{
121
auto
StringState = withState(IsIndented ?
PS_IndString
:
PS_String
);
122
std::shared_ptr<InterpolatedParts> Parts =
parseStringParts
();
123
if
(ExpectResult ER = expect(QuoteKind); ER.ok()) {
124
consume();
125
return
std::make_shared<ExprString>(
126
LexerCursorRange
{Quote.
lCur
(), ER.tok().rCur()}, std::move(Parts));
127
}
else
{
// NOLINT(readability-else-after-return)
128
ER.diag().note(Note::NK_ToMachThis, Quote.
range
()) << QuoteSpel;
129
return
std::make_shared<ExprString>(
130
LexerCursorRange
{Quote.
lCur
(), Parts->rCur()}, std::move(Parts));
131
}
132
133
}
// with(PS_String / PS_IndString)
134
}
nixf::Expr
Definition
Basic.h:70
nixf::LexerCursorRange
Definition
Range.h:105
nixf::LexerCursor
A point in the source file.
Definition
Range.h:57
nixf::Parser::parseInterpolation
std::shared_ptr< Interpolation > parseInterpolation()
Parse interpolations.
Definition
ParseStrings.cpp:6
nixf::Parser::parseExpr
std::shared_ptr< Expr > parseExpr()
Definition
ParseExpr.cpp:76
nixf::Parser::PS_String
@ PS_String
Definition
src/Parse/Parser.h:35
nixf::Parser::PS_IndString
@ PS_IndString
Definition
src/Parse/Parser.h:36
nixf::Parser::PS_Expr
@ PS_Expr
Definition
src/Parse/Parser.h:34
nixf::Parser::PS_Path
@ PS_Path
Definition
src/Parse/Parser.h:37
nixf::Parser::parseStringParts
std::shared_ptr< InterpolatedParts > parseStringParts()
Definition
ParseStrings.cpp:58
nixf::Parser::parseString
std::shared_ptr< ExprString > parseString(bool IsIndented)
Definition
ParseStrings.cpp:111
nixf::Parser::parseExprPath
std::shared_ptr< Expr > parseExprPath()
Parse paths.
Definition
ParseStrings.cpp:29
nixf::Token
A token. With it's kind, and the range in source code.
Definition
Token.h:14
nixf::Token::lCur
LexerCursor lCur() const
Definition
Token.h:22
nixf::Token::kind
tok::TokenKind kind() const
Definition
Token.h:24
nixf::Token::range
LexerCursorRange range() const
Definition
Token.h:25
nixf::Token::rCur
LexerCursor rCur() const
Definition
Token.h:23
nixf::Token::view
std::string_view view() const
Definition
Token.h:26
nixf::detail
Definition
src/Parse/Parser.h:22
nixf::detail::diagNullExpr
Diagnostic & diagNullExpr(std::vector< Diagnostic > &Diags, LexerCursor Loc, std::string As)
Definition
ParseSupport.cpp:11
nixf
Definition
Diagnostic.h:19
Parser.h
Parser for the Nix expression language.
Generated by
1.17.0