summaryrefslogtreecommitdiff
path: root/cli
diff options
context:
space:
mode:
Diffstat (limited to 'cli')
-rwxr-xr-xcli/src/main/resources/scalajsc16
-rw-r--r--cli/src/main/resources/scalajsc.bat14
-rwxr-xr-xcli/src/main/resources/scalajsld10
-rw-r--r--cli/src/main/resources/scalajsld.bat8
-rwxr-xr-xcli/src/main/resources/scalajsp9
-rw-r--r--cli/src/main/resources/scalajsp.bat7
-rw-r--r--cli/src/main/scala/scala/scalajs/cli/Scalajsld.scala180
-rw-r--r--cli/src/main/scala/scala/scalajs/cli/Scalajsp.scala158
8 files changed, 402 insertions, 0 deletions
diff --git a/cli/src/main/resources/scalajsc b/cli/src/main/resources/scalajsc
new file mode 100755
index 0000000..7fd1100
--- /dev/null
+++ b/cli/src/main/resources/scalajsc
@@ -0,0 +1,16 @@
+#! /bin/sh
+
+SCALA_BIN_VER="@SCALA_BIN_VER@"
+SCALAJS_VER="@SCALAJS_VER@"
+SCALA_VER=$(scalac -version 2>&1 | grep -o '[0-9]\.[0-9][0-9]\.[0-9]')
+
+if [ "$(echo $SCALA_VER | cut -b 1-4)" != "$SCALA_BIN_VER" ]; then
+ echo "This bundle of Scala.js CLI is for $SCALA_BIN_VER. Your scala version is $SCALA_VER!" >&2
+ exit 1
+fi
+
+BASE="$(dirname $0)/.."
+PLUGIN="$BASE/lib/scalajs-compiler_$SCALA_VER-$SCALAJS_VER.jar"
+JSLIB="$BASE/lib/scalajs-library_$SCALA_BIN_VER-$SCALAJS_VER.jar"
+
+scalac -classpath "$JSLIB" "-Xplugin:$PLUGIN" "$@"
diff --git a/cli/src/main/resources/scalajsc.bat b/cli/src/main/resources/scalajsc.bat
new file mode 100644
index 0000000..767c5df
--- /dev/null
+++ b/cli/src/main/resources/scalajsc.bat
@@ -0,0 +1,14 @@
+@ECHO OFF
+set SCALA_BIN_VER=@SCALA_BIN_VER@
+set SCALAJS_VER=@SCALAJS_VER@
+
+for /F "tokens=5" %%i in (' scala -version 2^>^&1 1^>nul ') do set SCALA_VER=%%i
+
+if NOT "%SCALA_VER:~0,4%" == "%SCALA_BIN_VER%" (
+ echo "This bundle of Scala.js CLI is for %SCALA_BIN_VER%. Your scala version is %SCALA_VER%!" 1>&2
+) else (
+ set PLUGIN=%~dp0\..\lib\scalajs-compiler_%SCALA_VER%-%SCALAJS_VER%.jar
+ set JSLIB=%~dp0\..\lib\scalajs-library_%SCALA_BIN_VER%-%SCALAJS_VER%.jar
+
+ scalac -classpath "%JSLIB%" "-Xplugin:%PLUGIN%" %*
+)
diff --git a/cli/src/main/resources/scalajsld b/cli/src/main/resources/scalajsld
new file mode 100755
index 0000000..7732e2a
--- /dev/null
+++ b/cli/src/main/resources/scalajsld
@@ -0,0 +1,10 @@
+#! /bin/sh
+
+SCALA_BIN_VER="@SCALA_BIN_VER@"
+SCALAJS_VER="@SCALAJS_VER@"
+
+BASE="$(dirname $0)/.."
+CLILIB="$BASE/lib/scalajs-cli-assembly_$SCALA_BIN_VER-$SCALAJS_VER.jar"
+JSLIB="$BASE/lib/scalajs-library_$SCALA_BIN_VER-$SCALAJS_VER.jar"
+
+scala -classpath "$CLILIB" scala.scalajs.cli.Scalajsld --stdlib "$JSLIB" "$@"
diff --git a/cli/src/main/resources/scalajsld.bat b/cli/src/main/resources/scalajsld.bat
new file mode 100644
index 0000000..e915237
--- /dev/null
+++ b/cli/src/main/resources/scalajsld.bat
@@ -0,0 +1,8 @@
+@ECHO OFF
+set SCALA_BIN_VER=@SCALA_BIN_VER@
+set SCALAJS_VER=@SCALAJS_VER@
+
+set CLILIB="%~dp0\..\lib\scalajs-cli-assembly_%SCALA_BIN_VER%-%SCALAJS_VER%.jar"
+set JSLIB="%~dp0\..\lib\scalajs-library_%SCALA_BIN_VER%-%SCALAJS_VER%.jar"
+
+scala -classpath %CLILIB% scala.scalajs.cli.Scalajsld --stdlib %JSLIB% %*
diff --git a/cli/src/main/resources/scalajsp b/cli/src/main/resources/scalajsp
new file mode 100755
index 0000000..e7a6e58
--- /dev/null
+++ b/cli/src/main/resources/scalajsp
@@ -0,0 +1,9 @@
+#! /bin/sh
+
+SCALA_BIN_VER="@SCALA_BIN_VER@"
+SCALAJS_VER="@SCALAJS_VER@"
+
+BASE="$(dirname $0)/.."
+CLILIB="$BASE/lib/scalajs-cli-assembly_$SCALA_BIN_VER-$SCALAJS_VER.jar"
+
+scala -classpath "$CLILIB" scala.scalajs.cli.Scalajsp "$@"
diff --git a/cli/src/main/resources/scalajsp.bat b/cli/src/main/resources/scalajsp.bat
new file mode 100644
index 0000000..dd9745c
--- /dev/null
+++ b/cli/src/main/resources/scalajsp.bat
@@ -0,0 +1,7 @@
+@ECHO OFF
+set SCALA_BIN_VER=@SCALA_BIN_VER@
+set SCALAJS_VER=@SCALAJS_VER@
+
+set CLILIB="%~dp0\..\lib\scalajs-cli-assembly_%SCALA_BIN_VER%-%SCALAJS_VER%.jar"
+
+scala -classpath %CLILIB% scala.scalajs.cli.Scalajsp %*
diff --git a/cli/src/main/scala/scala/scalajs/cli/Scalajsld.scala b/cli/src/main/scala/scala/scalajs/cli/Scalajsld.scala
new file mode 100644
index 0000000..55e61af
--- /dev/null
+++ b/cli/src/main/scala/scala/scalajs/cli/Scalajsld.scala
@@ -0,0 +1,180 @@
+/* __ *\
+** ________ ___ / / ___ __ ____ Scala.js CLI **
+** / __/ __// _ | / / / _ | __ / // __/ (c) 2013-2014, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ |/_// /_\ \ http://scala-js.org/ **
+** /____/\___/_/ |_/____/_/ | |__/ /____/ **
+** |/____/ **
+\* */
+
+
+package scala.scalajs.cli
+
+import scala.scalajs.ir.ScalaJSVersions
+
+import scala.scalajs.tools.sem._
+import scala.scalajs.tools.io._
+import scala.scalajs.tools.logging._
+import scala.scalajs.tools.classpath._
+import scala.scalajs.tools.classpath.builder._
+
+import CheckedBehavior.Compliant
+
+import scala.scalajs.tools.optimizer.{
+ ScalaJSOptimizer,
+ ScalaJSClosureOptimizer,
+ ParIncOptimizer
+}
+
+import scala.collection.immutable.Seq
+
+import java.io.File
+import java.net.URI
+
+object Scalajsld {
+
+ case class Options(
+ cp: Seq[File] = Seq.empty,
+ output: File = null,
+ jsoutput: Option[File] = None,
+ semantics: Semantics = Semantics.Defaults,
+ noOpt: Boolean = false,
+ fullOpt: Boolean = false,
+ prettyPrint: Boolean = false,
+ sourceMap: Boolean = false,
+ relativizeSourceMap: Option[URI] = None,
+ checkIR: Boolean = false,
+ stdLib: Option[File] = None,
+ logLevel: Level = Level.Info)
+
+ def main(args: Array[String]): Unit = {
+ val parser = new scopt.OptionParser[Options]("scalajsld") {
+ head("scalajsld", ScalaJSVersions.current)
+ arg[File]("<value> ...")
+ .unbounded()
+ .action { (x, c) => c.copy(cp = c.cp :+ x) }
+ .text("Entries of Scala.js classpath to link")
+ opt[File]('o', "output")
+ .valueName("<file>")
+ .required()
+ .action { (x, c) => c.copy(output = x) }
+ .text("Output file of linker (required)")
+ opt[File]("jsoutput")
+ .valueName("<file>")
+ .abbr("jo")
+ .action { (x, c) => c.copy(jsoutput = Some(x)) }
+ .text("Concatenate all JavaScript libary dependencies to this file")
+ opt[Unit]('f', "fastOpt")
+ .action { (_, c) => c.copy(noOpt = false, fullOpt = false) }
+ .text("Optimize code (this is the default)")
+ opt[Unit]('n', "noOpt")
+ .action { (_, c) => c.copy(noOpt = true, fullOpt = false) }
+ .text("Don't optimize code")
+ opt[Unit]('u', "fullOpt")
+ .action { (_, c) => c.copy(noOpt = false, fullOpt = true) }
+ .text("Fully optimize code (uses Google Closure Compiler)")
+ opt[Unit]('p', "prettyPrint")
+ .action { (_, c) => c.copy(prettyPrint = true) }
+ .text("Pretty print full opted code (meaningful with -u)")
+ opt[Unit]('s', "sourceMap")
+ .action { (_, c) => c.copy(sourceMap = true) }
+ .text("Produce a source map for the produced code")
+ opt[Unit]("compliantAsInstanceOfs")
+ .action { (_, c) => c.copy(semantics =
+ c.semantics.withAsInstanceOfs(Compliant))
+ }
+ .text("Use compliant asInstanceOfs")
+ opt[Unit]('c', "checkIR")
+ .action { (_, c) => c.copy(checkIR = true) }
+ .text("Check IR before optimizing")
+ opt[File]('r', "relativizeSourceMap")
+ .valueName("<path>")
+ .action { (x, c) => c.copy(relativizeSourceMap = Some(x.toURI)) }
+ .text("Relativize source map with respect to given path (meaningful with -s)")
+ opt[Unit]("noStdlib")
+ .action { (_, c) => c.copy(stdLib = None) }
+ .text("Don't automatcially include Scala.js standard library")
+ opt[File]("stdlib")
+ .valueName("<scala.js stdlib jar>")
+ .hidden()
+ .action { (x, c) => c.copy(stdLib = Some(x)) }
+ .text("Location of Scala.js standard libarary. This is set by the " +
+ "runner script and automatically prepended to the classpath. " +
+ "Use -n to not include it.")
+ opt[Unit]('d', "debug")
+ .action { (_, c) => c.copy(logLevel = Level.Debug) }
+ .text("Debug mode: Show full log")
+ opt[Unit]('q', "quiet")
+ .action { (_, c) => c.copy(logLevel = Level.Warn) }
+ .text("Only show warnings & errors")
+ opt[Unit]("really-quiet")
+ .abbr("qq")
+ .action { (_, c) => c.copy(logLevel = Level.Error) }
+ .text("Only show errors")
+ version("version")
+ .abbr("v")
+ .text("Show scalajsld version")
+ help("help")
+ .abbr("h")
+ .text("prints this usage text")
+
+ override def showUsageOnError = true
+ }
+
+ for (options <- parser.parse(args, Options())) {
+ val cpFiles = options.stdLib.toList ++ options.cp
+ // Load and resolve classpath
+ val cp = PartialClasspathBuilder.build(cpFiles).resolve()
+
+ // Write JS dependencies if requested
+ for (jsout <- options.jsoutput)
+ IO.concatFiles(WritableFileVirtualJSFile(jsout), cp.jsLibs.map(_.lib))
+
+ // Link Scala.js code
+ val outFile = WritableFileVirtualJSFile(options.output)
+ if (options.fullOpt)
+ fullOpt(cp, outFile, options)
+ else
+ fastOpt(cp, outFile, options)
+ }
+ }
+
+ private def fullOpt(cp: IRClasspath,
+ output: WritableVirtualJSFile, options: Options) = {
+ import ScalaJSClosureOptimizer._
+
+ val semantics = options.semantics.optimized
+
+ new ScalaJSClosureOptimizer(semantics).optimizeCP(
+ newScalaJSOptimizer(semantics),
+ Inputs(ScalaJSOptimizer.Inputs(cp)),
+ OutputConfig(
+ output = output,
+ wantSourceMap = options.sourceMap,
+ relativizeSourceMapBase = options.relativizeSourceMap,
+ checkIR = options.checkIR,
+ prettyPrint = options.prettyPrint),
+ newLogger(options))
+ }
+
+ private def fastOpt(cp: IRClasspath,
+ output: WritableVirtualJSFile, options: Options) = {
+ import ScalaJSOptimizer._
+
+ newScalaJSOptimizer(options.semantics).optimizeCP(
+ Inputs(cp),
+ OutputConfig(
+ output = output,
+ wantSourceMap = options.sourceMap,
+ checkIR = options.checkIR,
+ disableOptimizer = options.noOpt,
+ relativizeSourceMapBase = options.relativizeSourceMap),
+ newLogger(options))
+ }
+
+ private def newLogger(options: Options) =
+ new ScalaConsoleLogger(options.logLevel)
+
+ private def newScalaJSOptimizer(semantics: Semantics) =
+ new ScalaJSOptimizer(semantics, new ParIncOptimizer(_))
+
+}
diff --git a/cli/src/main/scala/scala/scalajs/cli/Scalajsp.scala b/cli/src/main/scala/scala/scalajs/cli/Scalajsp.scala
new file mode 100644
index 0000000..0d64b93
--- /dev/null
+++ b/cli/src/main/scala/scala/scalajs/cli/Scalajsp.scala
@@ -0,0 +1,158 @@
+/* __ *\
+** ________ ___ / / ___ __ ____ Scala.js CLI **
+** / __/ __// _ | / / / _ | __ / // __/ (c) 2013-2014, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ |/_// /_\ \ http://scala-js.org/ **
+** /____/\___/_/ |_/____/_/ | |__/ /____/ **
+** |/____/ **
+\* */
+
+
+package scala.scalajs.cli
+
+import scala.scalajs.ir
+import ir.ScalaJSVersions
+import ir.Trees.{Tree, ClassDef}
+import ir.Printers.{InfoPrinter, IRTreePrinter}
+
+import scala.scalajs.tools.sem.Semantics
+import scala.scalajs.tools.javascript
+import javascript.ScalaJSClassEmitter
+import javascript.Printers.JSTreePrinter
+
+import scala.scalajs.tools.io._
+import scala.collection.immutable.Seq
+
+import java.io.{Console => _, _}
+import java.util.zip.{ZipFile, ZipEntry}
+
+object Scalajsp {
+
+ case class Options(
+ infos: Boolean = false,
+ desugar: Boolean = false,
+ showReflProxy: Boolean = false,
+ jar: Option[File] = None,
+ fileNames: Seq[String] = Seq.empty)
+
+ def main(args: Array[String]): Unit = {
+ val parser = new scopt.OptionParser[Options]("scalajsp") {
+ head("scalajsp", ScalaJSVersions.current)
+ arg[String]("<file> ...")
+ .unbounded()
+ .action { (x, c) => c.copy(fileNames = c.fileNames :+ x) }
+ .text("*.sjsir file to display content of")
+ opt[File]('j', "jar")
+ .valueName("<jar>")
+ .action { (x, c) => c.copy(jar = Some(x)) }
+ .text("Read *.sjsir file(s) from the given JAR.")
+ opt[Unit]('d', "desugar")
+ .action { (_, c) => c.copy(desugar = true) }
+ .text("Desugar JS trees. This yields runnable JavaScript")
+ opt[Unit]('i', "infos")
+ .action { (_, c) => c.copy(infos = true) }
+ .text("Show DCE infos instead of trees")
+ opt[Unit]('p', "reflProxies")
+ .action { (_, c) => c.copy(showReflProxy = true) }
+ .text("Show reflective call proxies")
+ opt[Unit]('s', "supported")
+ .action { (_,_) => printSupported(); sys.exit() }
+ .text("Show supported Scala.js IR versions")
+ version("version")
+ .abbr("v")
+ .text("Show scalajsp version")
+ help("help")
+ .abbr("h")
+ .text("prints this usage text")
+
+ override def showUsageOnError = true
+ }
+
+ for {
+ options <- parser.parse(args, Options())
+ fileName <- options.fileNames
+ } {
+ val vfile = options.jar map { jar =>
+ readFromJar(jar, fileName)
+ } getOrElse {
+ readFromFile(fileName)
+ }
+
+ displayFileContent(vfile, options)
+ }
+ }
+
+ def printSupported(): Unit = {
+ import ScalaJSVersions._
+ println(s"Emitted Scala.js IR version is: $binaryEmitted")
+ println("Supported Scala.js IR versions are")
+ binarySupported.foreach(v => println(s"* $v"))
+ }
+
+ def displayFileContent(vfile: VirtualScalaJSIRFile, opts: Options): Unit = {
+ if (opts.infos)
+ new InfoPrinter(stdout).printClassInfo(vfile.info)
+ else {
+ val outTree = {
+ if (opts.showReflProxy) vfile.tree
+ else filterOutReflProxies(vfile.tree)
+ }
+
+ if (opts.desugar)
+ new JSTreePrinter(stdout).printTopLevelTree(
+ new ScalaJSClassEmitter(Semantics.Defaults).genClassDef(outTree))
+ else
+ new IRTreePrinter(stdout).printTopLevelTree(outTree)
+ }
+
+ stdout.flush()
+ }
+
+ private def fail(msg: String) = {
+ Console.err.println(msg)
+ sys.exit(1)
+ }
+
+ private def readFromFile(fileName: String) = {
+ val file = new File(fileName)
+
+ if (!file.exists)
+ fail(s"No such file: $fileName")
+ else if (!file.canRead)
+ fail(s"Unable to read file: $fileName")
+ else
+ FileVirtualScalaJSIRFile(file)
+ }
+
+ private def readFromJar(jar: File, name: String) = {
+ val jarFile =
+ try { new ZipFile(jar) }
+ catch { case _: FileNotFoundException => fail(s"No such JAR: $jar") }
+ try {
+ val entry = jarFile.getEntry(name)
+ if (entry == null)
+ fail(s"No such file in jar: $name")
+ else {
+ val name = jarFile.getName + "#" + entry.getName
+ val content =
+ IO.readInputStreamToByteArray(jarFile.getInputStream(entry))
+ new MemVirtualSerializedScalaJSIRFile(name).withContent(content)
+ }
+ } finally {
+ jarFile.close()
+ }
+ }
+
+ private val stdout =
+ new BufferedWriter(new OutputStreamWriter(Console.out, "UTF-8"))
+
+ private def filterOutReflProxies(tree: ClassDef): ClassDef = {
+ import ir.Trees._
+ import ir.Definitions.isReflProxyName
+ val newDefs = tree.defs.filter {
+ case MethodDef(Ident(name, _), _, _, _) => !isReflProxyName(name)
+ case _ => true
+ }
+ tree.copy(defs = newDefs)(tree.pos)
+ }
+
+}