diff --git a/build.sc b/build.sc index f69d616330f..d267f0fec87 100644 --- a/build.sc +++ b/build.sc @@ -1,221 +1,148 @@ import mill._ import mill.scalalib._ +import mill.scalalib.TestModule._ import mill.scalalib.publish._ import mill.scalalib.scalafmt._ import coursier.maven.MavenRepository -import $ivy.`com.lihaoyi::mill-contrib-buildinfo:$MILL_VERSION` -import mill.contrib.buildinfo.BuildInfo - -object chisel3 extends mill.Cross[chisel3CrossModule]("2.13.10", "2.12.17") - -// The following stanza is searched for and used when preparing releases. -// Please retain it. -// Provide a managed dependency on X if -DXVersion="" is supplied on the command line. -val defaultVersions = Map( - "firrtl" -> "1.6-SNAPSHOT", -) - -def getVersion(dep: String, org: String = "edu.berkeley.cs") = { - val version = sys.env.getOrElse(dep + "Version", defaultVersions(dep)) - ivy"$org::$dep:$version" -} -// Do not remove the above logic, it is needed by the release automation +import $file.common object v { - val firrtl = getVersion("firrtl") - val chiseltest = ivy"edu.berkeley.cs::chiseltest:0.6-SNAPSHOT" - val scalatest = ivy"org.scalatest::scalatest:3.2.15" - val scalacheck = ivy"org.scalatestplus::scalacheck-1-14:3.2.2.0" + val pluginScalaCrossVersions = Seq( + // scalamacros paradise version used is not published for 2.12.0 and 2.12.1 + "2.12.2", + "2.12.3", + // 2.12.4 is broken in newer versions of Zinc: https://github.com/sbt/sbt/issues/6838 + "2.12.5", + "2.12.6", + "2.12.7", + "2.12.8", + "2.12.9", + "2.12.10", + "2.12.11", + "2.12.12", + "2.12.13", + "2.12.14", + "2.12.15", + "2.12.16", + "2.12.17", + "2.13.0", + "2.13.1", + "2.13.2", + "2.13.3", + "2.13.4", + "2.13.5", + "2.13.6", + "2.13.7", + "2.13.8", + "2.13.9", + "2.13.10" + ) + val scalaCrossVersions = Seq( + "2.12.17", + "2.13.10" + ) val osLib = ivy"com.lihaoyi::os-lib:0.8.1" val upickle = ivy"com.lihaoyi::upickle:2.0.0" val macroParadise = ivy"org.scalamacros:::paradise:2.1.1" -} - -// Since chisel contains submodule core and macros, a CommonModule is needed -trait CommonModule extends CrossSbtModule with PublishModule with ScalafmtModule { - def firrtlModule: Option[PublishModule] = None - - def firrtlIvyDeps = if (firrtlModule.isEmpty) - Agg( - v.firrtl - ) - else Agg.empty[Dep] - - def chiseltestModule: Option[PublishModule] = None - - def chiseltestIvyDeps = if (chiseltestModule.isEmpty) - Agg( - v.chiseltest - ) - else Agg.empty[Dep] - - override def moduleDeps = super.moduleDeps ++ firrtlModule - - override def ivyDeps = super.ivyDeps() ++ Agg( - v.osLib, - v.upickle - ) ++ firrtlIvyDeps - - def publishVersion = "3.6-SNAPSHOT" + val scalatest = ivy"org.scalatest::scalatest:3.2.15" + val scalacheck = ivy"org.scalatestplus::scalacheck-1-14:3.2.2.0" + val json4s = ivy"org.json4s::json4s-native:4.0.6" + val dataclass = ivy"io.github.alexarchambault::data-class:0.2.5" + val commonText = ivy"org.apache.commons:commons-text:1.10.0" + val scopt = ivy"com.github.scopt::scopt:3.7.1" - // 2.12.10 -> Array("2", "12", "10") -> "12" -> 12 - protected def majorVersion = crossScalaVersion.split('.')(1).toInt + def scalaReflect(scalaVersion: String) = ivy"org.scala-lang:scala-reflect:$scalaVersion" - override def repositories = super.repositories ++ Seq( - MavenRepository("https://oss.sonatype.org/content/repositories/snapshots"), - MavenRepository("https://oss.sonatype.org/content/repositories/releases") - ) + def scalaCompiler(scalaVersion: String) = ivy"org.scala-lang:scala-compiler:$scalaVersion" - override def scalacOptions = T { - super.scalacOptions() ++ Agg( - "-deprecation", - "-feature" - ) ++ (if (majorVersion == 13) Agg("-Ymacro-annotations") else Agg.empty[String]) - } - - override def compileIvyDeps = if (majorVersion == 13) super.compileIvyDeps else Agg(v.macroParadise) - - override def scalacPluginIvyDeps = if (majorVersion == 13) super.compileIvyDeps else Agg(v.macroParadise) - - def pomSettings = PomSettings( - description = artifactName(), - organization = "edu.berkeley.cs", - url = "https://www.chisel-lang.org", - licenses = Seq(License.`Apache-2.0`), - versionControl = VersionControl.github("freechipsproject", "chisel3"), - developers = Seq( - Developer("jackbackrack", "Jonathan Bachrach", "https://eecs.berkeley.edu/~jrb/") - ) - ) + def scalaLibrary(scalaVersion: String) = ivy"org.scala-lang:scala-library:$scalaVersion" } +private def majorScalaVersion(scalaVersion: String) = scalaVersion.split('.')(1).toInt -class chisel3CrossModule(val crossScalaVersion: String) extends CommonModule with BuildInfo { - m => - - /** Default behavior assumes `build.sc` in the upper path of `src`. - * This override makes `src` folder stay with `build.sc` in the same directory, - * If chisel3 is used as a sub-project, [[millSourcePath]] should be overridden to the folder where `src` located. - */ - override def millSourcePath = super.millSourcePath / os.up - - override def mainClass = T { - Some("chisel3.stage.ChiselMain") - } - - override def moduleDeps = super.moduleDeps ++ Seq(macros, core) - - override def scalacPluginClasspath = T { - super.scalacPluginClasspath() ++ Agg( - plugin.jar() - ) - } - - override def scalacOptions = T { - super.scalacOptions() ++ Agg(s"-Xplugin:${plugin.jar().path}") - } +object firrtl extends mill.Cross[firrtl](v.scalaCrossVersions: _*) - object stdlib extends CommonModule { - override def moduleDeps = super.moduleDeps ++ Agg(m) +class firrtl(val crossScalaVersion: String) + extends common.FirrtlModule + with CrossSbtModule + with ScalafmtModule { + def macroParadiseIvy: Option[Dep] = if (majorScalaVersion(crossScalaVersion) < 13) Some(v.macroParadise) else None - override def millSourcePath = m.millSourcePath / "stdlib" + def osLibModuleIvy = v.osLib - override def crossScalaVersion = m.crossScalaVersion + def json4sIvy = v.json4s - override def scalacPluginClasspath = T { m.scalacPluginClasspath() } - } + def dataclassIvy = v.dataclass - object test extends Tests with TestModule.ScalaTest with ScalafmtModule { - override def scalacPluginClasspath = T { m.scalacPluginClasspath() } + def commonTextIvy = v.commonText - override def ivyDeps = m.ivyDeps() ++ Agg( - v.scalatest, - v.scalacheck - ) - - override def moduleDeps = super.moduleDeps - } - - object `integration-tests` extends Tests with TestModule.ScalaTest with ScalafmtModule { - override def sources = T.sources(millSourcePath / "integration-tests" / "src" / "test" / "scala") - override def ivyDeps = m.ivyDeps() ++ Agg( - v.scalatest, - v.scalacheck - ) ++ m.chiseltestIvyDeps + def scoptIvy = v.scopt +} - override def moduleDeps = super.moduleDeps ++ Seq(stdlib) ++ chiseltestModule - } +object macros extends mill.Cross[macros](v.scalaCrossVersions: _*) - override def buildInfoPackageName = Some("chisel3") +class macros(val crossScalaVersion: String) + extends common.MacrosModule + with CrossSbtModule + with ScalafmtModule { + def scalaReflectIvy = v.scalaReflect(crossScalaVersion) - override def buildInfoMembers = T { - Map( - "buildInfoPackage" -> artifactName(), - "version" -> publishVersion(), - "scalaVersion" -> scalaVersion() - ) - } + def macroParadiseIvy: Option[Dep] = if (majorScalaVersion(crossScalaVersion) < 13) Some(v.macroParadise) else None +} - object macros extends CommonModule { +object core extends mill.Cross[core](v.scalaCrossVersions: _*) - /** millOuterCtx.segment.pathSegments didn't detect error here. */ - override def millSourcePath = m.millSourcePath / "macros" +class core(val crossScalaVersion: String) + extends common.CoreModule + with CrossSbtModule + with ScalafmtModule { + def firrtlModule = firrtl(crossScalaVersion) - override def crossScalaVersion = m.crossScalaVersion + def macrosModule = macros(crossScalaVersion) - override def firrtlModule = m.firrtlModule - } + def macroParadiseIvy: Option[Dep] = if (majorScalaVersion(crossScalaVersion) < 13) Some(v.macroParadise) else None - object core extends CommonModule { + def osLibModuleIvy = v.osLib - /** millOuterCtx.segment.pathSegments didn't detect error here. */ - override def millSourcePath = m.millSourcePath / "core" + def upickleModuleIvy = v.upickle +} - override def crossScalaVersion = m.crossScalaVersion +object plugin extends mill.Cross[plugin](v.pluginScalaCrossVersions: _*) - override def moduleDeps = super.moduleDeps ++ Seq(macros) +class plugin(val crossScalaVersion: String) + extends common.PluginModule + with CrossSbtModule + with ScalafmtModule { + def scalaLibraryIvy = v.scalaLibrary(crossScalaVersion) - override def firrtlModule = m.firrtlModule + def scalaReflectIvy = v.scalaReflect(crossScalaVersion) - def scalacOptions = T { - super.scalacOptions() ++ Seq( - "-deprecation", - "-explaintypes", - "-feature", - "-language:reflectiveCalls", - "-unchecked", - "-Xcheckinit", - "-Xlint:infer-any" - ) - } + def scalaCompilerIvy: Dep = v.scalaCompiler(crossScalaVersion) +} - override def generatedSources = T { - Seq(generatedBuildInfo()._2) - } - } +object chisel extends mill.Cross[chisel](v.scalaCrossVersions: _*) - object plugin extends CommonModule { +class chisel(val crossScalaVersion: String) + extends common.ChiselModule + with CrossSbtModule + with ScalafmtModule { + override def millSourcePath = super.millSourcePath / os.up - /** millOuterCtx.segment.pathSegments didn't detect error here. */ - override def millSourcePath = m.millSourcePath / "plugin" + def macrosModule = macros(crossScalaVersion) - override def crossScalaVersion = m.crossScalaVersion + def coreModule = core(crossScalaVersion) - override def firrtlModule = m.firrtlModule + def pluginModule = plugin(crossScalaVersion) - override def ivyDeps = Agg( - ivy"${scalaOrganization()}:scala-library:$crossScalaVersion" - ) ++ (if (majorVersion == 13) Agg(ivy"${scalaOrganization()}:scala-compiler:$crossScalaVersion") - else Agg.empty[Dep]) + def macroParadiseIvy = if (majorScalaVersion(crossScalaVersion) < 13) Some(v.macroParadise) else None +} - def scalacOptions = T { - Seq( - "-Xfatal-warnings" - ) - } +object stdlib extends mill.Cross[stdlib](v.scalaCrossVersions: _*) - override def artifactName = "chisel3-plugin" - } +class stdlib(val crossScalaVersion: String) + extends common.StdLibModule + with CrossSbtModule + with ScalafmtModule { + def chiselModule = chisel(crossScalaVersion) - // make mill publish sbt compatible package - override def artifactName = "chisel3" + def pluginModule = plugin(crossScalaVersion) } diff --git a/common.sc b/common.sc new file mode 100644 index 00000000000..2491c8ed3a5 --- /dev/null +++ b/common.sc @@ -0,0 +1,135 @@ +// This file only records the recipe to + +import mill._ +import mill.scalalib._ +import $ivy.`com.lihaoyi::mill-contrib-buildinfo:` +import mill.contrib.buildinfo.BuildInfo + +// 12 or 13 +private def majorScalaVersion(scalaVersion: String) = scalaVersion.split('.')(1).toInt + +trait HasMacroAnnotations + extends ScalaModule { + def macroParadiseIvy: Option[Dep] + + def scalacPluginIvyDeps = super.scalacPluginIvyDeps() ++ macroParadiseIvy + + override def scalacOptions = T { + if (scalaVersion() == 12) { + require(macroParadiseIvy.isDefined, "macroParadiseIvy must be defined for Scala 2.12") + } + super.scalacOptions() ++ + (if (majorScalaVersion(scalaVersion()) == 13) Agg("-Ymacro-annotations") else Agg.empty[String]) + } +} + +trait MacrosModule + extends ScalaModule + with HasMacroAnnotations { + def scalaReflectIvy: Dep + + override def ivyDeps = super.ivyDeps() ++ Some(scalaReflectIvy) + + override def scalacPluginIvyDeps = super.scalacPluginIvyDeps() ++ macroParadiseIvy +} + +trait FirrtlModule + extends ScalaModule + with HasMacroAnnotations { + def osLibModuleIvy: Dep + + def json4sIvy: Dep + + def dataclassIvy: Dep + + def commonTextIvy: Dep + + def scoptIvy: Dep + + override def ivyDeps = super.ivyDeps() ++ Agg( + osLibModuleIvy, + json4sIvy, + dataclassIvy, + commonTextIvy, + scoptIvy + ) +} + +trait CoreModule + extends ScalaModule + with HasMacroAnnotations + with BuildInfo { + def firrtlModule: FirrtlModule + + def macrosModule: MacrosModule + + def osLibModuleIvy: Dep + + def upickleModuleIvy: Dep + + override def moduleDeps = super.moduleDeps ++ Seq(macrosModule, firrtlModule) + + override def ivyDeps = super.ivyDeps() ++ Agg( + osLibModuleIvy, + upickleModuleIvy + ) + + override def buildInfoPackageName = Some("chisel3") + + def buildVersion = T("build-from-source") + + override def buildInfoMembers = T { + Map( + "buildInfoPackage" -> artifactName(), + "version" -> buildVersion(), + "scalaVersion" -> scalaVersion() + ) + } +} + +trait PluginModule + extends ScalaModule { + def scalaLibraryIvy: Dep + + def scalaReflectIvy: Dep + + def scalaCompilerIvy: Dep + + override def ivyDeps = super.ivyDeps() ++ Agg(scalaLibraryIvy, scalaReflectIvy, scalaCompilerIvy) +} + +trait HasChiselPlugin + extends ScalaModule { + def pluginModule: PluginModule + + override def scalacOptions = T { + super.scalacOptions() ++ Agg(s"-Xplugin:${pluginModule.jar().path}") + } + + override def scalacPluginClasspath = T { + super.scalacPluginClasspath() ++ Agg( + pluginModule.jar() + ) + } +} + +trait StdLibModule + extends ScalaModule + with HasChiselPlugin { + def chiselModule: ChiselModule + + override def moduleDeps = super.moduleDeps ++ Seq(chiselModule) +} + +trait ChiselModule + extends ScalaModule + with HasChiselPlugin + with HasMacroAnnotations { + def macrosModule: MacrosModule + + def coreModule: CoreModule + + override def scalacPluginClasspath = T(super.scalacPluginClasspath() ++ Agg(pluginModule.jar())) + + override def moduleDeps = super.moduleDeps ++ Seq(macrosModule, coreModule) +}