Co expression (#181)

This commit is contained in:
Dmitry Kurinskiy 2021-06-24 11:01:59 +03:00 committed by GitHub
parent c48bf5c488
commit bbf47628c6
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
15 changed files with 67 additions and 10 deletions

View File

@ -50,7 +50,14 @@ object AirGen extends LogSupport {
case SeqRes =>
Eval later ops.toList.reduceLeftOption(SeqGen).getOrElse(NullGen)
case ParRes =>
Eval later ops.toList.reduceLeftOption(ParGen).getOrElse(NullGen)
Eval later (ops.toList match {
case o :: Nil => ParGen(o, NullGen)
case _ =>
ops.toList.reduceLeftOption(ParGen).getOrElse {
warn("ParRes with no children converted to Null")
NullGen
}
})
case XorRes =>
Eval later (ops.toList match {
case o :: Nil => XorGen(o, NullGen)

View File

@ -24,7 +24,7 @@ val airframeLog = "org.wvlet.airframe" %% "airframe-log" % airframeLogV
name := "aqua-hll"
val commons = Seq(
baseAquaVersion := "0.1.7",
baseAquaVersion := "0.1.8",
version := baseAquaVersion.value + "-" + sys.env.getOrElse("BUILD_NUMBER", "SNAPSHOT"),
scalaVersion := dottyVersion,
libraryDependencies ++= Seq(

View File

@ -111,7 +111,8 @@ object FuncOp {
object RightAssocSemi extends Semigroup[FuncOp] {
override def combine(x: FuncOp, y: FuncOp): FuncOp = (x.tree.head, y.tree.head) match {
case (ParTag, ParTag) => FuncOp(y.tree.copy(tail = (x.tree.tail, y.tree.tail).mapN(_ ++ _)))
case (_: ParGroupTag, ParTag) =>
FuncOp(y.tree.copy(tail = (x.tree.tail, y.tree.tail).mapN(_ ++ _)))
case (XorTag, XorTag) =>
FuncOp(y.tree.copy(tail = (x.tree.tail, y.tree.tail).mapN(_ ++ _)))
case (XorTag.LeftBiased, XorTag) =>

View File

@ -64,6 +64,9 @@ object FuncOps {
.map(FuncOp(_))
)
def co(ops: FuncOp*): FuncOp =
FuncOp.wrap(ParTag.Detach, seq(ops: _*))
def xor(left: FuncOp, right: FuncOp): FuncOp =
FuncOp.node(XorTag, Chain(left, right))

View File

@ -18,7 +18,7 @@ object PathFinder extends LogSupport {
!isExit &&
to.leftSiblings.isEmpty &&
to.moveUp.exists(_.pathOn == to.pathOn) &&
!to.parentTag.contains(ParTag)
!to.parentTag.exists(_.isInstanceOf[ParGroupTag])
if (wasHandled) {
debug("Was handled")

View File

@ -44,14 +44,14 @@ case class RawCursor(tree: NonEmptyList[ChainZipper[FuncOp.Tree]])
lazy val lastExecuted: Option[RawCursor] = tag match {
case XorTag => toFirstChild.flatMap(_.lastExecuted)
case _: SeqGroupTag => toLastChild.flatMap(_.lastExecuted)
case ParTag => None
case _: ParGroupTag => None
case _: NoExecTag => None
case _ => Some(this)
}
lazy val firstExecuted: Option[RawCursor] = tag match {
case _: SeqGroupTag => toLastChild.flatMap(_.lastExecuted)
case ParTag => None
case _: ParGroupTag => None
case _: NoExecTag => None
case _ => Some(this)
}
@ -95,7 +95,7 @@ case class RawCursor(tree: NonEmptyList[ChainZipper[FuncOp.Tree]])
}
lazy val pathToNext: Chain[ValueModel] = parentTag.fold(Chain.empty[ValueModel]) {
case ParTag =>
case _: ParGroupTag =>
val exports = FuncOp(current).exportsVarNames.value
if (exports.nonEmpty && checkNamesUsedLater(exports))
seqNext.fold(Chain.empty[ValueModel])(nxt =>

View File

@ -35,12 +35,16 @@ sealed trait NoExecTag extends RawTag
sealed trait GroupTag extends RawTag
sealed trait SeqGroupTag extends GroupTag
sealed trait ParGroupTag extends GroupTag
case object SeqTag extends SeqGroupTag
case object ParTag extends GroupTag
case object ParTag extends ParGroupTag {
case object Detach extends ParGroupTag
}
case object XorTag extends SeqGroupTag {
case object LeftBiased extends GroupTag
case object LeftBiased extends SeqGroupTag
}
case class XorParTag(xor: FuncOp, par: FuncOp) extends RawTag

View File

@ -54,7 +54,7 @@ object Topology extends LogSupport {
case _: OnTag => SeqRes
case MatchMismatchTag(a, b, s) => MatchMismatchRes(a, b, s)
case ForTag(item, iter) => FoldRes(item, iter)
case ParTag => ParRes
case ParTag | ParTag.Detach => ParRes
case XorTag | XorTag.LeftBiased => XorRes
case NextTag(item) => NextRes(item)
case CallServiceTag(serviceId, funcName, call) =>

View File

@ -0,0 +1,19 @@
package aqua.parser.expr
import aqua.parser.Expr
import aqua.parser.lexer.Token
import aqua.parser.lift.LiftParser
import aqua.parser.lift.LiftParser._
import cats.Comonad
import cats.parse.Parser
import Token.`co`
case class CoExpr[F[_]](point: Token[F]) extends Expr[F](CoExpr, point)
object CoExpr extends Expr.Prefix {
override def continueWith: List[Expr.Lexem] = ParExpr.continueWith
override def p[F[_]: LiftParser: Comonad]: Parser[Expr[F]] =
`co`.lift.map(Token.lift[F, Unit](_)).map(CoExpr(_))
}

View File

@ -30,6 +30,7 @@ object FuncExpr extends Expr.AndIndented {
ElseOtherwiseExpr ::
CatchExpr ::
ParExpr ::
CoExpr ::
DeclareStreamExpr ::
Nil

View File

@ -18,6 +18,8 @@ object IfExpr extends Expr.AndIndented {
CallArrowExpr ::
AbilityIdExpr ::
AssignmentExpr ::
Expr.defer(ParExpr) ::
Expr.defer(CoExpr) ::
Expr.defer(TryExpr) ::
Expr.defer(ForExpr) ::
Expr.defer(IfExpr) ::

View File

@ -17,6 +17,7 @@ object OnExpr extends Expr.AndIndented {
AbilityIdExpr ::
AssignmentExpr ::
ParExpr ::
CoExpr ::
Expr.defer(TryExpr) ::
Expr.defer(ForExpr) ::
Expr.defer(IfExpr) ::

View File

@ -42,6 +42,7 @@ object Token {
val `try`: P[Unit] = P.string("try")
val `catch`: P[Unit] = P.string("catch")
val `par`: P[Unit] = P.string("par")
val `co`: P[Unit] = P.string("co")
val `:` : P[Unit] = P.char(':')
val ` : ` : P[Unit] = P.char(':').surroundedBy(` `.?)

View File

@ -35,6 +35,7 @@ object ExprSem {
case expr: CatchExpr[F] => new CatchSem(expr).program[G]
case expr: ElseOtherwiseExpr[F] => new ElseOtherwiseSem(expr).program[G]
case expr: ParExpr[F] => new ParSem(expr).program[G]
case expr: CoExpr[F] => new CoSem(expr).program[G]
case expr: ReturnExpr[F] => new ReturnSem(expr).program[G]
case expr: ServiceExpr[F] => new ServiceSem(expr).program[G]
case expr: RootExpr[F] => new RootSem(expr).program[G]

View File

@ -0,0 +1,17 @@
package aqua.semantics.expr
import aqua.model.Model
import aqua.model.func.raw.{FuncOp, ParTag}
import aqua.parser.expr.CoExpr
import aqua.semantics.Prog
import cats.free.Free
class CoSem[F[_]](val expr: CoExpr[F]) extends AnyVal {
def program[Alg[_]]: Prog[Alg, Model] =
Prog.after[Alg, Model] {
case g: FuncOp =>
Free.pure[Alg, Model](FuncOp.wrap(ParTag.Detach, g))
case g => Free.pure[Alg, Model](g)
}
}