Merge branch 'ast' into parser

This commit is contained in:
Gleb Koval 2025-02-01 20:47:05 +00:00
commit a110225c49
Signed by: cyclane
GPG Key ID: 15E168A8B332382C
6 changed files with 28 additions and 37 deletions

View File

@ -3,3 +3,4 @@ runner.dialect = scala3
binPack.literalsExclude = [] binPack.literalsExclude = []
indent.infix.excludeRegex = "^$" indent.infix.excludeRegex = "^$"
maxColumn = 100

View File

@ -3,6 +3,7 @@
// dependencies // dependencies
//> using dep com.github.j-mie6::parsley::5.0.0-M10 //> using dep com.github.j-mie6::parsley::5.0.0-M10
//> using dep com.github.j-mie6::parsley-cats::1.3.0
//> using dep com.lihaoyi::os-lib::0.11.3 //> using dep com.lihaoyi::os-lib::0.11.3
//> using dep com.github.scopt::scopt::4.1.0 //> using dep com.github.scopt::scopt::4.1.0
//> using test.dep org.scalatest::scalatest::3.2.19 //> using test.dep org.scalatest::scalatest::3.2.19

View File

@ -1,6 +1,7 @@
package wacc package wacc
import parsley.generic._ import parsley.generic._
import cats.data.NonEmptyList
object ast { object ast {
// Expressions // Expressions
@ -24,10 +25,8 @@ object ast {
case object PairLiter extends Expr6 with ParserBridge0[PairLiter.type] case object PairLiter extends Expr6 with ParserBridge0[PairLiter.type]
case class Ident(v: String) extends Expr6 with LValue case class Ident(v: String) extends Expr6 with LValue
object Ident extends ParserBridge1[String, Ident] object Ident extends ParserBridge1[String, Ident]
case class ArrayElem(name: Ident, indices: List[Expr]) case class ArrayElem(name: Ident, indices: NonEmptyList[Expr]) extends Expr6 with LValue
extends Expr6 object ArrayElem extends ParserBridge2[Ident, NonEmptyList[Expr], ArrayElem]
with LValue
object ArrayElem extends ParserBridge2[Ident, List[Expr], ArrayElem]
case class Parens(expr: Expr) extends Expr6 case class Parens(expr: Expr) extends Expr6
object Parens extends ParserBridge1[Expr, Parens] object Parens extends ParserBridge1[Expr, Parens]
@ -78,31 +77,26 @@ object ast {
case object BoolType extends BaseType with ParserBridge0[BoolType.type] case object BoolType extends BaseType with ParserBridge0[BoolType.type]
case object CharType extends BaseType with ParserBridge0[CharType.type] case object CharType extends BaseType with ParserBridge0[CharType.type]
case object StringType extends BaseType with ParserBridge0[StringType.type] case object StringType extends BaseType with ParserBridge0[StringType.type]
case class ArrayType(elemType: Type, dimensions: Int) case class ArrayType(elemType: Type, dimensions: Int) extends Type with PairElemType
extends Type
with PairElemType
object ArrayType extends ParserBridge2[Type, Int, ArrayType] object ArrayType extends ParserBridge2[Type, Int, ArrayType]
case class PairType(fst: PairElemType, snd: PairElemType) extends Type case class PairType(fst: PairElemType, snd: PairElemType) extends Type
object PairType extends ParserBridge2[PairElemType, PairElemType, PairType] object PairType extends ParserBridge2[PairElemType, PairElemType, PairType]
sealed trait PairElemType sealed trait PairElemType
case object UntypedPairType case object UntypedPairType extends PairElemType with ParserBridge0[UntypedPairType.type]
extends PairElemType
with ParserBridge0[UntypedPairType.type]
// waccadoodledo // waccadoodledo
case class Program(funcs: List[FuncDecl], main: List[Stmt]) case class Program(funcs: List[FuncDecl], main: NonEmptyList[Stmt])
object Program extends ParserBridge2[List[FuncDecl], List[Stmt], Program] object Program extends ParserBridge2[List[FuncDecl], NonEmptyList[Stmt], Program]
// Function Definitions // Function Definitions
case class FuncDecl( case class FuncDecl(
returnType: Type, returnType: Type,
name: Ident, name: Ident,
params: List[Param], params: List[Param],
body: List[Stmt] body: NonEmptyList[Stmt]
) )
object FuncDecl object FuncDecl extends ParserBridge4[Type, Ident, List[Param], NonEmptyList[Stmt], FuncDecl]
extends ParserBridge4[Type, Ident, List[Param], List[Stmt], FuncDecl]
case class Param(paramType: Type, name: Ident) case class Param(paramType: Type, name: Ident)
object Param extends ParserBridge2[Type, Ident, Param] object Param extends ParserBridge2[Type, Ident, Param]
@ -124,13 +118,12 @@ object ast {
object Exit extends ParserBridge1[Expr, Exit] object Exit extends ParserBridge1[Expr, Exit]
case class Print(expr: Expr, newline: Boolean) extends Stmt case class Print(expr: Expr, newline: Boolean) extends Stmt
object Print extends ParserBridge2[Expr, Boolean, Print] object Print extends ParserBridge2[Expr, Boolean, Print]
case class If(cond: Expr, thenStmt: List[Stmt], elseStmt: List[Stmt]) case class If(cond: Expr, thenStmt: NonEmptyList[Stmt], elseStmt: NonEmptyList[Stmt]) extends Stmt
extends Stmt object If extends ParserBridge3[Expr, NonEmptyList[Stmt], NonEmptyList[Stmt], If]
object If extends ParserBridge3[Expr, List[Stmt], List[Stmt], If] case class While(cond: Expr, body: NonEmptyList[Stmt]) extends Stmt
case class While(cond: Expr, body: List[Stmt]) extends Stmt object While extends ParserBridge2[Expr, NonEmptyList[Stmt], While]
object While extends ParserBridge2[Expr, List[Stmt], While] case class Block(stmt: NonEmptyList[Stmt]) extends Stmt
case class Block(stmt: List[Stmt]) extends Stmt object Block extends ParserBridge1[NonEmptyList[Stmt], Block]
object Block extends ParserBridge1[List[Stmt], Block]
sealed trait LValue sealed trait LValue

View File

@ -12,22 +12,19 @@ object lexer {
), ),
symbolDesc = SymbolDesc.plain.copy( symbolDesc = SymbolDesc.plain.copy(
hardKeywords = Set( hardKeywords = Set(
"begin", "end", "is", "skip", "if", "then", "else", "fi", "while", "do", "begin", "end", "is", "skip", "if", "then", "else", "fi", "while", "do", "done", "read",
"done", "read", "free", "return", "exit", "print", "println", "true", "free", "return", "exit", "print", "println", "true", "false", "int", "bool", "char",
"false", "int", "bool", "char", "string", "pair", "newpair", "fst", "string", "pair", "newpair", "fst", "snd", "call", "chr", "ord", "len", "null"
"snd", "call", "chr", "ord", "len", "null"
), ),
hardOperators = Set( hardOperators = Set(
"+", "-", "*", "/", "%", ">", "<", ">=", "<=", "==", "!=", "&&", "||", "+", "-", "*", "/", "%", ">", "<", ">=", "<=", "==", "!=", "&&", "||", "!"
"!"
) )
), ),
spaceDesc = SpaceDesc.plain.copy( spaceDesc = SpaceDesc.plain.copy(
lineCommentStart = "#" lineCommentStart = "#"
), ),
textDesc = TextDesc.plain.copy( textDesc = TextDesc.plain.copy(
graphicCharacter = graphicCharacter = Basic(c => c >= ' ' && c != '\\' && c != '\'' && c != '"'),
Basic(c => c >= ' ' && c != '\\' && c != '\'' && c != '"'),
escapeSequences = EscapeDesc.plain.copy( escapeSequences = EscapeDesc.plain.copy(
literals = Set('\\', '"', '\''), literals = Set('\\', '"', '\''),
mapping = Map( mapping = Map(

View File

@ -2,9 +2,11 @@ package wacc
import parsley.Result import parsley.Result
import parsley.Parsley import parsley.Parsley
import parsley.Parsley.{atomic, many, pure, some} import parsley.Parsley.{atomic, many, pure}
import parsley.combinator.{countSome, sepBy, sepBy1} import parsley.combinator.{countSome, sepBy}
import parsley.expr.{precedence, SOps, InfixL, InfixN, InfixR, Prefix, Atoms} import parsley.expr.{precedence, SOps, InfixL, InfixN, InfixR, Prefix, Atoms}
import parsley.cats.combinator.{sepBy1, some}
import cats.data.NonEmptyList
object parser { object parser {
import lexer.implicits.implicitSymbol import lexer.implicits.implicitSymbol
@ -83,7 +85,7 @@ object parser {
`<stmt>` <~ "end" `<stmt>` <~ "end"
) )
private lazy val `<param>` = Param(`<type>`, `<ident>`) private lazy val `<param>` = Param(`<type>`, `<ident>`)
private lazy val `<stmt>`: Parsley[List[Stmt]] = private lazy val `<stmt>`: Parsley[NonEmptyList[Stmt]] =
sepBy1(`<basic-stmt>`, ";") sepBy1(`<basic-stmt>`, ";")
private lazy val `<basic-stmt>` = private lazy val `<basic-stmt>` =
(Skip from atomic("skip")) (Skip from atomic("skip"))

View File

@ -4,10 +4,7 @@ import org.scalatest.{ParallelTestExecution, BeforeAndAfterAll}
import org.scalatest.flatspec.AnyFlatSpec import org.scalatest.flatspec.AnyFlatSpec
import org.scalatest.Inspectors.forEvery import org.scalatest.Inspectors.forEvery
class ParallelExamplesSpec class ParallelExamplesSpec extends AnyFlatSpec with BeforeAndAfterAll with ParallelTestExecution {
extends AnyFlatSpec
with BeforeAndAfterAll
with ParallelTestExecution {
val files = val files =
allWaccFiles("wacc-examples/valid").map { p => allWaccFiles("wacc-examples/valid").map { p =>
(p.toString, List(0)) (p.toString, List(0))