aboutsummaryrefslogtreecommitdiff
path: root/stage1
diff options
context:
space:
mode:
Diffstat (limited to 'stage1')
-rw-r--r--stage1/Stage1Lib.scala20
-rw-r--r--stage1/URLClassLoader.scala4
-rw-r--r--stage1/cbt.scala32
-rw-r--r--stage1/logger.scala4
-rw-r--r--stage1/resolver.scala23
5 files changed, 62 insertions, 21 deletions
diff --git a/stage1/Stage1Lib.scala b/stage1/Stage1Lib.scala
index 7f8f600..71e6ee5 100644
--- a/stage1/Stage1Lib.scala
+++ b/stage1/Stage1Lib.scala
@@ -12,7 +12,10 @@ import java.util.{Set=>_,Map=>_,List=>_,_}
import javax.xml.bind.annotation.adapters.HexBinaryAdapter
// CLI interop
-case class ExitCode(integer: Int)
+case class ExitCode(integer: Int){
+ def ||( other: => ExitCode ) = if( this == ExitCode.Success ) this else other
+ def &&( other: => ExitCode ) = if( this != ExitCode.Success ) this else other
+}
object ExitCode{
val Success = ExitCode(0)
val Failure = ExitCode(1)
@@ -71,7 +74,7 @@ class Stage1Lib( logger: Logger ) extends BaseLib{
try{
Files.copy(stream, incomplete, StandardCopyOption.REPLACE_EXISTING)
} finally {
- stream.close()
+ stream.close
}
sha1.foreach{
hash =>
@@ -86,17 +89,11 @@ class Stage1Lib( logger: Logger ) extends BaseLib{
}
}
- def listFilesRecursive(f: File): Seq[File] = {
- f +: (
- if( f.isDirectory ) f.listFiles.flatMap(listFilesRecursive).toVector else Seq[File]()
- )
- }
-
// ========== compilation / execution ==========
def runMain( cls: String, args: Seq[String], classLoader: ClassLoader, fakeInstance: Boolean = false ): ExitCode = {
import java.lang.reflect.Modifier
- logger.lib(s"Running $cls.main($args) with classLoader: " ++ classLoader.toString)
+ logger.run(s"Running $cls.main($args) with classLoader: " ++ classLoader.toString)
trapExitCode{
val c = classLoader.loadClass(cls)
val m = c.getMethod( "main", classOf[Array[String]] )
@@ -149,7 +146,8 @@ class Stage1Lib( logger: Logger ) extends BaseLib{
/** Given a directory corresponding to the root package, iterate
the names of all classes derived from the class files found */
def iterateClassNames( classesRootDirectory: File ): Seq[String] =
- listFilesRecursive(classesRootDirectory)
+ classesRootDirectory
+ .listRecursive
.filter(_.isFile)
.map(_.getPath)
.collect{
@@ -270,7 +268,7 @@ class Stage1Lib( logger: Logger ) extends BaseLib{
_class,
dualArgs ++ singleArgs ++ (
if(cp.isEmpty) Nil else Seq("-cp", cp)
- ) ++ sourceFiles.map(_.toString),
+ ) ++ sourceFiles.map(_.string),
zinc.classLoader
)
} catch {
diff --git a/stage1/URLClassLoader.scala b/stage1/URLClassLoader.scala
index ff8d2a1..e93b1a4 100644
--- a/stage1/URLClassLoader.scala
+++ b/stage1/URLClassLoader.scala
@@ -8,6 +8,10 @@ case class URLClassLoader( classPath: ClassPath, parent: ClassLoader )( implicit
classPath.strings.map( p => new URL("file:" ++ p) ).toArray,
parent
) with CachingClassLoader{
+ override def loadClass(name: String) = {
+ logger.log("classloader","loadClass " + name)
+ super.loadClass(name)
+ }
val id = Math.abs( new java.util.Random().nextInt )
override def toString = (
scala.Console.BLUE
diff --git a/stage1/cbt.scala b/stage1/cbt.scala
index 4caa085..bc0e944 100644
--- a/stage1/cbt.scala
+++ b/stage1/cbt.scala
@@ -28,6 +28,28 @@ object `package`{
def /(s: String): File = new File( file, s )
def parent = lib.realpath(file ++ "/..")
def string = file.toString
+ /* recursively deletes folders*/
+ def deleteRecursive: Unit = {
+ val s = file.string
+ // some desperate attempts to keep people from accidentally deleting their hard drive
+ assert( file == file.getCanonicalFile, "deleteRecursive requires previous .getCanonicalFile" )
+ assert( file.isAbsolute, "deleteRecursive requires absolute path" )
+ assert( file.string != "", "deleteRecursive requires non-empty file path" )
+ assert( s.split("/").size > 4, "deleteRecursive requires absolute path of at least depth 4" )
+ assert( s.split("\\").size > 4, "deleteRecursive requires absolute path of at least depth 4" )
+ assert( !listRecursive.exists(_.isHidden), "deleteRecursive requires no files to be hidden" )
+ assert( listRecursive.forall(_.canWrite), "deleteRecursive requires all files to be writable" )
+ if( file.isDirectory ){
+ file.listFiles.map(_.deleteRecursive)
+ }
+ //file.delete
+ }
+
+ def listRecursive: Seq[File] = {
+ file +: (
+ if( file.isDirectory ) file.listFiles.flatMap(_.listRecursive).toVector else Seq[File]()
+ )
+ }
}
implicit class URLExtensionMethods( url: URL ){
def ++( s: String ): URL = new URL( url.toString ++ s )
@@ -38,6 +60,16 @@ object `package`{
case e:java.lang.UnsupportedOperationException if e.getMessage === "empty.max" => None
}
}
+ implicit class ClassLoaderExtensions(classLoader: ClassLoader){
+ def canLoad(className: String) = {
+ try{
+ classLoader.loadClass(className)
+ true
+ } catch {
+ case e: ClassNotFoundException => false
+ }
+ }
+ }
implicit class BuildInterfaceExtensions(build: BuildInterface){
import build._
// TODO: if every build has a method triggers a callback if files change
diff --git a/stage1/logger.scala b/stage1/logger.scala
index 8c8431a..373a954 100644
--- a/stage1/logger.scala
+++ b/stage1/logger.scala
@@ -20,7 +20,7 @@ case class Logger(enabledLoggers: Set[String], start: Long) {
def log(name: String, msg: => String) = {
if(
(
- (enabledLoggers contains name)
+ (enabledLoggers contains name)
|| (enabledLoggers contains "all")
) && !(disabledLoggers contains name)
){
@@ -41,6 +41,7 @@ case class Logger(enabledLoggers: Set[String], start: Long) {
final def git(msg: => String) = log(names.git, msg)
final def pom(msg: => String) = log(names.pom, msg)
final def dynamic(msg: => String) = log(names.dynamic, msg)
+ final def run(msg: => String) = log(names.run, msg)
final def transientCache(msg: => String) = log(names.transientCache, msg)
private object names{
@@ -53,6 +54,7 @@ case class Logger(enabledLoggers: Set[String], start: Long) {
val lib = "lib"
val test = "test"
val pom = "pom"
+ val run = "run"
val git = "git"
val dynamic = "dynamic"
val transientCache = "transientCache"
diff --git a/stage1/resolver.scala b/stage1/resolver.scala
index e02f931..ab3196a 100644
--- a/stage1/resolver.scala
+++ b/stage1/resolver.scala
@@ -89,6 +89,10 @@ trait DependencyImplementation extends Dependency{
def run( args: String* ): ExitCode = {
runClass.map( runMain( _, args: _* ) ).getOrElse{
+ // FIXME: this just doing nothing when class is not found has been repeatedly
+ // surprising. Let's try to make this more visible than just logging an error.
+ // Currently blocked on task `recursive` trying every subbuild and would error
+ // for all that don't have a run class. Maybe that's ok actually.
logger.task( "No main class found for " ++ show )
ExitCode.Success
}
@@ -205,13 +209,6 @@ object Classifier{
abstract class DependenciesProxy{
}
-class BoundMavenDependencies(
- cbtLastModified: Long, mavenCache: File, urls: Seq[URL], mavenDependencies: Seq[MavenDependency]
-)(
- implicit logger: Logger, transientCache: java.util.Map[AnyRef,AnyRef], classLoaderCache: ClassLoaderCache
-) extends Dependencies(
- mavenDependencies.map( BoundMavenDependency(cbtLastModified,mavenCache,_,urls) )
-)
case class MavenDependency(
groupId: String, artifactId: String, version: String, classifier: Classifier = Classifier.none
){
@@ -229,6 +226,11 @@ case class BoundMavenDependency(
implicit val logger: Logger, val transientCache: java.util.Map[AnyRef,AnyRef], val classLoaderCache: ClassLoaderCache
) extends ArtifactInfo with DependencyImplementation{
def moduleKey = this.getClass.getName ++ "(" ++ mavenDependency.serialize ++ ")"
+ override def hashCode = mavenDependency.hashCode
+ override def equals(other: Any) = other match{
+ case o: BoundMavenDependency => o.mavenDependency == mavenDependency && o.repositories == repositories
+ case _ => false
+ }
val MavenDependency( groupId, artifactId, version, classifier ) = mavenDependency
assert(
Option(groupId).collect{
@@ -261,7 +263,7 @@ case class BoundMavenDependency(
import scala.collection.JavaConversions._
private def resolve(suffix: String, hash: Option[String], useClassifier: Boolean): File = {
- logger.resolver("Resolving "+this)
+ logger.resolver(lib.blue("Resolving ")+this)
val file = mavenCache ++ basePath(useClassifier) ++ "." ++ suffix
val urls = repositories.map(_ ++ basePath(useClassifier) ++ "." ++ suffix)
urls.find(
@@ -284,7 +286,10 @@ case class BoundMavenDependency(
def jar: File = taskCache[BoundMavenDependency]("jar").memoize{ resolve("jar", Some(jarSha1), true) }
def pom: File = taskCache[BoundMavenDependency]("pom").memoize{ resolve("pom", Some(pomSha1), false) }
- private def pomXml = XML.loadFile(pom.string)
+ private def pomXml = {
+ logger.resolver( "Loading pom file: " ++ pom.string )
+ XML.loadFile(pom.string)
+ }
// ========== pom traversal ==========
private lazy val transitivePom: Seq[BoundMavenDependency] = {