scair

package scair

Members list

Packages

package scair.analysis
package scair.clair

Clair is a Scala library for creating custom IRs. It provides the end-user with a way to define custom IRs packaged in a Dialect (MLIR word for DSL) using Scala syntax and then generate the IR code in a target language (currently limited to Scala).

Clair is a Scala library for creating custom IRs. It provides the end-user with a way to define custom IRs packaged in a Dialect (MLIR word for DSL) using Scala syntax and then generate the IR code in a target language (currently limited to Scala).

To define a custom Dialect, the user needs to define an IR and package it into a Dialect object as shown in the code below with the Sample dialect example:

import scair.ir.*
import scair.clair.macros.*
import scair.dialects.builtin.*
import scair.dialects.cmath.*
import scair.enums.I32Enum
import fastparse.*
import scair.parse.*

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   defining a custom I32 enum attribute   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

enum Color(name: String) extends I32Enum(name):
 case Red extends Color("red")
 case Green extends Color("green")
 case Blue extends Color("blue")

case class EnumOperation(
   val color: Color
) extends DerivedOperation["arith.enum_op"] derives OpDefs

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   defining a custom data attribute   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

given AttributeCompanion[SampleData]:
 override def name: String = "sample"

 override def parse[$: P](using Parser) =
   "#sample<" ~ CharsWhile(_ != '>').!.map(SampleData.apply) ~ ">"

case class SampleData(val d: String)
   extends DataAttribute[String]("sample", d)

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   defining a custom attribute   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

case class SampleAttr(
   val value: FloatType
) extends DerivedAttribute["sample.sample_attr"] derives AttrDefs

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   defining a custom type attribute   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

case class SampleType(
   val value: FloatType
) extends DerivedAttribute["sample.sample_type"]
   with TypeAttribute derives AttrDefs

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   defining custom operations   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

case class SampOp1(
   e1: Seq[Operand[IntegerAttr]],
   e2: Result[Attribute],
   e3: Region,
) extends DerivedOperation["sample.sampop1"] derives OpDefs

case class SampOp2(
   e1: Seq[Operand[Complex]],
   e2: Result[Attribute],
) extends DerivedOperation["sample.sampop2"] derives OpDefs

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   constraints over operation components   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

import scair.constraints.{*, given}

type T = Var["T"]
val i32 = IntegerType(IntData(32), Signless)

case class MulIEq(
   lhs: Operand[IntegerType !> EqAttr[i32.type]],
   rhs: Operand[IntegerType !> EqAttr[i32.type]],
   result: Result[IntegerType],
) extends DerivedOperation["samplecnstr.mulieq"] derives OpDefs

case class MulIVar(
   lhs: Operand[IntegerType !> T],
   rhs: Operand[IntegerType !> T],
   result: Result[IntegerType],
) extends DerivedOperation["samplecnstr.mulivar"] derives OpDefs

/*≡≡=---=≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡≡=---=≡≡*\
||   packaging into a dialect   ||
\*≡==----=≡≡≡≡≡≡≡≡≡≡≡≡≡≡=----==≡*/

val Sample =
 summonDialect[(SampleAttr, SampleType, SampleData), (SampOp1, SampOp1)]

To include the defined Dialect in ScaIR, the user should put the file into the dialects directory in the scair project, and package it appropriately.

Attributes

See also

scair.dialects.cmathgen

package scair.dialects
package scair.enums
package scair.helpers
package scair.ir
package scair.irdl
package scair.parse
package scair.passes
package scair.print
package scair.tools
package scair.utils
package scair.verify

Type members

Classlikes

class MLContext()

Attributes

Supertypes
class Object
trait Matchable
class Any