Skip to content

Commit

Permalink
<WIP> language: preliminary support for separation of statements
Browse files Browse the repository at this point in the history
  • Loading branch information
ScrelliCopter committed Sep 11, 2023
1 parent 2ee1565 commit 0881924
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 12 deletions.
37 changes: 26 additions & 11 deletions parser/src/main/kotlin/gay/pizza/pork/parser/Parser.kt
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,8 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
private fun <T> collect(
peeking: TokenType,
consuming: TokenType? = null,
expecting: Array<TokenType>? = null,
expectingIgnoreType: IgnoreType = IgnoreType.Default,
read: () -> T
): List<T> {
val items = mutableListOf<T>()
Expand All @@ -354,6 +356,9 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
if (consuming != null) {
next(consuming)
}
if (expecting != null) {
expect(expectingIgnoreType, *expecting)
}
items.add(item)
}
return items
Expand Down Expand Up @@ -381,8 +386,8 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
} else false
}

private fun expect(vararg types: TokenType): Token {
val token = next()
private fun expect(ignoreType: IgnoreType, vararg types: TokenType): Token {
val token = next(ignoreType)
if (!types.contains(token.type)) {
throw RuntimeException(
"Expected one of ${types.joinToString(", ")}" +
Expand All @@ -392,24 +397,26 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
return token
}

private fun expect(vararg types: TokenType): Token = expect(IgnoreType.Default, *types)

private fun <T: Node> expect(vararg types: TokenType, consume: (Token) -> T): T =
consume(expect(*types))

private fun next(): Token {
private fun next(ignoreType: IgnoreType = IgnoreType.Default): Token {
while (true) {
val token = unsanitizedSource.next()
attribution.push(token)
if (ignoredByParser(token.type)) {
if (ignoredByParser(ignoreType, token.type)) {
continue
}
return token
}
}

private fun peek(): Token {
private fun peek(ignoreType: IgnoreType = IgnoreType.Default): Token {
while (true) {
val token = unsanitizedSource.peek()
if (ignoredByParser(token.type)) {
if (ignoredByParser(ignoreType, token.type)) {
attribution.push(token)
unsanitizedSource.next()
continue
Expand All @@ -423,10 +430,18 @@ class Parser(source: PeekableSource<Token>, val attribution: NodeAttribution) {
return attribution.exit(block())
}

private fun ignoredByParser(type: TokenType): Boolean = when (type) {
TokenType.BlockComment -> true
TokenType.LineComment -> true
TokenType.Whitespace -> true
else -> false
private fun ignoredByParser(ignoreType: IgnoreType, type: TokenType): Boolean = ignoreType.ignored(type)

private enum class IgnoreType {
ExpressionList, Default;

fun ignored(type: TokenType): Boolean = when {
type == TokenType.BlockComment -> true
type == TokenType.LineComment -> true
type == TokenType.Whitespace -> true
type == TokenType.Semicolon && this == Default -> true
type == TokenType.Line && this == Default -> true
else -> false
}
}
}
4 changes: 3 additions & 1 deletion parser/src/main/kotlin/gay/pizza/pork/parser/TokenType.kt
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,9 @@ enum class TokenType(vararg properties: TokenTypeProperty) {
Native(ManyChars("native"), KeywordFamily),
Let(ManyChars("let"), KeywordFamily),
Var(ManyChars("var"), KeywordFamily),
Whitespace(CharConsumer { it == ' ' || it == '\r' || it == '\n' || it == '\t' }),
Whitespace(CharConsumer { it == ' ' || it == '\t' || it == '\r' }), // JAAJ WAS HERE
Semicolon(SingleChar(';')),
Line(SingleChar('\n')),
BlockComment(CommentFamily),
LineComment(CommentFamily),
EndOfFile;
Expand Down

0 comments on commit 0881924

Please sign in to comment.