my grammar doesn’t compile – how do you mean?
If anyone wants to see what I have so far, It’s here: Implementation by NullVoxPopuli · Pull Request #2 · NullVoxPopuli/glimdown · GitHub
git clone git@github.com:NullVoxPopuli/glimdown.git
cd glimdown
git checkout implementation
cd packages/lezer/glimmer
pnpm install
pnpm build
At the time of posting this comment, this is my grammar, and I don’t know what I’m doing wrong (note that this is different from the original post)
@detectDelim
@top Glimmer { ( Expression | BlockComment )* }
@skip { invisibles }
String { string }
ShortComment { StartShortComment Text* EndStache }
LongComment { StartLongComment Text* EndLongComment }
BlockComment { LongComment | ShortComment }
Expression {
StartStache SubExpression EndStache
| Block
}
Block {
StartBlock
Expression*
EndBlock
}
As { kw<"as"> "|" list<name> "|" }
StartBlock[closedBy=EndBlock] {
StartOpenBlockStache Function SubExpression? As? EndStache
}
EndBlock[openedBy=StartBlock] {
StartCloseBlockStache Function EndStache
}
Function { if | let | each | else | name }
SubExpression {
list<Value>
NamedArgs?
}
Value {
boolean
| null
| undefined
| Function
| String
| Number
| Invocation
| Property
| PropertyPath
}
Invocation { SubExpStart SubExpression SubExpEnd }
Pair { string "=" Value }
NamedArgs { list<Pair> }
@precedence {
invisibles @left,
Invocation @left,
Value @left
}
Argument { "@" identifier }
Property { this | Argument | identifier }
PropertyPath { Property ("." identifier)+ }
boolean {
@specialize[@name=BooleanLiteral]<identifier, "true" | "false">
}
let { kw<"let"> }
each { kw<"each"> }
if { kw<"if"> }
else { kw<"else"> }
this { kw<"this"> }
null { kw<"null"> }
undefined { kw<"undefined"> }
Number { number }
@tokens {
invisibles { @whitespace }
number { @digit+ | (@digit+ ("." @digit*))}
identifierChar { @asciiLetter | $[_$\u{a1}-\u{10ffff}] }
word { identifierChar (identifierChar | @digit)* }
name { word }
identifier { word }
Text { ![{] Text? | "{" (@eof | ![{] Text?) }
string {
"\"" !["]* "\"" |
"\'" ![']* "\'"
}
StartOpenBlockStache[closedBy="EndStache"] { "{{#" }
StartCloseBlockStache[closedBy="EndStache"] { "{{/" }
StartStache[closedBy="EndStache"] { "{{" }
EndStache[openedBy="StartStache | StartShortComment | StartOpenBlockStache | StartCloseBlockStache"] { "}}" }
StartShortComment[closedBy="EndStache"] { "{{!" }
StartLongComment[closedBy="EndLongComment"] { "{{!--" }
EndLongComment[openedBy="StartLongComment"] { "--}}" }
SubExpStart[closedBy="SubExpEnd"] { "(" }
SubExpEnd[openedBy="SubExpStart"] { ")" }
@precedence {
identifier,
name,
".", "=",
"|", "@",
SubExpStart, SubExpEnd,
StartLongComment, EndLongComment,
StartShortComment, StartOpenBlockStache, StartCloseBlockStache,
StartStache, EndStache,
invisibles,
string,
number,
Text
}
}
// Helper And Special Things
list<item> { item (invisibles+ item)* }
kw<term> { @specialize[@name={term}]<identifier, term> }
@external propSource glimmerHighlighting from './highlight'
which, when running pnpm build
, I get
Use of token invisibles conflicts with skip rule (src/glimmer.grammar 1:1)
but if I remove all invisibles
from my grammar (except for the skip rule)
(which, at the time of writing, is just in the list definition, list<item> { item (invisibles+ item)* }
→ list<item> { item (item)* }
(which I don’t think would be a valid grammar entry?) but anyway, this gives:
shift/reduce conflict between
String -> · string
and
list<Value> -> Value
With input:
StartStache Value · string …
Shared origin: SubExpression -> · list<Value> NamedArgs
via list<Value> -> Value · Value+
via Value+ -> · Value
via Value -> · String
String -> · string
another shift/reduce confilct.
but then I could delete my String { string }
rule (feels kind of redundant anyway?)
and then pnpm build
gives:
shift/reduce conflict between
Value -> · String
and
list<Value> -> Value
With input:
StartStache Value · String …
Shared origin: SubExpression -> · list<Value> NamedArgs
via list<Value> -> Value · Value+
via Value+ -> · Value
Value -> · String
and I haven’t been able to figure out a precedence definition that solves this. I think because there is no delimeter in list
anymore.
Any guidance would be super appreciated <3