Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Class dependencies #86

Merged
merged 91 commits into from
Mar 30, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
91 commits
Select commit Hold shift + click to select a range
69eab6c
Add an explicit type annotions to the def `allRelations`.
gkossakowski Dec 18, 2015
649b4df
Remove MRelationsDefaultImpl
gkossakowski Dec 18, 2015
e23ecc3
Remove deprecated methods from Relations.
gkossakowski Dec 18, 2015
611df7d
Remove deprecated methods from Analysis.
gkossakowski Dec 18, 2015
5d3f5f6
Remove dead code from AnalysisFormat.
gkossakowski Dec 19, 2015
64f700c
Record declared class names in source files.
gkossakowski Dec 19, 2015
c93cb9d
Remove AnalysisTest.
gkossakowski Dec 23, 2015
54df37e
Remove old incremental compilation algorithm implementation.
gkossakowski Jan 4, 2016
a1b5449
Log progress on recording class-based dependencies.
gkossakowski Dec 23, 2015
cfa880e
Do not crash when source doesn't declare any classes.
gkossakowski Dec 26, 2015
5da0699
Fix bugs in className->src resolution.
gkossakowski Dec 26, 2015
c12d87d
Dependency tracking in locally defined classes requires more work.
gkossakowski Dec 24, 2015
196f84b
Fix treatment of refinements in dependency extraction.
gkossakowski Dec 26, 2015
125bfa0
Improve class->src mapping of dependencies.
gkossakowski Jan 2, 2016
153ff2e
Remove use of scala.Symbol from ScalaCompilerForUnitTesting
gkossakowski Jan 2, 2016
cd8d831
Extract dependencies on objects properly.
gkossakowski Jan 2, 2016
c7bf365
Fix bug in mapping source dep into class dep.
gkossakowski Jan 3, 2016
eb6fcb2
Fix invalidation by external changes.
gkossakowski Jan 4, 2016
f02affb
Switch from `declaredClasses` to `classes` relation.
gkossakowski Jan 5, 2016
21140ce
Hash individual top level definitions
gkossakowski Jan 5, 2016
1f8c76d
Invalidate dependencies at class level.
gkossakowski Jan 5, 2016
474e1c9
Use flatnames for classfile lookup.
gkossakowski Jan 6, 2016
eba665c
Distinguish between binary and source class names.
gkossakowski Jan 8, 2016
136b193
Clarify source and binary class name handling.
gkossakowski Jan 23, 2016
f5b0b60
Introduce `binaryClassName` relation.
gkossakowski Jan 23, 2016
2d3967c
Fix formatting of a comment in NameHashingSpecification
gkossakowski Jan 30, 2016
607ac6d
Add handling of unused top level imports
gkossakowski Jan 27, 2016
fff4538
Change indentation of DependencyContext.java to spaces.
gkossakowski Jan 28, 2016
10c3722
Handle dependencies coming from local classes.
gkossakowski Jan 30, 2016
b476e3d
Cleanup imports in Dependency.scala
gkossakowski Jan 30, 2016
2cfc90d
Fix invalidation of sealed class hierarchies
gkossakowski Jan 30, 2016
a36d098
Add pending tests for recording local classes
gkossakowski Feb 16, 2016
9ea440e
Do not track names of local and anonymous classes.
gkossakowski Feb 16, 2016
19ac268
Log only non-empty sets of invalidated files
gkossakowski Feb 16, 2016
d91858d
Support local classes not coming from src
gkossakowski Feb 16, 2016
89e069d
Remove the dead code and unused imports.
gkossakowski Feb 16, 2016
277262d
Track API at class level instead of source file level
gkossakowski Feb 18, 2016
ef27b62
Fix the check for package objects in ExtractAPI
gkossakowski Feb 18, 2016
43e5fb9
Remove an unnecessary type parameter
gkossakowski Feb 18, 2016
e02fb8e
Small improvement to IncrementalNameHashing
gkossakowski Feb 19, 2016
73cd133
Remove dead code from API extraction.
gkossakowski Feb 21, 2016
934eaa2
Extract API for each class separately
gkossakowski Feb 23, 2016
83c4e09
Cleanup ExtractUsedNamesSpecification
gkossakowski Feb 23, 2016
33e9a50
Use an explicit tree traverser in ExtractUsedNames
gkossakowski Feb 23, 2016
3ab396c
Fix compilation erros in JavaCompilerSpec
gkossakowski Feb 23, 2016
53c0e62
Track and extract used names at class level
gkossakowski Feb 23, 2016
4cc43e2
Cleanup imports in API phase definition.
gkossakowski Feb 23, 2016
a7d545a
Reduce use of ClassToSourceMapper
gkossakowski Feb 28, 2016
5ef2d8c
Fix bug in SameAPI.sameTopLevel
gkossakowski Feb 29, 2016
2e2a3fe
Persist all extracted apis in APIs datastructure.
gkossakowski Feb 29, 2016
29571f8
Extract APIs of Java inner classes separately
gkossakowski Mar 3, 2016
f8a907a
Fix computing name hashes for private classes
gkossakowski Mar 4, 2016
3617aa4
Fix handling of names of Java-defined class names
gkossakowski Mar 4, 2016
1cad892
Clarify a binary class name used in ExternalDependency
gkossakowski Feb 29, 2016
9cee296
Remove unnecessary ExtractAPI.forceStructures calls
gkossakowski Feb 29, 2016
ece2eab
Improve logging of invalidation of package objects
gkossakowski Mar 9, 2016
b0a8a91
Merge branch '1.0' into cd-filter-branch
gkossakowski Mar 16, 2016
2a8db55
Add .gitignore file
gkossakowski Mar 16, 2016
49f8786
Fix broken merge in Dependency.scala
gkossakowski Mar 16, 2016
469a3ac
Fix build failure of the Scala 2.10 bridge sources
gkossakowski Mar 16, 2016
19d8b9d
Fix Scaladoc failures in Dependency.scala
gkossakowski Mar 16, 2016
c46ebe1
Zinc is compatible with Scala 2.10 and 2.11 only
gkossakowski Mar 16, 2016
189a2a5
Revert "Include private members in API hash of traits."
gkossakowski Mar 17, 2016
a79b2c7
Fix import-class scripted test
gkossakowski Mar 17, 2016
e9241bc
Merge remote-tracking branch 'sbt/1.0' into class-dependencies
gkossakowski Mar 17, 2016
061e2d6
Remove old incremental compilation algorithm implementation.
gkossakowski Mar 17, 2016
a972625
Make scripted commands work with classes instead of srcs
gkossakowski Mar 17, 2016
2103e96
Fix specify-inc-options scripted test
gkossakowski Mar 17, 2016
a046bff
Add documentation to DependencyContext
gkossakowski Mar 17, 2016
7e3fc8e
Port class-based-inheritance scripted test
gkossakowski Mar 17, 2016
01ad362
Fix checkProducts and introduce checkClasses
gkossakowski Mar 17, 2016
fb4c895
Port recorded-products scripted test.
gkossakowski Mar 17, 2016
20c8593
Port java-inner scripted test
gkossakowski Mar 17, 2016
3484091
Port local-class-inheritance scripted test
gkossakowski Mar 17, 2016
c2a1fae
Port gkossakowski/sbt@800a01460b031790110e2c959ff474d8b9587a1b
gkossakowski Mar 17, 2016
5fc80fa
Add .DS_Store to ignored files
gkossakowski Mar 17, 2016
dead96c
Port class-based-memberRef scripted test
gkossakowski Mar 17, 2016
9d217d8
Port gkossakowski/sbt@e09fa6d383f2fd9017954af6805b5e129f64047e
gkossakowski Mar 17, 2016
4061c76
Port external-src-dependency sripted test
gkossakowski Mar 17, 2016
1e2b2de
Mark java scripted tests as passing
gkossakowski Mar 17, 2016
9920f12
Persist the local inheritance relation
gkossakowski Mar 25, 2016
983d309
Extend local class inheritance scripted test
gkossakowski Mar 25, 2016
8df9757
Improve invalidation of local inheritance dependencies.
gkossakowski Mar 25, 2016
ae5d0fe
Move Analyze and ClassToAPI specifications
gkossakowski Mar 25, 2016
fbc5956
Update docs of MemberRefInvalidator
gkossakowski Mar 25, 2016
52c7a6a
Update docs of Incremental{Common, NameHashing}
gkossakowski Mar 25, 2016
deac13a
Remove `declaredClasses` relation.
gkossakowski Mar 25, 2016
231e2f5
Remove `direct` and `publicInherited` relations
gkossakowski Mar 25, 2016
78bc5f2
Refactor classpath and analysis lookups.
gkossakowski Mar 29, 2016
f475de2
Reduce dependency on CallbackGlobal.
gkossakowski Mar 29, 2016
733649a
Merge remote-tracking branch 'sbt/1.0' into class-dependencies
gkossakowski Mar 30, 2016
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions build.sbt
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ lazy val compilerInterface = (project in internalPath / "compiler-interface").
// javaOnlySettings,
name := "Compiler Interface",
crossScalaVersions := Seq(scala211),
libraryDependencies ++= Seq(utilInterface),
libraryDependencies ++= Seq(utilInterface, scalaLibrary.value % Test),
exportJars := true,
watchSources <++= apiDefinitions,
resourceGenerators in Compile <+= (version, resourceManaged, streams, compile in Compile) map generateVersionFile,
Expand Down Expand Up @@ -203,7 +203,7 @@ lazy val compilerBridge: Project = (project in internalPath / "compiler-bridge")
// defines operations on the API of a source, including determining whether it has changed and converting it to a string
// and discovery of Projclasses and annotations
lazy val incrementalcompilerApiInfo = (project in internalPath / "incrementalcompiler-apiinfo").
dependsOn(compilerInterface, incrementalcompilerClassfile).
dependsOn(compilerInterface, incrementalcompilerClassfile % "compile;test->test").
settings(
testedBaseSettings,
name := "Incrementalcompiler ApiInfo"
Expand All @@ -222,7 +222,7 @@ lazy val incrementalcompilerClasspath = (project in internalPath / "incrementalc

// class file reader and analyzer
lazy val incrementalcompilerClassfile = (project in internalPath / "incrementalcompiler-classfile").
dependsOn(compilerInterface).
dependsOn(compilerInterface % "compile;test->test").
settings(
testedBaseSettings,
libraryDependencies ++= Seq(sbtIO, utilLogging),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -110,14 +110,35 @@ class IncrementalCompilerImpl extends IncrementalCompiler {
}
}

private class LookupImpl(compileConfiguration: CompileConfiguration) extends Lookup {
private val entry = MixedAnalyzingCompiler.classPathLookup(compileConfiguration)

override def lookupOnClasspath(binaryClassName: String): Option[File] =
entry(binaryClassName)
override def lookupAnalysis(classFile: File): Option[CompileAnalysis] =
compileConfiguration.getAnalysis(classFile)

override def lookupAnalysis(binaryDependency: File, binaryClassName: String): Option[CompileAnalysis] = {
lookupOnClasspath(binaryClassName) flatMap { defines =>
if (binaryDependency != Locate.resolve(defines, binaryClassName))
None
else
lookupAnalysis(defines)
}
}

override def lookupAnalysis(binaryClassName: String): Option[CompileAnalysis] =
lookupOnClasspath(binaryClassName).flatMap(lookupAnalysis)
}

/** Actually runs the incremental compiler using the given mixed compiler. This will prune the inputs based on the MiniSetup. */
private def compileInternal(
mixedCompiler: MixedAnalyzingCompiler,
equiv: Equiv[MiniSetup],
equivPairs: Equiv[Array[T2[String, String]]],
log: Logger
): (Analysis, Boolean) = {
val entry = MixedAnalyzingCompiler.classPathLookup(mixedCompiler.config)
val lookup = new LookupImpl(mixedCompiler.config)
import mixedCompiler.config._
import mixedCompiler.config.currentSetup.output
val sourcesSet = sources.toSet
Expand All @@ -136,7 +157,7 @@ class IncrementalCompilerImpl extends IncrementalCompiler {
case _ => Incremental.prune(sourcesSet, previousAnalysis)
}
// Run the incremental compiler using the mixed compiler we've defined.
IncrementalCompile(sourcesSet, entry, mixedCompiler.compile, analysis, getAnalysis, output, log, incOptions).swap
IncrementalCompile(sourcesSet, lookup, mixedCompiler.compile, analysis, output, log, incOptions).swap
}

def setup(analysisMap: F1[File, Maybe[CompileAnalysis]], definesClass: F1[File, DefinesClass], skip: Boolean, cacheFile: File, cache: GlobalsCache,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,9 @@ package inc
import java.io.File
import java.lang.ref.{ SoftReference, Reference }

import sbt.internal.inc.classfile.Analyze
import sbt.internal.inc.classpath.ClasspathUtilities
import inc.javac.AnalyzingJavaCompiler
import Locate.DefinesClass
import xsbti.{ AnalysisCallback => XAnalysisCallback, Reporter }
import xsbti.api.Source
import xsbti.compile.CompileOrder._
import xsbti.compile._
import sbt.io.IO
Expand Down Expand Up @@ -167,7 +164,6 @@ object MixedAnalyzingCompiler {
import config._
import currentSetup._
val absClasspath = classpath.map(_.getAbsoluteFile)
val apiOption = (api: Either[Boolean, Source]) => api.right.toOption
val cArgs = new CompilerArguments(compiler.scalaInstance, compiler.cp)
val searchClasspath = explicitBootClasspath(options.scalacOptions) ++ withBootclasspath(cArgs, absClasspath)
(searchClasspath, Locate.entry(searchClasspath, definesClass))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import java.io.File
import sbt._
import sbt.internal.inc.classfile.Analyze
import sbt.internal.inc.classpath.ClasspathUtilities
import xsbti.api.Source
import xsbti.compile._
import xsbti.{ AnalysisCallback, Reporter }
import sbt.io.PathFinder
Expand Down Expand Up @@ -71,10 +70,12 @@ final class AnalyzingJavaCompiler private[sbt] (
// TODO - Perhaps we just record task 1/2 here

// Reads the API information directly from the Class[_] object. Used when Analyzing dependencies.
def readAPI(source: File, classes: Seq[Class[_]]): Set[String] = {
val (api, inherits) = ClassToAPI.process(classes)
callback.api(source, api)
inherits.map(_.getName)
def readAPI(source: File, classes: Seq[Class[_]]): Set[(String, String)] = {
val (apis, inherits) = ClassToAPI.process(classes)
apis.foreach(callback.api(source, _))
inherits.map {
case (from: Class[_], to: Class[_]) => (from.getName, to.getName)
}
}
// Runs the analysis portion of Javac.
timed("Java analysis", log) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
object A
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
> compile
> checkClasses A.scala: A
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
> compile

> checkDependencies A.scala: B.scala C.scala
> checkDependencies A: B C
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
> compile
> checkProducts A.scala: A A$
> checkProducts A.scala: A.class A$.class
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,6 @@ $ copy-file changes/A.scala A.scala
> compile

> checkRecompilations 0
> checkRecompilations 1 A.scala
> checkRecompilations 2 B.scala C.scala
> checkRecompilations 3 D.scala
> checkRecompilations 1 A
> checkRecompilations 2 B C
> checkRecompilations 3 D
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class A {
class AA
}

class A2
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
class A {
class AA {
// add a member to an inner class, dependencies on A shouldn't be recompiled
def foo: Int = 123
}
}

class A2
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class A {
// class AA
}

class A2
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
class B extends A2
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
class C extends A
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Test for class-based invalidation of dependencies
# by inheritance. The source file A.scala defines
# A and A2 classes. The B.scala inherits from A2 but
# in the test api of A is modified. B.scala shouldn't
# get invalidated if invalidation happens at
# class level
# this test case covers https://github.com/sbt/sbt/issues/2320

# introduces first compile iteration
> compile
$ copy-file changes/A1.scala src/main/scala/A.scala
# second iteration and third iteration (due to invalidation of C)
> compile
$ copy-file changes/A2.scala src/main/scala/A.scala
# fourth iteration
> compile
# check if there were exactly four compile iterations performed
> checkRecompilations 0 B
> checkRecompilations 1
> checkRecompilations 2 C
> checkRecompilations 3 A A2 A.AA
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
class A1 {
//def foo: Int = 123
}

class A2 {
def bar: Int = 42
}
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
recompileAllFraction = 1.0
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
class A1 {
def foo: Int = 123
}

class A2 {
def bar: Int = 42
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
class B1(a1: A1)

class B2(a2: A2) {
def foo: Int = 53
def abc: Int = foo + a2.bar
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
# Test for class-based invalidation of dependencies by member reference
# This test checks if name hashes are tracked at the class level so
# only classes that depend on an API of a modified class are invalidated

# introduces first compile iteration
> compile
$ copy-file changes/A1.scala src/main/scala/A.scala
# second iteration
> compile
> checkRecompilations 0 B1 B2
> checkRecompilations 1 A1 A2
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
lazy val commonSettings = Seq(
logLevel := Level.Debug
)
lazy val provider = project.settings(commonSettings)
lazy val use = project.settings(commonSettings).dependsOn(provider)

InputKey[Unit]("check-number-of-compiler-iterations") <<= inputTask { (argTask: TaskKey[Seq[String]]) =>
(argTask, compile in Compile in use) map { (args: Seq[String], a: sbt.inc.Analysis) =>
assert(args.size == 1)
val expectedIterationsNumber = args(0).toInt
assert(a.compilations.allCompilations.size == expectedIterationsNumber,
"a.compilations.allCompilations.size = %d (expected %d)".format(a.compilations.allCompilations.size, expectedIterationsNumber))
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
// add a comment to trigger a recompilation of A.scala, this should not trigger a recompilation of B.scala
class A {
class Inner
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class A {
class Inner {
def foo: Int = 187
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
> compile

$ copy-file changes/A1.scala provider/A.scala
> compile
> check-number-of-compiler-iterations 1

$ copy-file changes/A2.scala provider/A.scala
> compile
> check-number-of-compiler-iterations 1
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
class A {
class Inner
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
class B extends A {
// introduce dependency on Inner
def inner: Inner = null
}
Original file line number Diff line number Diff line change
@@ -1 +1,3 @@
import a.A

class B

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

Loading