Compare commits

..

1502 Commits

Author SHA1 Message Date
Simon Ogorodnik
26da9976d2 Update changeling for 1.2-Beta 2017-09-29 14:42:52 +03:00
Dmitry Jemerov
ae135d979f Mark multiplatform projects as experimental in the UI 2017-09-27 17:29:01 +02:00
Nikolay Krasko
2950495c4a Execute action without writeActionPriority in tests
(cherry picked from commit ab6bc43)
2017-09-27 16:19:38 +03:00
Ilya Gorbunov
8cdde268c6 Fixup "Refactor: use the same arraybuffer to compute double hashcode": switch indices 2017-09-25 22:06:10 +03:00
Denis Zharkov
00146b383c Use Jsr305State.DEFAULT instead of IGNORE as a default value 2017-09-25 20:06:59 +03:00
Denis Zharkov
cc244f717e Fix loading additional compiler arguments from facets for libraries 2017-09-25 20:06:50 +03:00
Dmitry Jemerov
27c01598e8 Don't show "Run tests" gutter icon when there's nothing to run
#KT-20338 Fixed
2017-09-25 12:04:28 +02:00
Mikhail Glukhikh
6a11584cde Expect/actual: add inspection for Suppress("DIAGNOSTIC") migration
So #KT-20328 Fixed
2017-09-22 20:23:02 +03:00
Mikhail Glukhikh
1a9fc4fdc8 Fix a pair of multi-platform messages #KT-20327 Fixed 2017-09-22 20:22:49 +03:00
Sergey Igushkin
610a303bfa Revert "Fix agp25 source set Kotlin classes not included in kotlin-gradle-plugin"
This reverts commit 25ca079
2017-09-22 17:57:33 +03:00
Sergey Igushkin
f831d88259 Fix agp25 source set Kotlin classes not included in kotlin-gradle-plugin
(cherry picked from commit 25ca079)
2017-09-22 17:41:42 +03:00
Dmitry Jemerov
078acbb1a6 Fix exception in KotlinExpandNodeProjectViewProvider.modify 2017-09-21 15:22:28 +02:00
Stanislav Erokhin
1333442a96 Support expected type from explicit cast
This commit support the following case.
Suppose we have such declaration:
  fun <T> foo(): T { ... }

Then in code we want to use it like this: `foo() as String`.
But in LV <= 1.1 we have type inference error: "Not enough
information for type parameter `T`". This error happened because we
do not use type from cast as expected type for call.

In this commit we fix this problem and use this type as expected type
in following cases:
 - our function has only one type parameter (this can be relaxed later)
 - function parameter types and extension receiver type not contains `T`

Also this fix problem with `findViewById`.
Already signature was: `fun findViewById(...): View`
and was used like: `findViewById() as MyView`.
New signature is `fun <T : View> findViewById(...): T`
and old usage was broken because of problem described above
2017-09-21 16:06:19 +03:00
Mikhail Glukhikh
1e85dc3e12 Add DEPRECATED_MODIFIER to cleanup diagnostic list 2017-09-21 15:57:25 +03:00
Anton Bannykh
6c77a19794 JS: temporarily remove @Before @After annotations
(cherry picked from commit 0976a78)
2017-09-21 14:53:41 +03:00
Anton Bannykh
a8a0666ea5 JS: Support isInitialized intrisic for lateinit properties 2017-09-20 14:45:38 +03:00
Sergey Igushkin
103b41e90d Fix javaOutputDir changed to the JAR, which was breaking unit tests
internal visibility, because they did not get the JAR into classpath

Issue #KT-20212 Fixed

(cherry picked from commit 41b13d2)
2017-09-19 15:38:04 +03:00
Alexey Sedunov
50960a61d0 Misc: Fix multiplatform test configuration
(cherry picked from commit 04a4bef)
2017-09-18 20:52:16 +03:00
Dmitry Jemerov
75bd6264f5 Correctly detect multiplatform modules in run code
LanguageVersionSettings doesn't mean that the module is actually
multiplatform; it only means that it _could_ be one. Use
platform and information from facet instead.

Also fix detection of common stdlib version and add tests for common
run config.
2017-09-18 19:47:38 +02:00
Dmitry Jemerov
ad1663ec73 Add missing dependencies 2017-09-18 19:47:22 +02:00
Alexander Udalov
6d3a1bb51b Support -Werror CLI argument to treat warnings as errors
The option is named "warningsAsErrors" in the Gradle plugin

 #KT-10563 Fixed
2017-09-18 18:01:06 +03:00
Alexander Udalov
040de90d14 Add test on compiling against kotlin.reflect on JDK 9 2017-09-18 18:01:05 +03:00
Alexander Udalov
28b4a372d2 Remove deprecated API from package kotlin.reflect
This is needed to avoid the split package problem on Java 9 (KT-19258):
both kotlin-stdlib.jar and kotlin-reflect.jar export the package
kotlin.reflect
2017-09-18 18:01:05 +03:00
Alexander Udalov
45be5e971d Decrease resolution priority of declarations from kotlin-stdlib-jre7/8
In order to allow "overload resolution ambiguity" when both
kotlin-stdlib-jre7/8 and kotlin-stdlib-jdk7/8 are in the dependencies
2017-09-18 18:01:04 +03:00
Alexander Udalov
f8b5e276bc Add test on compiling against kotlin.stdlib.jdk7/8 on JDK 9 2017-09-18 18:01:03 +03:00
Alexander Udalov
12cb4ffde5 Move internal declarations in kotlin-stdlib-jdk7/8 to other packages
- in kotlin-stdlib-jdk7, package kotlin.internal -> kotlin.internal.jdk7
- in kotlin-stdlib-jdk8, package kotlin.internal -> kotlin.internal.jdk8
2017-09-18 18:01:02 +03:00
Alexander Udalov
1fd5e25bb3 Restore kotlin-stdlib-jre7/8 libraries 2017-09-18 18:01:02 +03:00
Alexander Udalov
fa06b74440 Introduce kotlin-stdlib-jdk7/8 libraries, deprecate kotlin-stdlib-jre7/8
The idea is to keep all declarations in the same packages from Kotlin's
point of view, but use JvmPackageName annotation to move them to another
JVM package, to avoid the split package problem which is otherwise
unsolvable when using module path on Java 9 (KT-19258).

In this commit, kotlin-stdlib-jre7/8 are moved to kotlin-stdlib-jdk7/8
and in the subsequent commit, -jre7/8 are restored. This is done in
order to make Git recognize this as a file move to preserve history
2017-09-18 18:01:01 +03:00
Alexander Udalov
4d2c2c39c2 Update copyrights in kotlin-stdlib-jre7/8 sources 2017-09-18 18:01:00 +03:00
Alexander Udalov
5e6b195551 Revert "Temporarily remove JvmPackageName and tests, but keep the implementation"
This reverts commit 9ae6feb2c5.
2017-09-18 18:00:59 +03:00
Alexander Udalov
adaa4da502 Revert "Temporarily remove isInitialized and tests, but keep the implementation"
This reverts commit 234148518e.
2017-09-18 18:00:58 +03:00
Ilya Gorbunov
6f98973786 Refactor: use the same arraybuffer to compute double hashcode 2017-09-18 18:00:58 +03:00
Ilya Gorbunov
e82eb7bc87 Detect endianness when reinterpreting Float64 as two Int32
#KT-18264

Use Int32Array instead of Uint32Array since ints are required to be singed.
2017-09-18 18:00:57 +03:00
Ilya Gorbunov
7c51e305d0 Implement in JS nextUp(), nextDown(), nextTowards() and ulp extensions
#KT-4900
2017-09-18 18:00:56 +03:00
Ilya Gorbunov
eae7e959e8 Make withSign(NaN) behave as in JVM
#KT-4900

Where only the sign of the result is undefined, but the absolute value is unchanged.
2017-09-18 18:00:55 +03:00
Ilya Gorbunov
a94843cdd9 Provide Double and Float bit conversion functions as extensions in JS and Common
Instance extension: Double/Float.toBits/toRawBits
Companion extension: Double/Float.Companion.fromBits

#KT-18264 Fixed
2017-09-18 18:00:55 +03:00
Ilya Gorbunov
7e9c487073 Introduce inverse hyperbolic functions
#KT-4900

Improve accuracy of JS polyfills of hyperbolic functions and expm1/log1p
2017-09-18 18:00:54 +03:00
Alexey Sedunov
5919f5e2b3 Do not overwrite facet settings in Module.languageVersionSettings 2017-09-18 18:00:53 +03:00
Mikhael Bogdanov
c6511f465b Switch warning to error for java-default method calls within 1.6 target
#KT-15825 Fixed

(cherry picked from commit 9b29ebb)
2017-09-18 18:00:53 +03:00
Ilya Gorbunov
e1ae00cdf4 Minor fixes in logarithm functions docs 2017-09-18 18:00:52 +03:00
Ilya Gorbunov
17826efbf6 Annotate new API with SinceKotlin, provide common headers
#KT-4900

Also update binary API dump.
2017-09-18 18:00:51 +03:00
Ilya Gorbunov
fb673c4c9f Deprecate kotlin.js.Math object, rename kotlin.math.kt to just math.kt 2017-09-18 18:00:50 +03:00
Ilya Gorbunov
77faa8659d Integer math functions and tests for them
#KT-4900
2017-09-18 18:00:50 +03:00
Ilya Gorbunov
d986a20e42 Float Math API
#KT-4900
2017-09-18 18:00:49 +03:00
Ilya Gorbunov
39b103ba9c JVM-specific math functions and tests
#KT-4900
2017-09-18 18:00:48 +03:00
Ilya Gorbunov
7672b65c5f Provide Double and Float bit conversion functions as extensions
Instance extension: Double/Float.toBits/toRawBits
Companion extension: Double/Float.Companion.fromBits

 #KT-18264 Fixed
2017-09-18 18:00:48 +03:00
Ilya Gorbunov
2a4c21908b Rename log to ln, log1p to ln1p, keep pow only as extension
#KT-4900
2017-09-18 18:00:47 +03:00
Ilya Gorbunov
018cd25f6d Rename sgn to sign, add docs and tests
#KT-4900
2017-09-18 18:00:46 +03:00
Ilya Gorbunov
774ee74812 Use HALF_EVEN rounding mode for round()
Add docs and tests for rounding.

 #KT-4900
2017-09-18 18:00:45 +03:00
Ilya Gorbunov
759bfb5869 Common math tests and document for trigonometric functions and powers.
#KT-4900
2017-09-18 18:00:45 +03:00
Ilya Gorbunov
5516924430 Draft common math API with top-level functions and constants in kotlin.math package
#KT-4900
2017-09-18 18:00:44 +03:00
Ilya Gorbunov
24b2dd0166 Provide polyfills for missing ES6 math functions
#KT-4900

Rename math.kt to js.math.kt
2017-09-18 18:00:43 +03:00
Ilya Gorbunov
e87cf00d7b windowed function: add default parameters, drop or keep partial windows, KEEP-11
Make step default to 1.
Add partialWindows boolean parameter defaulting to false to control
whether to keep partial windows in the end.
2017-09-18 18:00:43 +03:00
Ilya Gorbunov
02d006eafa Rename pairwise to zipWithNext, KEEP-11 2017-09-18 18:00:42 +03:00
Ilya Gorbunov
b6a9e6fc0c Update binary api dump, rearrage bignumbers tests 2017-09-18 18:00:41 +03:00
Ilya Gorbunov
765adaef0a Add missing api: radix overloads, mathContext and scale overloads, orNull overloads
Move string-to-number conversions and their tests near to existing ones

Add documentation and copyrights.
2017-09-18 18:00:40 +03:00
voddan
cd22050cda KEEP-49: extending Kotlin API for BigInteger and BigDecimal 2017-09-18 18:00:40 +03:00
Anton Bannykh
3dc4bc284a JS: enable TypedArrays by default 2017-09-18 18:00:39 +03:00
Ilya Gorbunov
cec91bfd47 Temporary make 'implement' dependency transient 2017-09-18 18:00:38 +03:00
Ilya Gorbunov
89e0797d63 Provide MutableList.fill for JS, annotate new API with @SinceKotlin
#KT-8823 #KT-9010
2017-09-18 18:00:35 +03:00
Ilya Gorbunov
c41cae6264 Introduce MutableList.fill and shuffle/shuffled extensions for JVM only
'shuffle' and 'fill' are inline only, but 'shuffled' is not.

#KT-8823 Fixed
#KT-9010 Fixed
2017-09-18 17:59:43 +03:00
Ilya Gorbunov
64169a5b02 Make Regex class serializable on JVM
#KT-16447 Fixed

Refactor helper functions for serialization tests.
2017-09-18 17:59:42 +03:00
Ilya Gorbunov
fb10690690 Docs and samples for 'windowed' function 2017-09-18 17:59:41 +03:00
Ilya Gorbunov
4f1a483c22 Docs and samples for 'chunked' function 2017-09-18 17:59:41 +03:00
Ilya Gorbunov
a7d17eb24c Docs and samples for 'pairwise' function 2017-09-18 17:59:40 +03:00
Ilya Gorbunov
a035c2beb3 Minor refactoring in RingBuffer 2017-09-18 17:59:39 +03:00
Ilya Gorbunov
be1715cd59 Optimize 'windowed' and 'chunked' for char sequences, iterables and sequences 2017-09-18 17:59:38 +03:00
Ilya Gorbunov
03dcbcaf8d Add tests for windowed and chunked, fix precondition checks 2017-09-18 17:59:38 +03:00
Ilya Gorbunov
0e57fa3a82 Generate 'chunked' and 'windowed' signatures and delegating implementations
Add implementations of windowed.
2017-09-18 17:59:37 +03:00
Sergey Mashkov
120ab10d79 Sliding window implementation helper utilities 2017-09-18 17:59:36 +03:00
Ilya Gorbunov
e320104016 Introduce 'pairwise' function, KEEP-11 2017-09-18 17:59:35 +03:00
Mikhael Bogdanov
c5353f97c8 Move object initialization from <init> to <clinit>
Codegen generates static backing fields for object properties.
  They are initialized in class constructor but some of them are final static
  and such access is prohibited in specification but it's allowed in
  java bytecode <= 1.8. Such access in 1.9 bytecode cause
  "IllegalAccessError: Update to static final field Object.INSTANCE
  attempted from a different method (<init>) than the initializer method <clinit>"

  Added additional hidden field in interface companion to pass out
  companion instance from <clinit>.

 #KT-15894 Fixed
2017-09-18 17:59:35 +03:00
Ilya Gorbunov
dbc3891418 Remove "EXPERIMENTAL" from 1.2 version description in tests and gradle options 2017-09-18 17:59:34 +03:00
Ilya Gorbunov
f41a48f11a Set 1.2-SNAPSHOT in maven build 2017-09-18 17:59:33 +03:00
Ilya Gorbunov
81dc100276 Set 1.2-SNAPSHOT in gradle build 2017-09-18 17:59:32 +03:00
Ilya Gorbunov
b68ac868f5 Set LATEST_STABLE language version and current version of stdlib to 1.2, set IS_PRE_RELEASE 2017-09-18 17:59:32 +03:00
Vyacheslav Gerasimov
43ee2bd9c4 Add new Gradle with Kotlin DSL project wizard for Kotlin, KotlinJS, Java, Groovy
#KT-20308 Fixed Target Version 1.2
2017-09-18 17:15:54 +03:00
Vyacheslav Gerasimov
3d71fa85be Copy initial new gradle project wizard files from idea gradle plugin 2017-09-18 17:15:50 +03:00
Stanislav Erokhin
e8d42e4dde Increase stub version because we add new soft-keywords: expect and actual 2017-09-18 16:37:36 +03:00
Alexey Sedunov
7c26f87b0c Misc: Fix multiplatform test configuration 2017-09-18 16:30:28 +03:00
Mikhail Glukhikh
9b0f15137f Expect/actual: introduce DEPRECATED_MODIFIER instead of ..._FOR_TARGET 2017-09-18 16:19:41 +03:00
Mikhail Glukhikh
721889600f Expect/actual: fix some error messages 2017-09-18 16:09:18 +03:00
Nikolay Krasko
98e9238763 Force canceling injection search when it's executed without progress (KT-19901)
More accurate fix for KT-19901.
There're cases when injectors are counted without progress indicator but
under read action. In that cases typing can't be started until exit from
the computing that produces lags in typing.

Tested with long spek-like test file.

 #KT-19901 Fixed
2017-09-18 14:56:46 +03:00
Alexey Sedunov
bd3d79d318 Minor: Do not specify platform for project-level language settings 2017-09-18 14:55:16 +03:00
Mikhail Glukhikh
79308287be Minor: rename directory in quick-fix test data 2017-09-18 14:40:14 +03:00
Denis Grachev
0722c5c13a KT-19565: J2K: Determine mutability using iterator
#KT-19565 fixed
2017-09-18 14:07:57 +03:00
Alexey Andreev
d312996f3a JS: generate import statement for COROUTINE_SUSPENDED property
This makes code with lots of corutines more feasible for uglification
2017-09-18 13:13:40 +03:00
Alexey Andreev
9771a3c66e JS: prove that KT-8282 is no more reproducible 2017-09-18 13:13:00 +03:00
Alexey Andreev
aa35d4ed36 JS: prove that KT-8315 is no more reproducible 2017-09-18 13:13:00 +03:00
Alexey Andreev
6ba0ac1238 JS: prove that KT-7011 is no more reproducible 2017-09-18 13:12:59 +03:00
Alexey Andreev
a66cd8b309 Fix name clash in JS implementation of multiplatform extension property
See KT-18756
2017-09-18 13:10:51 +03:00
Toshiaki Kameyama
1c7d66c803 Do not suggest "Redundant Unit return type" for Nothing-typed expression
So #KT-20261 Fixed
2017-09-18 13:02:03 +03:00
Toshiaki Kameyama
d87c0b164f Add quick-fix for CANNOT_CHECK_FOR_ERASED #KT-18742 Fixed 2017-09-18 12:11:15 +03:00
Mikhail Zarechenskiy
6a1b6d10d8 Setup JDK roots and initialize JDK_HOME in common core environment
#KT-20167 Fixed
2017-09-18 08:19:41 +03:00
Stanislav Erokhin
6d26d1fb67 Minor. rename header -> commonModule 2017-09-16 19:47:47 +03:00
Stanislav Erokhin
91a99b4726 Migrate impl to actual in libraries projects 2017-09-16 19:47:46 +03:00
Stanislav Erokhin
481cbd0850 Migrate header to expect in libraries projects 2017-09-16 19:47:45 +03:00
Stanislav Erokhin
7cd5eeb24d Regenerate common stdlib: use 'expect' instead 'header' 2017-09-16 19:47:44 +03:00
Mikhail Glukhikh
e12de11ce9 Fix add modifier for replacement case, add expect/actual order tests 2017-09-16 19:47:43 +03:00
Mikhail Glukhikh
2c521727c3 Add header/impl/expect/actual into modifiers order list 2017-09-16 19:47:42 +03:00
Mikhail Glukhikh
c0dd97b40d Migration to expect/actual: fix CLI tests 2017-09-16 19:47:41 +03:00
Mikhail Glukhikh
a18e9436a1 Migration to expect/actual: change diagnostics rendering 2017-09-16 19:47:40 +03:00
Stanislav Erokhin
7982f3489e Rename compiler key -Xno-check-impl to -Xno-check-actual 2017-09-16 19:47:39 +03:00
Mikhail Glukhikh
2fe7cc5534 Add more tests for KT-20262 2017-09-16 19:47:38 +03:00
Mikhail Glukhikh
77f625bfc8 Include ReplaceModifierFix in cleanup #KT-20262 Fixed 2017-09-16 19:47:37 +03:00
Stanislav Erokhin
7849452b66 Rename ALLOW_HEADER_WITHOUT_IMPLS to ALLOW_EXPECT_WITHOUT_ACTUAL 2017-09-16 19:47:36 +03:00
Vyacheslav Gerasimov
bba2d27e82 UAST: Fix getType and getText for UastKotlinPsiVariable 2017-09-16 13:21:44 +03:00
Vyacheslav Gerasimov
14742a6048 UAST: Fix getContainingFile, should return KtFile instead of FakeFileForLightClass
#KT-20170 Fixed
2017-09-16 13:02:08 +03:00
Vyacheslav Gerasimov
6d7c88a2bc Fix KotlinWithGradleConfigurator, get psi files under read action
EA-106672 Fixed
2017-09-16 13:02:07 +03:00
Alexander Udalov
37a23f0958 Use JVM package name in Java 9 module accessibility checks
This fixes Java9ModuleIntegrationTest.testDependencyOnStdlibJdk78 from
the 1.2 branch
2017-09-15 20:30:29 +03:00
Mikhail Glukhikh
d3082b0e62 Migration to expect/actual: change some comments in compiler 2017-09-15 18:30:32 +03:00
Mikhail Glukhikh
fcc84d00c3 Migration: make header/impl/expect/actual contradictory to each other 2017-09-15 18:30:25 +03:00
Mikhail Glukhikh
fc4ff3b760 Migration to expect/actual: renames in DeclarationResolver 2017-09-15 18:30:18 +03:00
Mikhail Glukhikh
afdd647df1 Migration to expect/actual: renames in DeclarationsChecker 2017-09-15 18:30:11 +03:00
Mikhail Glukhikh
c5c6050baa Migration to expect/actual: renames in ExpectedActualDeclarationChecker 2017-09-15 18:30:04 +03:00
Stanislav Erokhin
88644001d3 Rename heared/impl around highlighter markers 2017-09-15 18:29:57 +03:00
Stanislav Erokhin
8d8f683042 Fix header/impl in LazyClassDescriptor.toString 2017-09-15 18:29:50 +03:00
Stanislav Erokhin
956b0aca92 Rename header/impl in DescriptorRendererModifier 2017-09-15 18:29:43 +03:00
Stanislav Erokhin
194d16176c Rename protobuf header/impl flags 2017-09-15 18:29:36 +03:00
Stanislav Erokhin
2b186909d4 Migrate diagnostic names for header/impl 2017-09-15 18:29:29 +03:00
Mikhail Glukhikh
d20ba5d082 Migration to expect/actual minor: rename icon constants 2017-09-15 18:29:21 +03:00
Mikhail Glukhikh
19b8ecab61 Migration to expect/actual: KotlinSafeDeleteProcessor 2017-09-15 18:29:13 +03:00
Mikhail Glukhikh
6e41bbc2a7 Migration: header->expect & impl->actual in IDEA test data 2017-09-15 18:29:06 +03:00
Mikhail Glukhikh
32cc619f15 Migration to expect/actual: fix multiplatform highlighting tests 2017-09-15 18:28:57 +03:00
Mikhail Glukhikh
85d6a4d1af Migration to expect/actual: fix multiplatform integration tests 2017-09-15 18:28:50 +03:00
Mikhail Glukhikh
27615209ed Migration to expect/actual: remove header/impl from completion, tests 2017-09-15 18:28:43 +03:00
Mikhail Glukhikh
6766196bd8 Migration to expect/actual: correct multi-module QF tests 2017-09-15 18:28:36 +03:00
Mikhail Glukhikh
bc78d672c1 Migration: add quick-fix to replace header->expect & impl->actual 2017-09-15 18:28:28 +03:00
Mikhail Glukhikh
e896a1f5ea Migration: add check for illegal expect on nested in non-expect class 2017-09-15 18:28:21 +03:00
Mikhail Glukhikh
5d25106267 Migration: deprecation tests for header/impl 2017-09-15 18:28:14 +03:00
Mikhail Glukhikh
dd8bed8b46 Migration: expect/actual in diagnostic tests 2017-09-15 18:28:07 +03:00
Mikhail Glukhikh
1a2dc4c96c Migration: expect/actual in descriptor renderer 2017-09-15 18:28:00 +03:00
Mikhail Glukhikh
205272f51b Migration: add expect/actual to hasExpected... / hasActualModifier 2017-09-15 18:27:53 +03:00
Mikhail Glukhikh
0640d5618c Migration: make modifiers HEADER & IMPL deprecated 2017-09-15 18:27:47 +03:00
Mikhail Glukhikh
6650340716 Migration: expect/actual in OverrideMemberChooserObject 2017-09-15 18:27:40 +03:00
Mikhail Glukhikh
b909704bb9 Migration: expect/actual in KotlinSafeDeleteProcessor 2017-09-15 18:27:33 +03:00
Mikhail Glukhikh
31f4f2d0c9 Migration: add actual instead of impl on IMPL_MISSING 2017-09-15 18:27:26 +03:00
Mikhail Glukhikh
89c8ee8614 Migration: hasImpl -> hasExpectedModifier (OverrideMemberChooserObject) 2017-09-15 18:27:19 +03:00
Mikhail Glukhikh
280a60af6f Migration to expect/actual: some intentions 2017-09-15 18:27:12 +03:00
Mikhail Glukhikh
62ec4b5a31 Migration to expect/actual: KeywordCompletion 2017-09-15 18:27:05 +03:00
Mikhail Glukhikh
9f02a8b2a8 Migration: PlatformHeaderAnnotator -> PlatformExpectedAnnotator 2017-09-15 18:26:59 +03:00
Mikhail Glukhikh
74f81f38ba Migration to expect/actual: highlighter markers 2017-09-15 18:26:46 +03:00
Mikhail Glukhikh
2d0ac0011a Migration to expect/actual: ExpectedActualDeclarationChecker 2017-09-15 18:26:23 +03:00
Mikhail Glukhikh
c4fd1a8e5c Migration to expect/actual: ModifierCheckerCore 2017-09-15 18:26:16 +03:00
Mikhail Glukhikh
fba1a2a2db Migration to actual/expect: quick-fix CreateActualFix with tests 2017-09-15 18:26:09 +03:00
Mikhail Glukhikh
810d62bbaf Add expect & actual to MODIFIERS_TO_REPLACE table 2017-09-15 18:26:02 +03:00
Mikhail Glukhikh
eb648e20c6 Add expect & actual modifiers 2017-09-15 18:25:56 +03:00
Stanislav Erokhin
e86d2f00ff Rename isImpl to isActual in descriptors 2017-09-15 18:25:49 +03:00
Stanislav Erokhin
c8ee424f67 Rename isHeader to isExpect in descriptors 2017-09-15 18:25:41 +03:00
Stanislav Erokhin
fd6eab38e5 Regenerate comments in protobuf files for isHeader -> isExpect 2017-09-15 18:25:34 +03:00
Stanislav Erokhin
4dc47c734c Rename has[Header|Impl]Modifier() to has[Expect|Actual]Modifier() 2017-09-15 18:25:27 +03:00
Stanislav Erokhin
0bf7dc3e0c Refactoring. Replace hasModifier(IMPL_KEYWORD) to hasImplModifier() 2017-09-15 18:25:20 +03:00
Stanislav Erokhin
1ebfe1af43 Refactoring. Replace hasModifier(HEADER_KEYWORD) to hasHeaderModifier() 2017-09-15 18:25:13 +03:00
Yan Zhulanow
79b2b40289 Allow access to effectively invisible declarations in evaluator (KT-18775) 2017-09-15 17:54:46 +03:00
Yan Zhulanow
5641909d1d Parcel: Invoke box tests as an external process to prevent class clashes with IntelliJ platform 2017-09-15 17:54:46 +03:00
Mikhail Zarechenskiy
11b6382518 Revert "Setup JDK roots and initialize JDK_HOME in common core environment"
This reverts commit 05dd4714045494dcc648412t 2ea2179a242991639.
2017-09-15 16:47:42 +03:00
Mikhail Zarechenskiy
05dd471404 Setup JDK roots and initialize JDK_HOME in common core environment
#KT-20167 Fixed
2017-09-15 16:34:12 +03:00
Anton Bannykh
373bd5ff17 JS: throw exception on access to an uninitialized local variable (KT-20248 fixed) 2017-09-15 14:46:26 +03:00
Nikolay Krasko
aa442860c2 Run inline usages search in debugger under progress indicator (KT-19974)
#KT-19974 Fixed
2017-09-15 12:27:41 +03:00
Mikhail Zarechenskiy
bbf4c56c06 Update generated tests 2017-09-15 11:47:16 +03:00
Mikhail Glukhikh
faaddacec6 Fix "unexpected error type" exception in constructor conversion
So #KT-20218 Fixed
2017-09-15 11:17:21 +03:00
Mikhail Glukhikh
13fc526695 Fix "unexpected error type" exception in initializer -> getter
So #KT-19674 Fixed
2017-09-15 11:16:51 +03:00
Mikhail Glukhikh
a9ece23e63 Remove BodyResolveMode.FULL from OverrideImplementMembersHandler 2017-09-15 11:15:44 +03:00
Mikhail Zarechenskiy
a63495aa0b Use language version settings of definitely known module 2017-09-15 08:16:25 +03:00
Yan Zhulanow
26af128694 Parcelable: produce error on "CREATOR" companion object 2017-09-14 19:36:48 +03:00
Yan Zhulanow
d9f99971bb Disable old Parcelable quickfixes if @Parcelize annotation is present 2017-09-14 19:36:47 +03:00
Yan Zhulanow
e6171dc4c5 Parcelable: Add quick fixes 2017-09-14 19:36:24 +03:00
Yan Zhulanow
8eeed17b65 Add android-extensions-runtime.jar to CLI libs 2017-09-14 19:29:11 +03:00
Yan Zhulanow
9984b6f9d1 Minor: Refactoring 2017-09-14 19:29:10 +03:00
Yan Zhulanow
2fb2211a4d Kapt: Prevent kaptGenerateStubsTask from being UP-TO-DATE when there is no incremental data generated for some reason 2017-09-14 19:16:55 +03:00
Yan Zhulanow
83bf257666 Kapt: Attach kapt stub location when reporting annotation processor errors 2017-09-14 19:16:55 +03:00
Yan Zhulanow
4ac8a98050 Kapt: Hide fake "Error while annotation processing" error in Android Studio build console 2017-09-14 19:16:54 +03:00
Yan Zhulanow
69051a4764 Simplify KotlinOutputParser, remove old reflection-based logic that didn't work well with the newer versions of Android Studio 2017-09-14 19:16:53 +03:00
Anton Bannykh
74bda80ec2 JS: added forgotten JsLegacyPrimitiveArraysBoxTestGenerated.java 2017-09-14 18:55:12 +03:00
Yan Zhulanow
8e72a1211b Kapt: Add IDEA integration (KT-19097, KT-17923, KT-19823) 2017-09-14 18:40:55 +03:00
Mikhail Zarechenskiy
b574ddfba0 Deprecate syntax for assigning single named arguments to varargs
See more in KT-20171
2017-09-14 18:27:43 +03:00
Mikhail Zarechenskiy
68259f7939 Allow assigning array to vararg in named form in annotations
See more in KT-20171
2017-09-14 18:27:41 +03:00
Mikhail Zarechenskiy
f905d56b38 Don't try to get KtFile on random element as it can throw exception
For example, this can be for copied elements (DummyHolder)
2017-09-14 18:27:40 +03:00
Mikhail Zarechenskiy
b1d9abdf83 Propagate languageVersionSettings to resolution context 2017-09-14 18:27:34 +03:00
Denis Zharkov
6336ad874b Get rid of ParametersAreNonnullByDefault copy in test data 2017-09-14 18:05:32 +03:00
Denis Zharkov
24b1f2ed1f Minor. Update CliTestGenerated.Jvm::testExtraHelp test data 2017-09-14 18:05:32 +03:00
Denis Zharkov
4d95c30360 Restore -Xjsr305-annotations flag as a deprecated 2017-09-14 18:05:32 +03:00
Denis Zharkov
97fed6336b Add cli tests on different options of -Xjsr305 flag 2017-09-14 18:05:32 +03:00
Denis Zharkov
363d345752 Make default value for -Xjsr305 flag to be WARN 2017-09-14 18:05:32 +03:00
Denis Zharkov
2ca220d442 Ignore built-in type qualifier defaults when Jsr305State=IGNORE 2017-09-14 18:05:32 +03:00
Denis Zharkov
b744ed0fd3 Minor. Remove unused properties 2017-09-14 18:05:32 +03:00
Denis Zharkov
943dd96a87 Fix Jsr305State::STRICT description 2017-09-14 18:05:32 +03:00
Alexander Udalov
d32e101802 Support deprecatedName for advanced CLI arguments 2017-09-14 18:05:32 +03:00
Mikhail Glukhikh
92215b41b9 Replace resolveToDescriptor with unsafeResolveToDescriptor
Now unsafeResolveToDescriptor is equivalent to resolveToDescriptorIfAny
but throws exception in case no descriptor is found.
Old version of resolveToDescriptor is kept intact but made deprecated.
Some clarifying comments were added
2017-09-14 17:20:37 +03:00
Toshiaki Kameyama
cd6201c5df Java class with static-only methods can contain 'protected' members (#1257)
#KT-19651 Fixed
2017-09-14 15:47:10 +03:00
Mikhail Glukhikh
0f9d31c9d1 Patch resolveToDescriptorIfAny() for parameter case
Now property descriptor is returned for primary constructor val / var,
otherwise parameter descriptor is returned.
2017-09-14 15:08:06 +03:00
Mikhail Glukhikh
04b8f1db6e Minor: convert to expression body applied (resolutionApi) 2017-09-14 15:08:05 +03:00
Mikhail Glukhikh
71c2489ade Use safe resolveToDescriptorIfAny() when possible (related to EA-105681) 2017-09-14 15:08:04 +03:00
Nikolay Krasko
94e3a51a45 Test no psi stub mismatch for light classes with suspend in overloads
IdeCompiledLightClassTestGenerated is relevant.
2017-09-14 12:28:26 +03:00
Nikolay Krasko
74043089ab Generate modifier list stub under nullable type for suspend functions (KT-20185)
Otherwise there's a PSI and Stub mismatch error produced.

 #KT-20185 Fixed
2017-09-14 12:28:26 +03:00
Nikolay Krasko
b9872b7651 Render annotations in suspend functions in single modifier list (KT-20185)
#KT-20185 Fixed
2017-09-14 12:28:26 +03:00
Dmitry Petrov
d20af1133a Use captured instance in interface companion object initializer
Similar to enum entry initialization, when we have a companion object
in an interface, its constructor (or clinit) initializes its state
before the instance field in corresponding interface is initialized.
So, interface companion object must be accessed via a captured object
reference (#0, or #0.this$0 for inner anonymous objects).
2017-09-14 10:26:35 +03:00
Dmitry Petrov
179e720e4a Provide fallback flag for KT-19174
-Xno-exception-on-explicit-equals-for-boxed-null

Also unify corresponding names.
2017-09-14 10:15:28 +03:00
Dmitry Petrov
773eff1de8 Update IEEE 754 'equals' tests for LV 1.2
NB IEEE 754 doesn't say anything about nulls.
2017-09-14 10:15:01 +03:00
Dmitry Petrov
a3c4850f0d Fail with NPE on explicit 'equals' call for null platform type value 2017-09-14 10:15:01 +03:00
Dmitry Petrov
4c2cfd3ea9 Synthesized 'copy' in data classes cannot override anything since 1.3
Synthesized 'copy' introduces default values for parameters, which is
prohibited for regular overrides.
Report warning in language version 1.2-, error in 1.3+.
2017-09-14 10:13:22 +03:00
Alexander Udalov
9ae6feb2c5 Temporarily remove JvmPackageName and tests, but keep the implementation
This is needed because we want the compiler code to stay as much the
same in master and in 1.2 as possible
2017-09-13 23:23:36 +03:00
Alexander Udalov
e8e38d90ff Validate JvmPackageName annotation value and placement
- do not allow it to be used together with JvmMultifileClass (otherwise
  implementation becomes complex)
- do not allow to declare classes in a JvmPackageName-annotated file
  (similarly, the implementation of this would be much harder in the
  compiler, and there would need to be special support in the IDE)
- check that the value is a valid FQ name
- do not allow root package just in case
2017-09-13 22:59:03 +03:00
Alexander Udalov
2bb437b219 Do not load JvmPackageName-annotated parts on Kotlin < 1.2 2017-09-13 22:59:03 +03:00
Alexander Udalov
70ae1596fb Support JvmPackageName annotation in binary format
The main changes are in jvm_package_table.proto and ModuleMapping.kt.
With JvmPackageName, package parts can now have a JVM package name that
differs from their Kotlin name. So, in addition to the old package parts
which were stored as short names + short name of multifile facade (we
can't change this because of compatibility with old compilers), we now
store separately those package parts, which have a different JVM package
name. The format is optimized to avoid storing any package name more
than once as a string.

Another notable change is in KotlinCliJavaFileManagerImpl, where we now
load .kotlin_module files when determining whether or not a package
exists. Before this change, no PsiPackage (and thus, no JavaPackage and
eventually, no LazyJavaPackageFragment) was created unless there was at
least one file in the corresponding directory. Now we also create
packages if they are "mapped" to other JVM packages, i.e. if all package
parts in them have been annotated with JvmPackageName.

Most of the other changes are refactorings to allow internal names of
package parts/multifile classes where previously there were only short
names.
2017-09-13 22:59:03 +03:00
Alexander Udalov
d07b628e0c Support JvmPackageName annotation in JVM back-end
This annotation is currently internal because we only commit to its
support for our own libraries. It will be used to change JVM package
names of declarations in JDK-specific stdlib additions (now called
kotlin-stdlib-jre7/8), both to preserve source compatibility of the old
Kotlin code and to solve the split package problem (KT-19258)
2017-09-13 22:59:03 +03:00
Alexander Udalov
234148518e Temporarily remove isInitialized and tests, but keep the implementation
This is needed because we want the compiler code to stay as much the
same in master and in 1.2 as possible
2017-09-13 22:51:23 +03:00
Alexander Udalov
7d80afbe63 Avoid getting invisible_fake visibility for properties in ExpressionCodegen
Before this change, we were computing the visibility of an inherited
private property setter, and ISE at AsmUtil.getVisibilityAccessFlag
happened ("invisible_fake is not a valid visibility in backend")
2017-09-13 22:49:26 +03:00
Alexander Udalov
c6263ac8e6 Support isInitialized intrinsic for lateinit properties
See https://github.com/Kotlin/KEEP/pull/73

 #KT-9327 Fixed
2017-09-13 22:49:26 +03:00
Ilya Gorbunov
08052e63e9 Test to ensure fixed typed char array content[Deep]ToString, relates to #KT-16056 2017-09-13 20:53:17 +03:00
Anton Bannykh
2249675e59 JS: throw exception when accessing uninitialized lateinit property (KT-14964) 2017-09-13 20:16:01 +03:00
Anton Bannykh
49bc9249a1 JS: add support for the ::foo syntax (callable reference with empty LHS) 2017-09-13 20:12:48 +03:00
Anton Bannykh
497251a6d7 Revert "JS: use Mocha + NodeJs instead of Karma + PhantomJs to run stdlib tests" so that it wouldn't clash with Gradle Build transition
This reverts commit 11c83ad
2017-09-13 20:11:11 +03:00
Anton Bannykh
11c83ad0fc JS: use Mocha + NodeJs instead of Karma + PhantomJs to run stdlib tests 2017-09-13 19:43:53 +03:00
Anton Bannykh
22dc36a596 JS: enable translation of primitive arrays to TypedArray's by default (KT-17137) 2017-09-13 18:45:19 +03:00
Dmitry Jemerov
cc8fbf6078 Store third-party annotations in a separate directory 2017-09-13 17:25:20 +02:00
Alexander Udalov
296638a7c4 Minor, fix test after 60c735f2fd 2017-09-13 18:13:39 +03:00
Nikolay Krasko
cad6fdb323 Reenable workaround for JVMTI_ERROR_WRONG_PHASE in debugger tests
It was fixed in custom intellij jdk and disabled in DescriptorTestCase.
2017-09-13 16:29:51 +03:00
Nikolay Krasko
75fa982370 Minor: split long line in KotlinDebuggerSettings.kt 2017-09-13 16:29:51 +03:00
Alexander Udalov
1b45e9d517 Minor, fix before vs after in some tests 2017-09-13 15:46:37 +03:00
Alexander Udalov
b01a3eb747 Drop JvmFileClassesProvider and inline implementations
Both of its implementations called the same static function; inline
those and move related utilities to JvmFileClassUtil
2017-09-13 15:46:36 +03:00
Alexander Udalov
16c5fb6f6b Refactor and simplify JvmFileClassUtil 2017-09-13 15:46:35 +03:00
Denis Zharkov
28d785854c Optimize codegen for generic SAM types
Search abstract members in unsubstituted scope to avoid computation
of substituted descriptors for each type (effectively for each SAM call)

 #KT-20055 In progress
2017-09-13 15:34:14 +03:00
Denis Zharkov
97fd72a1e0 Minor. Drop unused function in resolution 2017-09-13 15:34:14 +03:00
Denis Zharkov
b905ddeac9 Memoize deprecations-related computations
It might be helpful for performance as these methods are called
for each resolution candidate and in the same time they scan
the whole overridden tree of a callable member
2017-09-13 15:34:14 +03:00
Denis Zharkov
4eb0f245a6 Avoid creating substitution instances for empty argument list 2017-09-13 15:34:14 +03:00
Denis Zharkov
fbdcf45976 Optimize AbstractClassTypeConstructor::equals 2017-09-13 15:34:14 +03:00
Denis Zharkov
8753baeab6 Optimize DirectoriesScope::contains
Previously its complexity was O(directoriesCount * pathSize),
now it's O(pathSize) in average
2017-09-13 15:34:14 +03:00
e5l
5bb88b659b Rename flag Xjsr305-annotations->Xjsr305 2017-09-13 15:19:54 +06:00
Zalim Bashorov
30c7f633bd KJS: don't load declarations marked by PlatformDependent annotation
#KT-17450 Fixed
2017-09-13 02:18:43 +03:00
Yan Zhulanow
d7ad973843 Kapt, minor: Remove duplicating 'visitInnerClass()' calls (rebase issue) 2017-09-12 22:17:18 +03:00
Vladimir
9a8699a2ab Kapt: kaptGenerateStubs now depends on kapt build dependencies (KT-20001) 2017-09-12 22:07:18 +03:00
Yan Zhulanow
7b4e24a454 Android Extensions: Allow LayoutContainers in inner/local classes and objects 2017-09-12 22:07:18 +03:00
Yan Zhulanow
07be1e9d10 Android Extensions: Generate proper receiver for clearFindViewByIdCache() call (KT-19742) 2017-09-12 22:07:17 +03:00
Yan Zhulanow
f84df6381e NoArg: Support @MappedSuperclass JPA annotation (KT-19692) 2017-09-12 22:07:16 +03:00
Yan Zhulanow
3f4ddb006a Android Extensions: Fix compilation when LayoutContainer is used as an interface (KT-19753) 2017-09-12 22:07:16 +03:00
Yan Zhulanow
eefb490a8a Parcelable: Use efficient serialize strategy for Java/Kotlin Parcelables only from the current source roots (KT-20029) 2017-09-12 22:07:15 +03:00
Yan Zhulanow
1b688182cd Parcelable: Use specialized write/create methods where available (KT-20057) 2017-09-12 22:07:14 +03:00
Yan Zhulanow
f6d7a17227 Parcelable: Remove 'ACC_STATIC' flag from Creator class, Dalvik dex checker hates it, and it's illegal anyway (KT-20034) 2017-09-12 22:07:13 +03:00
Yan Zhulanow
e0509e8c4d Parcelable: Specify declaration origin for the synthetic descriptors 2017-09-12 22:07:13 +03:00
Yan Zhulanow
033386b47d Parcelable: Do not check property types if the Parcelable class has a custom Parceler implementation (KT-20062) 2017-09-12 22:07:12 +03:00
Yan Zhulanow
89c5f78a8e Parcelable: Use Parcel methods for reading-writing primitive types (KT-20020) 2017-09-12 22:07:11 +03:00
Yan Zhulanow
a03c03c427 Parcelable: Handle nullability in Parcelize Parcelable serializer (KT-20032) 2017-09-12 22:07:11 +03:00
Yan Zhulanow
88138fc420 Parcelable: Use java/lang/Enum methods to read/write enum values (KT-20022) 2017-09-12 22:07:10 +03:00
Yan Zhulanow
7b96c9a003 Parcelable: Give priority to Parcelable type over objects and enums (KT-20021) 2017-09-12 22:07:09 +03:00
Yan Zhulanow
be3273a933 Parcelable: Flags argument should be propagated to the nested Parcelable's writeToParcel() (KT-20019) 2017-09-12 22:07:08 +03:00
Yan Zhulanow
3587a2a08e Parcelable: Use ClassLoader from the container class to load Parcelable (KT-20027)
When the parameter type is just "Parcelable", we would not pick the wrong (system) class loader anymore.
2017-09-12 22:07:08 +03:00
Yan Zhulanow
c9ec1a2511 Parcelable: Array serializer should correctly handle wide primitive types – long, double (KT-20002) 2017-09-12 22:07:07 +03:00
Yan Zhulanow
32fc340d62 Parcelable: Parcelize overrides describeContents despite being already implemented (KT-20026) 2017-09-12 22:07:06 +03:00
Yan Zhulanow
e645da64da Parcelable: Use the Parcelable implementation class as a containing declaration for Creator (KT-19899) 2017-09-12 22:07:06 +03:00
Yan Zhulanow
f8ca714c45 Parcelable: Cast types deserialized with Parcel.readValue() (KT-19747) 2017-09-12 22:07:05 +03:00
Yan Zhulanow
eee28d8507 Parcelable: Fix signature for Serializable Parcel serializer (KT-19749) 2017-09-12 22:07:04 +03:00
Nikolay Krasko
32c02161cd Refactoring: improve isApplicable methods in surrounders 2017-09-12 18:27:47 +03:00
Nikolay Krasko
b925df0e14 Minor: remove '\n' from if surrounder 2017-09-12 18:27:47 +03:00
Nikolay Krasko
239f88e5d3 Refactoring: use sealed classes for try-catch expression surrounders 2017-09-12 18:27:47 +03:00
Kirill Rakhman
08103d1cb4 Implement "Surround with try/catch(/finally)" and "Surround with if/else" for expressions
Fixes #KT-14175
Fixes #KT-19782
2017-09-12 18:27:47 +03:00
Mikhail Zarechenskiy
e16d16fdb7 Do not report diagnostic about annotation with receiver target twice 2017-09-12 17:39:24 +03:00
Mikhail Zarechenskiy
2048a74302 Introduce Language Feature for annotations with wrong targets
#KT-9580 Fixed
2017-09-12 17:39:23 +03:00
Mikhail Zarechenskiy
a4766cc293 Report errors on annotations with wrong use site targets
#KT-9580 In Progress
2017-09-12 17:39:22 +03:00
Mikhail Glukhikh
dafb52a44a CodeBlockModification...: count file as changed when no changed elements
It means that root PSI (KtFile itself) is changed

So #KT-19726 Fixed
So #KT-20157 Fixed
2017-09-12 17:28:32 +03:00
Mikhail Glukhikh
dd1ac5bb6b Add a set of tests for internal callables find usages
Related to KT-19811
2017-09-12 16:51:02 +03:00
Mikhail Glukhikh
97233448d0 Enclosing element: do not handle parameters of for as function ones
So #KT-19626 Fixed
2017-09-12 16:13:56 +03:00
Mikhail Glukhikh
7ae722492f Unused symbol: do not use body of function literal as scope for members
So #KT-10546 Fixed
2017-09-12 16:13:34 +03:00
Mikhail Glukhikh
4b25317ecb Minor: KtPsiUtil: extract isNonLocalCallable 2017-09-12 16:13:15 +03:00
Toshiaki Kameyama
5eb69e0ae4 KT-20010 'Replace safe access expression with 'if' expression' IDEA Kotlin plugin intention may failed (#1288)
* 'Replace safe access expression with 'if' expression' IDEA Kotlin plugin intention may failed #KT-20010 Fixed

* #KT-20010 Fixed
2017-09-12 14:54:50 +02:00
Alexander Udalov
60c735f2fd Do not use deprecated kotlin.reflect API 2017-09-12 15:08:21 +03:00
Alexander Udalov
593d6b7a95 Minor, do not use ".java.kotlin" on KClass instances 2017-09-12 15:02:25 +03:00
Alexander Udalov
ac1c7d9a6a Drop Incompatible.NoImpl, fix no "missing impl" on nested class
Header/impl declarations are now considered fully compatible even in the
case when the impl declaration has no "impl" modifier. The error about
no "impl" is now reported separately and only on the impl declaration,
never on the header declaration

 #KT-20087 Fixed
2017-09-12 14:41:11 +03:00
Vyacheslav Gerasimov
b6c32edc43 Implement Kotlin Script support in UAST
#KT-18353 Fixed
2017-09-12 13:10:38 +03:00
Vyacheslav Gerasimov
89257e6397 Implement light classes for Kotlin scripts 2017-09-12 13:10:38 +03:00
Vyacheslav Gerasimov
26cbcfa1ac J2K: AbstractCompilerLightClassTest java -> kt 2017-09-12 13:10:38 +03:00
Kirill Rakhman
7fe1e4f83e Fix grammar in inspection description 2017-09-12 12:05:30 +03:00
Dmitry Petrov
38d1d06e6e Update modifier applicability tests for LV 1.2 2017-09-12 11:54:04 +03:00
Dmitry Petrov
6b6d1e80f8 Fix enum entry reference from enum entry initialization context
Enum entries are "special" kind of singletons that should be
referenced as a captured 'this' instance inside during entry
initialization, because corresponding static fields in enum class
are not initialized yet.

 #KT-7257 Fixed
2017-09-12 11:00:24 +03:00
Anton Bannykh
40e2046e76 Updated ChangeLog.md 2017-09-11 21:06:32 +03:00
Anton Bannykh
ea9f5a7200 Update ChangeLog.md for version 1.1.50 2017-09-11 21:05:36 +03:00
Dmitry Jemerov
b2e27f9172 Add idea-jvm to ultimate classpath 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
cd44131f88 Add impl module roots also when gradle-aware make is enabled 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
0caadcd2f1 Put Kotlin runner on the first place 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
9d2b9df3b4 Correctly run multiplatform modules
When a JVM run configuration requests compiling a common module,
compile the corresponding JVM module instead.
2017-09-11 15:07:51 +02:00
Dmitry Jemerov
1d05e83401 Recognize common tests marked with annotations typealiased to @Test 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
6d30123c21 Add test dependencies when creating multiplatform projects 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
aed01c8475 Consistent naming: common platform is common, not default 2017-09-11 15:07:51 +02:00
Dmitry Jemerov
62b3059425 Support running main() under JVM in multiplatform projects
#KT-20093 In progress
2017-09-11 15:07:51 +02:00
Dmitry Jemerov
0b143e982f Always delegate build/run actions in MPP projects to Gradle 2017-09-11 15:07:51 +02:00
Alexey Andreev
c90c3e4bf5 Add hack to make JS coercion compatible with older versions of stdlib 2017-09-11 14:34:35 +03:00
Alexey Andreev
0acc96c4f3 Translate reference to kotlin.Unit to a shorter JS code 2017-09-11 14:34:35 +03:00
Alexey Andreev
2656a6a513 Eliminate redundant RHS of JS comma expression 2017-09-11 14:34:34 +03:00
Alexey Andreev
37fa45dc34 Add mechanism for type coercion in JS
Use it for char boxing/unboxing and unit materialization.
Possible to use for other purposes, for example, to add type checks
to dynamics.

See KT-18793, KT-17915, KT-19081, KT-18216, KT-12970, KT-17014,
KT-13932, KT-13930
2017-09-11 14:34:34 +03:00
Mikhail Glukhikh
ae509d5980 Unused symbol: add test to fix behaviour #KT-16318 Obsolete 2017-09-11 12:12:20 +03:00
Mikhail Glukhikh
37d2386a0b Unused symbol: handle imports from nested objects correctly
So #KT-17437 Fixed
2017-09-11 12:12:18 +03:00
Mikhail Glukhikh
7e3d3bde74 Unused symbol: never use VALUE_ARGUMENT scope for members
So #KT-10546 Fixed
2017-09-11 12:12:17 +03:00
Mikhail Glukhikh
5c4e034171 Unused symbol: do not search for internal member light methods
Use direct references search instead
So #KT-19811 Fixed
2017-09-11 12:12:16 +03:00
Dmitry Petrov
4428798c61 Change diagnostic message and rename to NESTED_CLASS_DEPRECATED 2017-09-11 09:42:18 +03:00
Dmitry Petrov
66ece54b25 Fix initialization of inner class instances in enum entries
In an inner class of the enum entry class, enum entry reference should
be generated as an outer 'this', not as a enum entry access, because
enum entry itself may be not initialized yet.
2017-09-11 09:42:18 +03:00
Dmitry Petrov
26b2f59b86 Check that resolve works properly with inner classes in enum entries 2017-09-11 09:42:18 +03:00
Dmitry Petrov
ba2c3136bb Prohibit non-inner classes in enum entries since 1.3 2017-09-11 09:42:18 +03:00
Dmitry Petrov
ea91a0794d Allow modifier 'inner' on a class nested in enum entry class 2017-09-11 09:42:18 +03:00
Dmitry Petrov
488a825349 Specialize diagnostic message for nested classes not allowed 2017-09-11 09:42:18 +03:00
Mikhail Zarechenskiy
dd9ffd10b6 Preserve order of types in new type intersector 2017-09-10 22:29:07 +03:00
Dmitry Jemerov
d8b46406ab Delete unused extension point 2017-09-09 10:01:36 +02:00
Alexey Andreev
24c6f5f0f0 JS: add test to prove that KT-19483 is no more reproducible 2017-09-08 18:27:43 +03:00
Alexey Andreev
c65a79bca4 Fix tests for inline cycle diagnostics in JS 2017-09-08 18:27:42 +03:00
Alexey Andreev
c66bc0b0e9 Remap source maps in JS DCE. Improve JS DCE error logging
See KT-19821
2017-09-08 18:27:41 +03:00
Alexey Andreev
1350e3c4ac JS: improve optimization of for loop over range literals
See KT-18329, partial fix for KT-8372
2017-09-08 18:27:40 +03:00
Alexey Andreev
502c51ccff Sanitize names for backing fields and private declarations in JS BE
See KT-1816
2017-09-08 18:27:40 +03:00
Alexey Andreev
206369c088 JS: fix capturing of reified type parameters when used as class literals
See KT-19891
2017-09-08 18:27:39 +03:00
Mikhail Glukhikh
03ce6d859f Disable destructure inspection by default
Now (by default) action is accessible as intention only
So #KT-15422 Fixed
So #KT-18666 Fixed
2017-09-08 17:41:44 +03:00
Mikhail Glukhikh
c149c37ac7 Do not suggest destructuring for invisible properties #KT-18665 Fixed 2017-09-08 17:41:44 +03:00
Mikhail Glukhikh
c4ebfe8e84 Add accessors: determine header properties more correctly
Related to KT-17322
2017-09-08 16:10:55 +03:00
Mikhail Glukhikh
13775f8637 Fix broken quick-fix tests (related to KT-17322) 2017-09-08 16:10:54 +03:00
Alexey Sedunov
bdad58cec6 Kotlin Facet: Support "implements" relation between modules
#KT-17593 Fixed
2017-09-08 15:38:14 +03:00
Alexey Sedunov
8ebc766b5b Kotlin Ultimate: Support Mocha run configurations for module directory
#KT-16814 In Progress
2017-09-08 15:38:14 +03:00
Alexey Sedunov
8b64a4c8ea Override/Implement: Drop 'impl' modifier for non-impl class members
#KT-18469 Fixed
2017-09-08 15:38:14 +03:00
Alexey Sedunov
6f8503a178 Override/Implement: Do not generate bodies for header class members
#KT-15659 Fixed
2017-09-08 15:38:14 +03:00
Alexander Udalov
6c3620f481 Suppress logging from jline
#KT-19243 Fixed
2017-09-08 15:33:30 +03:00
Nikolay Krasko
69176a146e getModuleInfo.kt: refactor 2017-09-08 15:06:03 +03:00
Pavel V. Talanov
deda5e7eee Fix navigation to script dependency sources failing
Specifically in case where some lib is in project and script dependencies at the same time
2017-09-08 15:06:00 +03:00
Pavel V. Talanov
ebd3ac6dc8 Fix script resolver failing
Specifically the case where some lib is in project dependencies and script dependencies at the same time

 #EA-105435 at least partially fixed
 #KT-19458 Fixed
 #KT-19474 Fixed
2017-09-08 15:05:58 +03:00
Pavel V. Talanov
e9ce5bbb37 Infrastructure to test sharing libs by project and scripts
Allow to test scenario where project and scripts share some jar as dependency
Refactor AbstractScriptConfigurationTest
2017-09-08 15:04:20 +03:00
Pavel V. Talanov
53144def10 AbstractScriptConfigurationTest: rewrite script template setup
Allow simpler setup of common scenarios
Do not require to define DependenciesResolver for every test
Drop redundant template files
2017-09-08 15:04:17 +03:00
Pavel V. Talanov
d7149a4083 getModuleInfo.kt: allow go get all module infos for a given psiElement 2017-09-08 15:04:14 +03:00
Pavel V. Talanov
6bec17246c Fix inspections run for script dependency source files in come cases
This filter defines which files inspections are run for
In most cases other platform code prevented inspections from running for
    library source files but this check is needed to prevent KT-19377

 #KT-19377 Fixed
2017-09-08 15:03:30 +03:00
Nikolay Krasko
6b14d15374 Clean state in AbstractKotlinKapt3IntegrationTest 2017-09-08 12:56:28 +03:00
Nikolay Krasko
c479e585ca Clean project in uast tests 2017-09-08 12:56:28 +03:00
Nikolay Krasko
fcab80db96 Add uast-tests files to our project
Copy files from obsolete project https://github.com/JetBrains/uast
2017-09-08 12:56:28 +03:00
Nikolay Krasko
6fd3ce07b3 Force remove JpsModel in BaseKotlinJpsBuildTestCase tests 2017-09-08 12:56:28 +03:00
Nikolay Krasko
eb7a984843 Store descriptor via soft reference to avoid holding project from debugger 2017-09-08 12:56:28 +03:00
Alexander Udalov
2877314313 Support "::foo" as a short-hand for "this::foo"
#KT-15667 Fixed
2017-09-08 10:59:44 +03:00
Alexey Andreev
d2ff821a3b JS: prove that lambdas in inline function compiled correctly
Obsoletes KT-19712
2017-09-08 10:57:42 +03:00
Alexey Andreev
ff0efe59f6 JS: fix error in generation of if/else statements in some cases
See KT-19495
2017-09-08 10:56:49 +03:00
Alexey Andreev
4779f4fefb JS: don't mark access to captured var as pure
See KT-19108
2017-09-08 10:56:06 +03:00
Alexey Sedunov
f2b6644db5 Kotlin Ultimate: Add JS debugger plugin dependency
This fixes tests failure due to unresolved NodeJS dependency
2017-09-08 03:42:22 +03:00
Ilya Gorbunov
980feffffa Improve @PublishedApi annotation docs #KT-19881 2017-09-07 20:07:27 +03:00
Alexey Sedunov
78b1fb2e93 Kotlin Facet: Avoid reparse of additional arguments during analysis 2017-09-07 17:39:18 +03:00
Alexey Sedunov
dcd966f7c2 Kotlin Ultimate: Support Mocha run configurations for Kotlin sources
#KT-16814 In Progress
2017-09-07 17:39:17 +03:00
Alexey Sedunov
4f647e84c9 Line Marking: Respect @Test/@Ignore annotations in test line markers
#KT-16814 In Progress
2017-09-07 17:39:16 +03:00
Toshiaki Kameyama
5a5a27b983 Intentions to generate accessors for a property #KT-17322 Fixed 2017-09-07 17:33:39 +03:00
Toshiaki Kameyama
fe0f44da94 Added "Add remaining branches with import" quick fix #KT-16033 Fixed 2017-09-07 16:24:35 +03:00
Mikhael Bogdanov
2fa4c28e0f Properly reorder arguments in anonymous object super class constructor
#KT-18356 Fixed
2017-09-07 15:18:05 +02:00
Mikhael Bogdanov
44fd8103d4 Convert ObjectSuperCallArgumentGenerator to Kotlin 2017-09-07 15:18:04 +02:00
Mikhael Bogdanov
ddb6e3307e Rename ObjectSuperCallArgumentGenerator.java to ObjectSuperCallArgumentGenerator.kt 2017-09-07 15:18:04 +02:00
Mikhael Bogdanov
529036eb78 Move ObjectSuperCallArgumentGenerator to separate file 2017-09-07 15:18:03 +02:00
Nikolay Krasko
c327118eac Remove PCE throwing as it can cancel background tasks (KT-19901)
Method can be called from the background task and be paused because
the write action is in progress. Throwing the PCE might stop the whole
task, that is wrong.

Explicit read action seems to be unneeded.

#KT-19901 Fixed
2017-09-07 16:10:09 +03:00
Nikolay Krasko
d38fd0fdf8 Need reformat inspection 2017-09-07 16:10:09 +03:00
scache
ba19931aef Keep braces in redundant cascade if #KT-19704 Fixed 2017-09-07 15:23:04 +03:00
Dmitry Jemerov
97e4dbe330 Add 'multiplatform' to spellchecker dictionary 2017-09-07 12:29:24 +02:00
Dmitry Jemerov
e1b79fc316 Show descriptions for Kotlin Gradle frameworks 2017-09-07 12:29:24 +02:00
Dmitry Jemerov
f840d0df41 Wizard for creating multiplatform projects 2017-09-07 12:29:24 +02:00
Dmitry Jemerov
140db74607 Correctly import 'implements' dependencies on root project 2017-09-07 12:29:24 +02:00
Dmitry Jemerov
369f3d6553 Don't break dependency import on invalid 'implement' dependency 2017-09-07 12:29:24 +02:00
Dmitry Jemerov
e392b4a427 Framework providers for modules of Kotlin multiplatform projects 2017-09-07 12:29:24 +02:00
Mikhail Zarechenskiy
088800d82f Report error about val reassignment via backing field since Kotlin 1.3
Also improve message for current warning

 #KT-16681 Fixed
2017-09-07 12:54:31 +03:00
Mikhail Zarechenskiy
03440210ee Introduce language version 1.3 2017-09-07 12:52:32 +03:00
Alexander Udalov
27b8b209e3 Refactor accessors for backing fields in JVM back-end 2017-09-07 12:24:54 +03:00
Alexander Udalov
326111aece Render .kotlin_module files nicely for tests 2017-09-07 12:24:53 +03:00
Mikhael Bogdanov
1cf8ee9433 Don't remove nullability assertions of anonymous object transformation
#KT-19910 Fixed
2017-09-06 17:48:13 +02:00
Ilya Gorbunov
599113b30f Fix internal KotlinVersion representation that caused invalid comparison 2017-09-06 18:45:33 +03:00
Alexey Andreev
5bf4540458 JS: fix inlining of functions derived from other modules
See KT-16408
2017-09-06 17:55:31 +03:00
Alexey Andreev
361d6dfca0 JS: rewrite source map generator to use specialized JSON writer
Fixes problems with string escaping. See KT-20005
2017-09-06 17:55:06 +03:00
Yan Zhulanow
187ca71dc6 NoArg: Fix compatibility with sealed classes with non-zero-parameter constructors (KT-19687)
Also check if a class has a sealed super class properly.
2017-09-06 17:40:20 +03:00
Yan Zhulanow
cea891c754 Kapt: Do not replace '/' with dots before converting to fqName (KT-19680)
getQualifiedName() converts slashes by itself, and it causes the internal name equality check (it.name == classFromSources.name) to fail.
This reproduces only for the pure synthetic classes (for which we don't generate Java light classes).
2017-09-06 17:40:19 +03:00
Yan Zhulanow
fe3413c291 Parcelable: Add INNERCLASS metadata to Creator factory class and its outer class 2017-09-06 17:40:19 +03:00
Yan Zhulanow
04c2e28341 Kapt: Do not use awkward ('$' -> '/') logic for KAPT3 class builder mode
So (for the most often reproduction case) #KT-19433 Fixed

Before this commit, internal names for nested classes were written as test/Foo/Bar (comparing to test/Foo$Bar in the normal mode), as getting qualified names from such internal names was trivial. But, because of IC, we needed to write class files to the disk, so our decompiler could find such "broken" classes and read it in a wrong way.
2017-09-06 17:40:18 +03:00
Yan Zhulanow
c330285fd0 Parcelable: Use innerClassNameFactory to figure out the internal name of the Creator class (KT-19680)
KAPT3 class builder mode in 1.1.4 replaces '$' (inner class name separators) with '/' by providing special innerClassNameFactory.
We should use it to be compatible with kapt.
2017-09-06 17:40:18 +03:00
Yan Zhulanow
84e59601c1 Kapt: Generic arguments in anonymous type should always be mapped to boxed types (KT-19750) 2017-09-06 17:40:17 +03:00
Yan Zhulanow
4d9a612a64 Kapt: Substitute type parameters from the actual type, not from the anonymous one (KT-19700) 2017-09-06 17:40:16 +03:00
Dmitry Jemerov
4e4291c586 Fix formatting of class headers when "blank lines after class
header" is enabled
2017-09-06 15:11:05 +02:00
Anton Bannykh
f4b329a055 JS: support @Before and @After annotations in kotlin.test 2017-09-06 14:36:45 +03:00
Dmitry Petrov
8c5d18c1f2 Tests for boxing optimization on KClass are JVM-specific 2017-09-06 14:20:05 +03:00
Dmitry Petrov
61faa068d4 Do not optimize == for KClasses in redundant boxing elimination
For primitive wrappers such as java.lang.Integer,
  jlc = java.lang.Integer.class
  jlt = java.lang.Integer.TYPE
  !(ljc.equals(ljt))
However, in Kotlin corresponding KClass instances are equal.

 #KT-17748 Fixed Target versions 1.1.50
 #KT-17879 Fixed Target versions 1.1.50
2017-09-06 09:54:36 +03:00
Dmitry Petrov
2b27e64fc8 Improve diagnostics for "not yet supported in inline"
- Tell user what exactly is not supported (e.g., local inline function)
- Reduce diagnostics range to a keyword or an identifier
  where appropriate

 #KT-16223 Fixed Target versions 1.1.50
2017-09-06 09:46:33 +03:00
Mikhael Bogdanov
160ba0c7c0 Destroy state and environment in android test 2017-09-06 08:20:33 +02:00
Mikhael Bogdanov
71663afbfe Update android test configuration 2017-09-06 08:20:33 +02:00
Mikhael Bogdanov
81a1bf3319 Recalculate max stack on method emitting: optimizations could change it 2017-09-06 08:20:32 +02:00
Nikolay Krasko
638cf346aa Add soutf template for printing current position (KT-19709)
#KT-19709 Fixed
2017-09-05 19:49:58 +03:00
Nikolay Krasko
2ce6a0eaee Minor: fix warnings in TypedHandlerTest.kt 2017-09-05 19:49:02 +03:00
Nikolay Krasko
385ff3f4eb Test for smart indent in parameters (KT-17648)
Fixed in IDEA-173208

#KT-17648 Fixed
2017-09-05 19:49:01 +03:00
Nikolay Krasko
80ffc5cd41 Make local file indent feature work for Kotlin files
Revert "Add language to formatting blocks to fetch indent settings propertly"
This reverts commit d717da5
2017-09-05 19:49:01 +03:00
Toshiaki Kameyama
e01371b231 Redundant getter / setter inspection #KT-19514 Fixed (#1282) 2017-09-05 17:27:56 +02:00
Mikhail Zarechenskiy
a3060f1073 Add test on obsolete issue
#KT-9203 Obsolete
2017-09-05 16:15:18 +03:00
Dmitry Petrov
21cdf9dd5b Add cast to expected type in call-based in-expression generation
#KT-20106 Fixed
2017-09-05 15:32:53 +03:00
Mikhail Zarechenskiy
081b732070 Improve diagnostics for lateinit properties with generic type
#KT-11834 Fixed
2017-09-05 14:44:55 +03:00
Mikhail Zarechenskiy
356f903645 Make classes for CLI public to reuse them in other tools
To configure Kotlin environment and use them in plugins for Eclipse or NetBeans
2017-09-05 14:42:48 +03:00
Mikhail Zarechenskiy
0dc29d6d7e Get rid of passing typeChecker from the call hierarchy 2017-09-05 14:41:46 +03:00
Mikhail Zarechenskiy
e7449a3584 Fix referencing inner class constructor on an outer class instance
#KT-12796 Fixed
2017-09-05 14:41:44 +03:00
Mikhail Zarechenskiy
4a6f35b9c2 Fix exception on invalid code, don't resolve uninitialized type
#KT-11963 Fixed
2017-09-05 14:41:42 +03:00
Mikhail Zarechenskiy
6d4bb229ac Fix compilation exception where overload ambiguity should be
#KT-16246 Fixed
2017-09-05 14:41:40 +03:00
Mikhail Zarechenskiy
ec512d1c8a Add tests on obsolete issues
#KT-11236 Obsolete
 #KT-12399 Obsolete
2017-09-05 14:41:34 +03:00
Dmitry Jemerov
cbe79e94a6 Update testdata 2017-09-04 20:39:52 +02:00
scache
e5b290d77f Fix replacedBaseClause for selector which has implicit receiver
#KT-19666 Fixed
2017-09-04 20:36:07 +02:00
Toshiaki Kameyama
a9a52379ee Quickfix for "variable initializer is redundant" (VARIABLE_WITH_REDUNDANT_INITIALIZER) #KT-5878 Fixed (#1281) 2017-09-04 16:58:32 +02:00
Pavel V. Talanov
653314e671 IDE script support: cancel coroutines on project disposal 2017-09-04 16:35:28 +03:00
Pavel V. Talanov
7f361c7579 Add utility for EDT coroutines to be canceled on project disposal 2017-09-04 16:33:31 +03:00
Dmitry Jemerov
7ca1fe0f55 Fix compilation 2017-09-04 14:39:25 +02:00
Alexey Andreev
b8aa2f81a2 Fix delegate property name clash in JS BE
See KT-19542
2017-09-04 15:35:35 +03:00
Alexey Andreev
28c9d274ec JS: prohibit illegal chars on dynamic call site
See KT-19540
2017-09-04 15:35:00 +03:00
Alexey Andreev
5a984a40e6 Fix JS compiler crash when translating external object fun with vararg
See KT-19793
2017-09-04 15:34:10 +03:00
Alexey Andreev
989cebe79e JS: fix bug in temporary variable eliminator
The problem was in considering `a` as trivial in following case:

```
var a = b;
```

However, that's wrong assumption, since `b` can be temporary variable
itself which is further substituted by a non-trivial expression.
2017-09-04 15:33:16 +03:00
Alexey Andreev
abb254297a Properly rename local name aliases when merging JS fragments together 2017-09-04 15:33:16 +03:00
Alexey Andreev
593aa72439 Fix bug in new JS inliner when inlining nested calls 2017-09-04 15:33:15 +03:00
Alexey Andreev
63855af026 Raise JS metadata version due to incompatible changes in inliner 2017-09-04 15:33:14 +03:00
Alexey Andreev
df7d69b5b4 Minor refactoring after improving JS inliner 2017-09-04 15:33:14 +03:00
Alexey Andreev
918ce78c5a Support inlining internal functions to friend modules in JS BE
There's one exception: if an inline internal function calls
private function, this will fail at run time.
2017-09-04 15:33:13 +03:00
Alexey Andreev
41140d00b1 JS: do not copy declarations from inline function wrapper more than once 2017-09-04 15:33:13 +03:00
Alexey Andreev
1260146d25 Use local aliases for char boxing and unboxing in JS BE 2017-09-04 15:33:12 +03:00
Alexey Andreev
7646c2fc72 Use local aliases for Kotlin runtime functions in JS BE 2017-09-04 15:33:11 +03:00
Alexey Andreev
8c256b24dc Avoid duplication of imports introduced during JS inlining 2017-09-04 15:33:10 +03:00
Alexey Andreev
f2b2e20331 Minor cleanup in JS backend 2017-09-04 15:33:10 +03:00
Alexey Andreev
b90885d1cb Support new inline function format in JS DCE tool 2017-09-04 15:33:09 +03:00
Alexey Andreev
901346243d JS: fix inlining of function that calls functions from other modules 2017-09-04 15:33:08 +03:00
Alexey Andreev
6bb5d00700 Fix inlining of default arguments in JS BE 2017-09-04 15:33:07 +03:00
Alexey Andreev
834cd1d93d Fix testdata for new JS inliner 2017-09-04 15:33:07 +03:00
Alexey Andreev
61ba6e528a Fix JS line number tests 2017-09-04 15:33:06 +03:00
Alexey Andreev
df782eaadd Fix incremental compilation to JS with new inliner 2017-09-04 15:33:06 +03:00
Alexey Andreev
eb6186b74d Fix translation of classes to work with new JS inliner 2017-09-04 15:33:05 +03:00
Alexey Andreev
8e6b1da592 Generate less JS inline function wrappers 2017-09-04 15:33:04 +03:00
Alexey Andreev
aaf3380050 Add optimizer for trivial functions with wrappers in JS BE 2017-09-04 15:33:04 +03:00
Alexey Andreev
445a80c755 Support new JS inline function format in multi-module projects 2017-09-04 15:33:03 +03:00
Alexey Andreev
7c421b0b83 Refactor JS translator to generate code for new inliner 2017-09-04 15:33:03 +03:00
Nicolay Mitropolsky
29857e48c8 KtLightAnnotationTest fix for oddly broken annotations getter 2017-09-04 15:20:20 +03:00
Nicolay Mitropolsky
be4b86e3d9 KtLightAnnotationForSourceEntry fix for smart-pointers creating
`LightElementValue` made PsiCompiledElement to make it properly anchorable when creating smartpointers, when still use `kotlinOrigin.containingFile` for it to be able to `registerProblem` on such elements. (refs KT-18054)
2017-09-04 15:20:20 +03:00
Dmitry Jemerov
b0fb3370e3 Correctly get qualified name for properties without backing field
#KT-19903
2017-09-04 13:21:03 +02:00
Dmitry Jemerov
cc6bfcfc7c Attach super line marker to name identifier
#KT-19843 Fixed
2017-09-04 13:21:03 +02:00
Dmitry Jemerov
f008736ef7 Fix package name convention pattern
#KT-19927 Fixed
2017-09-04 13:21:03 +02:00
Dmitry Jemerov
f709bd869a Accept invalid patterns in naming convention settings
#KT-19926 Fixed
2017-09-04 13:21:03 +02:00
Dmitry Jemerov
f74416a151 Cache the result of hasTopLevelCallables() for a KtFile
#KT-19885 Fixed
2017-09-04 13:21:03 +02:00
Dmitry Jemerov
839f197a1e KtFile: J2K and cleanup 2017-09-04 13:21:03 +02:00
Dmitry Jemerov
ebef2dc0cf KtFile: rename to .kt 2017-09-04 13:21:03 +02:00
dzieciolowski
80f1a1bde8 Update gradle.xml - remove typo (#1279) 2017-09-04 13:11:24 +02:00
Alexander Udalov
840fce520c Update KotlinVersion.CURRENT to 1.1.50 2017-09-04 13:09:52 +03:00
Dmitry Jemerov
2d10df1541 Fix red code: mark dependency as exported 2017-09-01 16:59:03 +02:00
Dmitry Jemerov
81d0445775 Fix master-171 build: don't use API introduced in newer IDEA 2017-09-01 16:54:24 +02:00
Dmitry Jemerov
ad37626af3 Fix compilation of KotlinBytecodeToolWindow 2017-09-01 16:41:26 +02:00
Dmitry Jemerov
59976baac2 Fix path to generated test 2017-09-01 15:27:44 +02:00
Dmitry Petrov
76acd23bd7 Revert "Fix synthetic accessor generation for properties"
This reverts commit 2427b2c
2017-09-01 16:09:29 +03:00
Dmitry Jemerov
db840a73a9 Set scope of all plugin module dependencies to provided 2017-09-01 14:06:39 +02:00
Alexander Udalov
05290c3ed2 Fix AssertionError on incompatible scopes with impl typealias
This has been introduced in 9ecd04f628
2017-09-01 14:47:29 +03:00
Pavel V. Talanov
f695ff96e8 IDEKotlinBinaryClassCache: store soft reference in UserData
Storing hard reference leads to binary headers being stored indefinitely
2017-09-01 14:30:27 +03:00
Dmitry Jemerov
0fa4e1cbaf Set scope of plugin dependencies to provided 2017-09-01 13:11:39 +02:00
Vyacheslav Gerasimov
5220dfc0ad Android: Add inspection & quickfix to convert findViewById to api 26
#KT-19940 Fixed Target Version 1.1.5
2017-09-01 13:32:52 +03:00
Vyacheslav Gerasimov
be900a76d8 Android Lint: check for array initializer in SuppressLint 2017-09-01 13:32:08 +03:00
Vyacheslav Gerasimov
f4da6c2cc6 UAST: findAttributeValue returns default value when no declared value found 2017-09-01 13:32:00 +03:00
Vyacheslav Gerasimov
56a075eab6 UAST: Fix annotation arguments processing
multiple unnamed arguments represented as value named expression with array initializer
 call kind for array in annotation argument should be "array initializer" instead of "method call"

 #KT-16600 Fixed Target Versions 1.1.5
2017-09-01 13:31:50 +03:00
Dmitry Jemerov
e0bf438195 Move .xml files back to main idea module 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
895d5fda46 Extract parts of plugin that depend on Java-only plugins to idea-jvn 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
8b0d606ab5 Move Android .xml file to idea-android module 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
9eace7b295 Move Gradle tests to idea-gradle module; remove idea dep on idea-gradle 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
d2972314bc Remove duplicate version detection code from AddKotlinLibQuickFix 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
92103ff393 Add tests for "add kotlin-reflect.jar" quickfix 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
feeacda12b Extract logic of adding a dependency to KotlinProjectConfigurator 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
f5cea51d21 idea no longer depends on idea-maven 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
bf639b1272 Move logic of EnableUnsupportedFeatureFix into KotlinProjectConfigurator 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
6fbb370eae Move coroutine state update logic to KotlinProjectConfigurator 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
e781b70170 Remove unnecessary dependency 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
6f9869ae11 Remove unnecessary dependency 2017-09-01 11:57:37 +02:00
Dmitry Jemerov
d8b6bd5cb3 Decouple idea-analysis from Android
Introduce API for extending syntax highlighting; use it in android
component
2017-09-01 11:57:37 +02:00
Dmitry Jemerov
982461e207 Remove unnecessary dependencies 2017-09-01 11:57:37 +02:00
Dmitry Petrov
5d44e095c8 Nullability assertions for extension receiver
In Kotlin 1.1 and before, there were no nullability assertions on
extension receivers, because receiver is resolved with NO_EXPECTED_TYPE.
So, if an expression of platform type is passed as an extension receiver
to a non-private function, it would fail with IllegalArgumentException.
However, if the function is private, then we generated no parameter
assertions under assumption that such function can be called from Kotlin
only, and all arguments are checked on the call site. Thus 'null' could
propagate indefinitely.

In Kotlin 1.2, we do the following:
- Generate nullability assertions for expression receivers.
NB nullability assertions are stored for ReceiverValue instances, not
for expressions: given expression can act as receiver in different
calls, each with an expected receiver type of its own.
- Generate nullability assertions for extension receivers of private
operator functions.
NB it still can throw NPE for some particular "optimized" cases, but at
least those nulls would not propagate indefinitely.

This behavior is disabled by an "advanced" command-line option
'-Xno-receiver-assertions'.
2017-09-01 09:49:21 +03:00
Dmitry Petrov
2427b2cc6c Fix synthetic accessor generation for properties
Generate synthetic accessors for property accessors only if the
corresponding methods are accessible in the current context.

 #KT-19306 Fixed Target versions 1.1.5
2017-09-01 09:48:26 +03:00
Mikhail Zarechenskiy
dde0efd8ab Refactoring: extract anonymous objects to classes, rename variable 2017-09-01 02:24:35 +03:00
Mikhail Zarechenskiy
f5222600d8 Improve diagnostics for fake calls when type inference failed
#KT-13665 Fixed
2017-09-01 02:05:58 +03:00
Mikhail Zarechenskiy
17b4874c37 Refactor FakeCallResolver, make error reporting simpler 2017-09-01 02:05:50 +03:00
Sergey Igushkin
ff1c5ad793 Merge pull request #1260 from JetBrains/kotlinx.serialization.patches/gradle
Support for gradle subplugins in Kotlin2JS compilation
2017-09-01 01:03:37 +03:00
Leonid Startsev
a0ddef22ef Extension points for serialization plugin in JS translator:
* Plugins for JS CLI compiler now can be loaded via -XPlugin option
* New extension point in project
* JS translator modified to accept synthetic declarations and call
 extension.
* Some functions made public to create a small API
2017-09-01 00:50:46 +03:00
Toshiaki Kameyama
0246b82833 @deprecated with multi-line message in Javadoc converted to @Deprecated("long ugly string") #KT-19644 Fixed (#1253) 2017-08-31 14:15:15 +02:00
Denis Zharkov
4e4bf31016 Fix loading JSR-305 nicknames for @CheckForNull annotation
For sake of working without jsr305.jar in the classpath `resolveTypeQualifierAnnotation`
may return javax.annotation.CheckForNull (although the latter is nickname itself)

 #KT-19985 Fixed
2017-08-31 15:13:26 +03:00
Denis Zharkov
ed79891ee6 Fix type mapping for parameter of Collection<Int>::remove override
In the case the single parameter of override has `Integer` type instead
of `int` type (while in common case it would be just `int`)

See the comment inside forceSingleValueParameterBoxing for clarification

 #KT-19892 Fixed
2017-08-31 12:38:08 +03:00
Denis Zharkov
73c139d250 Minor. Drop unused ExpressionCodegen::expressionJetType 2017-08-31 12:35:41 +03:00
Denis Zharkov
6af91b8c97 Drop redundant tests erroneously added in c8d25c587a 2017-08-31 12:35:05 +03:00
Denis Zharkov
80a90572d6 Fix target for annotations/metadata on open suspend functions
Get rid of rewriting of vars in FunctionCodegen::generateMethod,
just extracted generateMethodBody instead

 #KT-19814 Fixed
2017-08-31 12:27:28 +03:00
Dmitry Petrov
742fecf69c Minor: readability improvements after code review 2017-08-31 11:28:08 +03:00
Dmitry Petrov
21e3051a78 Use Name instead of String for lateinit-related StackValues
to emphasize that this is a descriptor name, not a JVM name
2017-08-31 11:28:08 +03:00
Dmitry Petrov
c8d25c587a Do not use reflection it local/top-level lateinit tests 2017-08-31 11:28:08 +03:00
Dmitry Petrov
638eb28692 Unify code for lateinit properties and local variables checking 2017-08-31 11:28:08 +03:00
Dmitry Petrov
b12e20b2a3 Minor: move local lateinit tests to lateinit/local 2017-08-31 11:28:08 +03:00
Dmitry Petrov
bbf9bf91fc Check language feature support for local and top-level lateinit vars 2017-08-31 11:28:08 +03:00
Dmitry Petrov
01cce59c35 Make sure lateinit top-level properties work in JVM BE 2017-08-31 11:28:08 +03:00
Dmitry Petrov
d951e957ea Support lateinit modifier on top-level properties
Allow lateinit modifier on top-level properties.
Modifiers 'lateinit' and 'header' are incompatible.
2017-08-31 11:28:08 +03:00
Dmitry Petrov
78b69cad77 Support lateinit local vars in redundant null check elimination
Lateinit local vars are guaranteed to be non-null after store.
So we mark such stores as storing non-null value
(could be useful for some other constructs, too),
and optimize null checks accordingly.
2017-08-31 11:28:08 +03:00
Dmitry Petrov
d0b0fdd732 Ignore lateinit local vars tests in JS and Native 2017-08-31 11:28:08 +03:00
Dmitry Petrov
c5b9d500bc Support lateinit local vars in JVM BE 2017-08-31 11:28:08 +03:00
Dmitry Petrov
53961e8df0 Check lateinit applicability for local variables
TODO probably should be refactored together with DeclarationsChecker
2017-08-31 11:28:08 +03:00
Dmitry Petrov
3bae430d49 Resolve lateinit variables
Do not report UNINITIALIZED_VARIABLE on lateinit variables
Provide delegating constructors for descriptors for compatibility.
2017-08-31 11:28:08 +03:00
Dmitry Petrov
f88cd5ed3d Allow 'lateinit' modifier on local variables 2017-08-31 11:28:08 +03:00
Pavel V. Talanov
352071dc4a Avoid creating ModuleSourceInfo instances with empty content
This is overall desirable because it means less ModuleDescriptor
    instances which is good for IDE analysis performance
2017-08-30 19:22:30 +03:00
Dmitry Jemerov
a623fb5312 Cleanup 2017-08-30 15:37:03 +02:00
Toshiaki Kameyama
29d2482b62 J2K RemovePartsFromPropertyFix 2017-08-30 15:36:58 +02:00
Toshiaki Kameyama
350cea7afd move RemovePartsFromPropertyFix.java to RemovePartsFromPropertyFix.kt 2017-08-30 15:36:26 +02:00
Toshiaki Kameyama
be64a6feeb INAPPLICABLE_LATEINIT_MODIFIER should have a quickfix to remove initializer #KT-18826 Fixed 2017-08-30 15:36:25 +02:00
Dmitry Jemerov
a68312379e Update ReadMe.md (#1274) 2017-08-30 15:25:48 +02:00
Denis Zharkov
aef5911c7e Obtain original suspend function view for inline codegen
It's necessary for generic inline suspend as a codegen
for it uses binding slice SUSPEND_FUNCTION_TO_JVM_VIEW
to generate fake continuation parameter, so all the
descriptors that are used for body generation must be
obtained from the SUSPEND_FUNCTION_TO_JVM_VIEW

 #KT-19528 Fixed
2017-08-30 16:19:43 +03:00
Alexander Udalov
abb07ced6d Minor, improve kdoc on JvmStatic 2017-08-30 15:51:30 +03:00
Alexander Udalov
fb4bf4e5b8 Report error if Java 9 module "kotlin.stdlib" is not found in the graph
Use "-Xallow-kotlin-package" to suppress this error

 #KT-19176 Fixed
2017-08-30 15:47:54 +03:00
Alexander Udalov
f47093dc45 Allow to access unexported package of named module in unnamed module in IDE
#KT-19492 Fixed
2017-08-30 15:45:45 +03:00
Alexander Udalov
290deb6ba4 Minor, improve test on Java 9 modules
Test that unnamed module does not read unexported package of a named
module
2017-08-30 15:45:45 +03:00
Alexander Udalov
09c1115ff9 Report errors on usages of unnamed module from named modules in IDE
#KT-19493 Fixed
2017-08-30 15:45:45 +03:00
Denis Zharkov
0d7c0d4e5e Add auto-generated tests after d6fbb084b1 2017-08-30 15:07:31 +03:00
Mikhael Bogdanov
b231bf0207 Switch custom jre path for run configuration from 9-ea to 9 jdk 2017-08-30 13:18:43 +02:00
Mikhael Bogdanov
ce0fb60ff4 Switch custom jre path for run configuration from 9-ea to 9 jdk 2017-08-30 12:52:44 +02:00
Denis Zharkov
d6fbb084b1 Use the same temporary trace for analyzing all candidate calls
Otherwise, when completing all the unsuccessfull candiates,
resolution of each lambda-arguments starts repeatedly for each candidate
that leads to exponential time

NB: Changes in `completeArguments` are necessary because otherwise
nested lambdas will be analyzed twice:
once for the main resolved call, and then for all candidates
that again leads to exponential complexity

 #KT-16672 Fixed
 #KT-19457 Fixed
2017-08-30 12:51:29 +03:00
Mikhael Bogdanov
84c2e01161 Update changelog for 1.1.4-3 2017-08-30 10:43:11 +02:00
Mikhael Bogdanov
68522b9f1e Use lazy logging in lowers 2017-08-30 10:41:55 +02:00
Dmitry Jemerov
dce6cb0cfc Highlight Kotlin files in build output
#KT-12246 Fixed
2017-08-30 10:18:00 +02:00
Pavel V. Talanov
4ada692421 Provide correct resolve scope to binaries in script dependencies
#KT-16760 Fixed
2017-08-29 20:55:20 +03:00
Pavel V. Talanov
a120130069 Workaround NonClasspathClassFinder not supporting inner classes
Explicitly split qualified names, can be removed once platform is fixed

 #KT-19310 Fixed
2017-08-29 20:54:25 +03:00
Toshiaki Kameyama
a6c2135851 Counter loop in Java is transformed to less effective loop in Kotlin #KT-19337 Fixed 2017-08-29 17:37:58 +02:00
Dmitry Jemerov
eefc6ebcc9 Add missing read action in KotlinBuildScriptManipulator 2017-08-29 17:33:42 +02:00
baratynskiy
67fdd9f76e javac-wrapper: fixes after rebase and review 2017-08-29 18:01:36 +03:00
baratynskiy
2dc0c55e76 javac-wrapper: get rid of TreePath because it is slow 2017-08-29 18:01:36 +03:00
baratynskiy
1b0d7ff5be javac-wrapper: constant evaluator 2017-08-29 18:01:36 +03:00
baratynskiy
4f180e1292 javac-wrapper: identifier resolver 2017-08-29 18:01:36 +03:00
baratynskiy
01883a41cb javac-wrapper: refactoring, fixes and tests 2017-08-29 18:01:36 +03:00
baratynskiy
8494e54608 javac-wrapper: -Xuse-javac -> -Xuse-javac and -Xcompile-java 2017-08-29 18:01:36 +03:00
Nicolay Mitropolsky
2224720a90 findClass is nullable in IDEA 171, so !! added 2017-08-29 17:40:53 +03:00
Nicolay Mitropolsky
108a40261b KtLightAnnotationForSourceEntry fix for reading unnamed java-annotation parameter 2017-08-29 17:32:07 +03:00
Sergey Igushkin
e1924e0d2f (minor) Modify warning logic for separate classes dirs opt-out flag
(cherry picked from commit 0dfe1a1)
2017-08-29 14:39:17 +03:00
Sergey Igushkin
0e28d612e7 Add a test for the opt-out flag for disabling separate classes directory
(cherry picked from commit 393966d)
2017-08-29 14:39:17 +03:00
Sergey Igushkin
0263919dbd Provide an opt-out flag for separate classes dirs with Gradle 4.0+
Issue #KT-19774 Fixed

(cherry picked from commit 2aa6f5a)
2017-08-29 14:39:17 +03:00
Dmitry Jemerov
843a9871b1 Detect library kind field based on type, not name 2017-08-29 10:29:22 +02:00
Dmitry Jemerov
106db13a6a Add missing read action (EA-105188 - assert: FileManagerImpl.findFile) 2017-08-29 10:16:35 +02:00
Dmitry Jemerov
f37cc9c8ef Start read action at correct time (EA-105045) 2017-08-29 10:16:35 +02:00
Dmitry Jemerov
f7f3bacc8e Add missing write action (EA-102929) 2017-08-29 10:16:34 +02:00
Dmitry Jemerov
cc5d23440e Correctly check for project disposed (EA-103064) 2017-08-29 10:16:33 +02:00
Alexey Tsvetkov
ac3beabf43 Update 'idea.plugins.compatible.build' in KotlinCoreEnvironment
When compiler test was run before Intellij tests,
KotlinCoreEnvironment set the 'idea.plugins.compatible.build'
system property to '171.9999', which then prevented
Kotlin plugin from loading in Intellij tests (so all these tests failed),
because Kotlin plugin has 'sinceBuild' set to '172.1'.
2017-08-29 04:28:10 +03:00
Alexey Tsvetkov
cb1ffdccd7 Add test where unused file is removed 2017-08-29 04:28:10 +03:00
Alexey Tsvetkov
10feac9402 Remove CacheVersionChangedIT#testExperimentalCacheVersionChanged
experimental-format-version.txt was removed recently.
See also 534db2d45b
2017-08-29 04:28:09 +03:00
Alexey Tsvetkov
8e10a22aab Use correct task name in KaptIncrementalIT test 2017-08-29 04:28:09 +03:00
Alexey Tsvetkov
66a77c7ec2 Fix Gradle IC cache version checking 2017-08-29 04:28:09 +03:00
Alexey Tsvetkov
cf72b14b34 Fix typo in test name 2017-08-29 04:28:08 +03:00
Alexey Tsvetkov
141c889a84 Make test case more useful 2017-08-29 04:28:08 +03:00
Alexey Tsvetkov
5f9bad5905 Add JS specific build logs to inline properties IC tests
Unlike the JVM target platform, the JS back-end does
not track getters' and setters' usages separately,
so when either accessor of some property is changed,
all usages of that property will be rebuilt.
2017-08-29 04:28:07 +03:00
Alexey Tsvetkov
73b63bb343 Refactor inline properties tests 2017-08-29 04:28:07 +03:00
Alexey Tsvetkov
44e8ae3571 JS IC: detect inline function changes 2017-08-29 04:28:07 +03:00
Alexey Tsvetkov
b73d5cbe1f Mock constant search in JPS tests 2017-08-29 04:28:06 +03:00
Alexey Tsvetkov
2312013c41 Move JVM specific IC tests to separate dir 2017-08-29 04:28:06 +03:00
Alexey Tsvetkov
556c43ae00 Update lookup tracker test "classifierMembers"
Before the change, the initial build has been failing,
so lookups from deserialized descriptors were not tested.
2017-08-29 04:28:06 +03:00
Alexey Tsvetkov
4a591bf5b6 Avoid processing JS IC output when compilation failed 2017-08-29 04:28:05 +03:00
Alexey Tsvetkov
66cb45c202 Minor: replace forEach with filterTo 2017-08-29 04:28:05 +03:00
Alexey Tsvetkov
dbe3baf740 Minor: mark calculateSourcesToCompile abstract 2017-08-29 04:28:04 +03:00
Alexey Tsvetkov
919daefb0e Rename IncrementalCacheImpl->IncrementalJvmCache 2017-08-29 04:28:04 +03:00
Alexey Tsvetkov
093bbc069a Fix typo destonationDir->destinationDir 2017-08-29 04:28:04 +03:00
Alexey Tsvetkov
b28382b8e7 Ignore out directory everywhere
After IDEA-175172 JPS does not use Gradle's output directories
when buildsing imported projects.
Now JPS uses an `out/` directory instead,
which wasn't gitignored anywhere besides the project's root.
2017-08-29 04:28:03 +03:00
Alexey Tsvetkov
1c4ada2008 Fix searching serialized classes package contains multiple fragments 2017-08-29 04:28:03 +03:00
Alexey Tsvetkov
b54414d628 Implement Gradle JS IC support
#KT-19956 fixed

To try the experimental JS IC add
'kotlin.incremental.js = true' to a 'local.properties'
or 'gradle.properties' file in Gradle project's root.
2017-08-29 04:23:02 +03:00
Alexey Tsvetkov
eeb90656dc Exclude generated IC tests from ant build
Generated tests depend on the annotations from the `tests-common` module.
Testing utils from test root of the `incremental-compilation-impl` module
are also used in Gradle tests, so the test root is built in the ant build too.
However building `tests-common` separately from the compiler is complicated,
so I decided to exclude generated tests from 'kotlin-build-common-test.jar'.
2017-08-29 02:24:38 +03:00
Alexey Tsvetkov
7ecf5abdc7 Add class hierarchy tests to JS and JVM IC tests 2017-08-29 02:24:38 +03:00
Alexey Tsvetkov
0a5fe3ef7c Move JVM specific IC tests with class hierarchy changes 2017-08-29 02:24:38 +03:00
Alexey Tsvetkov
e16c5ddb97 Avoid using JVM only APIs in IC tests to reuse with JS 2017-08-29 02:24:38 +03:00
Alexey Tsvetkov
23bc907d3f Move multi-module IC tests to separate dir
At the moment they are used only with JPS
2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
166883d847 Move JVM specific IC test data to separate dir 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
7810da7018 Add IC compiler tests with Java 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
71e8f16906 Generate IC compiler tests instead of using parametrized runner
# Conflicts:
#	compiler/incremental-compilation-impl/incremental-compilation-impl.iml
2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
52b638ddb3 Throw exception if initial build has failed in IC tests 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
c7775b8d11 Write build info only on successful build 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
20551f6c99 Do not report error when JS IC is enabled and no source files is specified 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
bb1cba67b7 Implement JS IC 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
4aea9b349c Refactor incremental services 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
356536d32b Update inputs cache on rebuild 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
20b14d4121 Extract IncrementalJvmCompilerRunnerTest 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
6fedf07f56 Introduce ChangesCollector 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
d4d684a7f0 Introduce IncrementalCompilerRunner#makeServices 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
65529fa866 Introduce IncrementalCompilerRunner#markDirty 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
53d911ab99 Move IncrementalCompilerRunner to separate file 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
5ddc8d83bb Move compileIncrementally to common IC 2017-08-29 02:24:37 +03:00
Alexey Tsvetkov
60f68266dd Continue extracting common IC code 2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
9727ec401b Remove Target parameter from GeneratedFile 2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
af73082fcc Begin extracting common IC code 2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
508d96836c Remove compiledWithErrors param
`updateIncrementalCache` is not called when
code does not compile.
2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
d1fd88fb8e Minimize usage of TargetId in IC 2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
a076b4614e Refactor computeChanges 2017-08-29 02:24:36 +03:00
Alexey Tsvetkov
3ad5e78d77 Extract common caches 2017-08-29 02:24:36 +03:00
Toshiaki Kameyama
367b9f6664 "Redundant setter parameter type" range includes whole parameter declaration #KT-19648 Fixed (#1267) 2017-08-28 17:06:10 +02:00
Pavel V. Talanov
e3b7f6d698 Prevent multiple concurrent 'checkHideNonConfiguredNotifications' calls 2017-08-28 16:18:44 +03:00
Nicolay Mitropolsky
6953ae79e2 Fix for KtLightParameter and KtLightParameterList equality 2017-08-28 15:57:44 +03:00
Nicolay Mitropolsky
f8f5494d79 KotlinLightConstantExpressionEvaluator fix for processing Java-sourced annotation entry value 2017-08-28 15:55:57 +03:00
Dmitry Jemerov
ceae10f451 Update .iml 2017-08-28 12:03:45 +02:00
Dmitry Jemerov
1814f3172a Fix compilation 2017-08-28 11:32:38 +02:00
Dmitry Jemerov
5b8e5fb9aa Compile kotlin-gradle-tooling against JDK 6 2017-08-28 10:50:52 +02:00
Dmitry Jemerov
f07d4901ca Reset kind for incorrectly imported libraries
#KT-19847 Fixed
2017-08-28 10:36:25 +02:00
Alexander Udalov
cdda5d39e5 Use ResolvedCall to generate callable reference receiver
This will be helpful in supporting KT-15667
2017-08-28 10:42:05 +03:00
Alexander Udalov
c420e2bfa5 Refactor FunctionReferenceGenerationStrategy
Draw a clear distinction between the referenced function's parameters
and the anonymous synthetic function's parameters (see the comment).
This will be useful in supporting advanced callable reference features
like KT-8834
2017-08-28 10:22:52 +03:00
Nikolas Havrikov
3d8b15d9db Fixed trailing underscores in numeric literals (#1264)
This change prohibits such illegal numeric literals as 13_37_ or 0xCAFE_BABE_ (note the trailing underscore).
2017-08-26 16:07:35 +03:00
Alexander Udalov
fac207ce7c Minor, improve error message in BuiltInDecompilerConsistencyTest 2017-08-25 15:40:40 +03:00
Alexander Udalov
38849893b6 Temporarily ignore some multiplatform IDE tests 2017-08-25 15:40:39 +03:00
Alexander Udalov
b87abc9f0f Relax rules related to noinline/crossinline/reified in header/impl functions
See the comments in KT-18752 for the current resolution

 #KT-15377 Fixed
 #KT-18752 Fixed
2017-08-25 15:40:38 +03:00
Alexander Udalov
d1cff41ce0 Treat nested class of header class as header
Note that the quick fix to implement header class works incorrectly when
that class has nested classes at the moment; this should be fixed
separately

 #KT-15494 Fixed
 #KT-18573 Fixed
2017-08-25 15:40:37 +03:00
Alexander Udalov
56b507d141 Remove obsolete code from ModifiersChecker
Simplify existing code and move closer to usages
2017-08-25 15:40:37 +03:00
Alexander Udalov
3a2d93f73e Do not report "header with no impl" on incorrect header
Descriptor for a 'header' member in a non-'header' class now has
isHeader = false

 #KT-18442 Fixed
2017-08-25 15:40:36 +03:00
Alexander Udalov
6cb4916dee Refactor and simplify PlatformHeaderAnnotator 2017-08-25 15:40:35 +03:00
Alexander Udalov
59c49675b0 Improve header-impl mismatch diagnostic rendering in IDE
Use HTML instead of text to render line breaks and lists correctly
2017-08-25 15:40:34 +03:00
Alexander Udalov
3bc8ca5913 Report "declaration should be marked with impl" when possible
Also support a quick fix to add 'impl' modifier (KT-18454), although it
doesn't work yet on classes because there's no error on them in the IDE

 #KT-18087 Fixed
 #KT-18452 Fixed
 #KT-18454
2017-08-25 15:35:05 +03:00
Alexander Udalov
9ecd04f628 Improve diagnostics on header/impl classes when scopes don't match
Try to report most of the errors on the actual members of the impl
class. In many cases, there's a 1:1 mapping of header to impl class
members, so the error "some members are not implemented" on the class
declaration itself is redundant. Exceptions include functions/properties
from supertypes (there may be no other place to report a signature
mismatch error in this case), functions/properties not marked with
'impl' (the checker is only run for declarations explicitly marked with
'impl') and default constructors (the checker is not run for them)

 #KT-18447 Fixed
2017-08-25 15:35:05 +03:00
Alexander Udalov
74ba0080b1 Improve header/impl mismatch diagnostic messages
Try to report most mismatch errors on the 'impl' declaration. Only
report a mismatch error on the 'header' declaration if no error would be
otherwise reported on any 'impl' declaration in the compilation unit.
Also render declaration kind in the message

 #KT-18447 In Progress
2017-08-25 15:35:05 +03:00
Alexander Udalov
472959aca1 Improve rendering of modifiers in DescriptorRenderer
* Use bold font to render all modifiers
* Render 'external' according to the style guide, right after modality
2017-08-25 15:35:05 +03:00
Alexander Udalov
f01e0ef335 Minor, rename renderer configuration parameter 2017-08-25 15:35:04 +03:00
Stanislav Erokhin
e65a62c48c Minor. regenerate tests: kt19767_3 in JS muted. 2017-08-25 03:48:55 +03:00
Stanislav Erokhin
2ceb8cef36 [NI] Use same ResolvedCall when run completion
It is necessary, because some clients store this ResolvedCall to other
places, for example for get call it stored to INDEXED_LVALUE_GET
2017-08-25 03:38:49 +03:00
Stanislav Erokhin
98eae4e7ee [NI] Support Exact and NoInfer annotations 2017-08-25 03:38:48 +03:00
Stanislav Erokhin
d1e52e76f9 [NI] Reduced allowed depth in incorporation
We set it to 1 now, because otherwise there is examples where
incorporation work too long. We will fix such cases in the future,
but seems like 1 is also good depth delta for incorporation
2017-08-25 03:38:47 +03:00
Mikhail Zarechenskiy
f31c48017b [NI] Don't process lambda until expected type will be fixed 2017-08-25 02:47:46 +03:00
Simon Ogorodnik
ff4f928420 KT-19896: Fix force parenthesizing of multiline elvis
#KT-19896 fixed
2017-08-25 01:25:58 +03:00
xiexed
c163e71662 Spring testAmbiguousBean formatting fix (#1261) 2017-08-24 19:19:36 +03:00
Dimach
b988fb701d KT-17888 Inspection to warn about suspicious combination of == and === 2017-08-24 18:14:24 +02:00
Dmitry Jemerov
83a1d6e5ca Avoid exception from autoimport fix with misconfigured analyzer 2017-08-24 16:55:01 +02:00
Dmitry Jemerov
8cf7f7a8f3 Don't break entire highlighting if exception is thrown from one quickfix 2017-08-24 16:55:01 +02:00
Leonid Startsev
749a574234 Support for gradle subplugins in Kotlin2JS compilation
Because ServiceLoader can't check generic argument of
KotlinGradleSubplugin in runtime, we have to manually check the type in
`isApplicable`.
2017-08-24 17:26:01 +03:00
Mikhail Zarechenskiy
e666b87545 [NI] Support AllCandidates mode for features in IDE 2017-08-24 13:50:11 +03:00
Mikhail Zarechenskiy
3f8a685ace [NI] Make return type of !! operator definitely not-null 2017-08-24 13:50:11 +03:00
Mikhail Zarechenskiy
d18a14b717 [NI] Eliminate special intersection type from result type 2017-08-24 13:50:10 +03:00
Mikhail Zarechenskiy
51be629e13 [NI] Pass resulting constraint system for error candidate 2017-08-24 13:50:10 +03:00
Mikhail Zarechenskiy
6f397f8512 [NI] Drop useless isEmpty property from NewTypeSubstitutor 2017-08-24 13:50:10 +03:00
Mikhail Zarechenskiy
9f2bf066b9 [NI] Transform anonymous types of expected type for delegation 2017-08-24 13:50:09 +03:00
Mikhael Bogdanov
1a05df204e Properly check expression nullability on attempt to apply == optimizations
#Fix KT-19767
2017-08-24 09:51:55 +02:00
Dimach
f0035a7be0 KT-17379: Fix J2K removal of parentheses in multiline expressions
When there is multiline polyadic expression with some operators
J2K should keep surrounding parentheses, otherwise
operators will be dangling due resolved to prefix variant

 #KT-17379 fixed
2017-08-23 20:47:01 +03:00
Dimach
0920b2574c KT-10375, KT-19523: Fix J2K hex literal number conversion issues.
#KT-10375, #KT-19523 fixed
2017-08-23 20:19:57 +03:00
Alexander Udalov
08e090bf5e Include JDK home path into virtual file paths in CoreJrtFileSystem
The problem in KT-19833 is caused by the fact that the application
environment instance is shared between consecutive runs of the compiler
in one Make action (KotlinCoreEnvironment.ourApplicationEnvironment).
If the JDK 8 module is compiled first, the created application
environment has no JRT file system, and once the JDK 9 module is
compiled later, that environment is not recreated and thus classes from
JDK 9 are unresolved.

To mitigate this, split the CoreJrtFileSystem implementation into the
file system itself which is global per application, and CoreJrtHandler
which is bound to a particular JDK home location. CoreJrtVirtualFile
paths now consist of the path to the JDK home, the "!/" separator, and
the path to the file itself, e.g.
"/usr/lib/jvm/java9!/modules/java.base/java/lang/Object.class". The
implementation is inspired by CoreJarFileSystem & CoreJarHandler.

No tests added because the application environment is _not_ shared in
tests. Also, a JDK 9 module is going to be added to the Kotlin project
soon, and that will serve as a test

 #KT-19833 Fixed
2017-08-23 18:08:30 +03:00
Alexander Udalov
c142db15fa Rename CoreLocalPathVirtualFile -> CoreJrtVirtualFile 2017-08-23 18:08:29 +03:00
Toshiaki Kameyama
46a1c8ca12 Repeated annotation @Deprecated after J2K for method with annotation and javadoc #KT-19351 Fixed (#1251) 2017-08-23 18:05:04 +03:00
Simon Ogorodnik
91f50c99e7 Add benchmark action for highlighting 2017-08-23 17:19:36 +03:00
Pavel V. Talanov
7fecec1141 lightAnnotations: remove several brittle assertions
Add some test cases with "red" code
2017-08-23 17:12:56 +03:00
Nicolay Mitropolsky
a6b446cc4f Correct 'asJava' view of annotations as annotation arguments
Fix light elements for nested arrays/annotations inside annotations

 #KT-18378 Fixed
2017-08-23 17:12:55 +03:00
Stanislav Erokhin
6eb534fca8 [NI] Fix processParts in KotlinResolutionCandidate 2017-08-23 15:53:53 +03:00
Mikhail Zarechenskiy
c45f86a2fc [NI] Resolve function literals in block as lambda expression 2017-08-23 15:53:52 +03:00
Mikhail Zarechenskiy
08964006de [NI] Avoid type capturing for types that can contain type variables 2017-08-23 15:53:51 +03:00
Mikhail Zarechenskiy
e040a317cc [NI] Store setValue with fresh type variables before substitution 2017-08-23 15:53:50 +03:00
Mikhail Zarechenskiy
55d1130dfc [NI] Add getters to avoid inspections about useless boolean expressions 2017-08-23 15:53:49 +03:00
Mikhail Zarechenskiy
f075934697 [NI] Pass candidates with wrong visibility in debugger context
See test 'privateMembersPriority' (KT-10634)
2017-08-23 15:53:48 +03:00
Mikhail Zarechenskiy
963ab7f27f [NI] Fix KNPE, exception occurred when element is synthetic 2017-08-23 15:53:47 +03:00
Mikhail Zarechenskiy
f42be4aea2 [NI] Fix exception explicit qualified receiver and dispatch receiver 2017-08-23 15:53:46 +03:00
Stanislav Erokhin
9f71de5f66 Add test for lambda as last expression in lambda 2017-08-23 15:53:45 +03:00
Stanislav Erokhin
74e07b6580 Add regression test for no resolution recursion 2017-08-23 15:53:44 +03:00
Stanislav Erokhin
d9eef94a8e [NI] Support smartcast info in ResolvedCall on receivers 2017-08-23 15:53:43 +03:00
Stanislav Erokhin
cb1270836c [NI] Introduced ResolutionAtom's
Introduced new model for resolution result: tree of ResolvedAtoms.
Moved all postprocessing for arguments to front-end module.
Do not create freshDescriptor -- use freshTypeSubstitutor directly.
Removed Candidates for variables+invoke.
Add lazy way for argument analysis -- do not analyze all arguments
if we have subtyping error in first argument, but if we want report
all errors, then all arguments checks will be performed.

Future improvements:
  - optimize constraint system usage inside ResolutionCandidate
  - improve constraint system API
  - improve diagnostic handlers
2017-08-23 15:53:42 +03:00
Stanislav Erokhin
76012f6603 Minor. rename ConstraintSystemCompleter
In front-end we have other ConstraintSystemCompleter and because of this
in dist we have ambiguity(because there all src folders compiles inside
same module.
2017-08-23 15:53:41 +03:00
Stanislav Erokhin
e011e443cc [NI] Implement next call completer.
Type inference completer features:
  - type variables depended from result type will be fixed in the end
  - type variables with proper constraints will be fixed first
  - fixation via groups "accessible" via constraints is supported

 TODO:
  - stable order via PSI order
  - argument constraint should rewrite position if constraint is the
      same as upper bound for type parameter
2017-08-23 15:53:40 +03:00
Stanislav Erokhin
3cf240340c [NI] Extract logic about fixation order to separated component 2017-08-23 15:53:39 +03:00
Stanislav Erokhin
ff1e230828 [NI] Use right scope for callable reference resolution
Previously was used scope for top-level call. It isn't correct because
if we have callable reference inside lambda -> scope is different.
2017-08-23 15:53:38 +03:00
Stanislav Erokhin
da003d48ff Support isSuccessful in SuccessfulResultCollector
Since now SuccessfulResultCollector do not run computation of
resultingApplicability for error candidate before
getFinalCandidates(). It is very useful because we can do not run
all checks for error candidates if we have not-error candidate.
2017-08-23 15:53:37 +03:00
Stanislav Erokhin
6b8293ae5b Refactoring. Remove ResolutionCandidateStatus.
Use diagnostics directly.
Also TowerCandidate since now know only about applicability
and not about diagnostics itself.
2017-08-23 15:53:36 +03:00
Stanislav Erokhin
aca21c847d [NI] Fix resolution for callable references to nested class members 2017-08-23 15:53:35 +03:00
Stanislav Erokhin
1ae4ad1598 [NI] Do not take type advice for delegation if type is not fixed 2017-08-23 15:53:34 +03:00
Stanislav Erokhin
cdaa98fb63 [NI] Fixes after review 2017-08-23 15:53:33 +03:00
Stanislav Erokhin
2b01b91315 [NI] Refactoring: KotlinCallContext to stateless component (2) 2017-08-23 15:53:32 +03:00
Stanislav Erokhin
e88c1b4f0a [NI] Refactoring: KotlinCallContext to stateless component (1) 2017-08-23 15:53:31 +03:00
Stanislav Erokhin
9bbfac11b4 [NI] Add common supertype for PSI lambda arguments
Also move initial dataFlowInfo to lambda arguments.
As result, we can not store outer call for postpone call arguments
2017-08-23 15:53:30 +03:00
Vyacheslav Gerasimov
aedb4c0ade Android Lint: Fix constant evaluation in annotation parameter
#KT-17785 Fixed Target Versions 1.1.5
2017-08-23 13:18:56 +03:00
Vyacheslav Gerasimov
2e1edaf3d4 Uast: Fix getExpressionType for elvis expression
#KT-18997 Fixed Target Versions 1.1.5
2017-08-23 13:18:49 +03:00
Vyacheslav Gerasimov
e06cb1ec39 Android Lint: Use Uast to check for SuppressLint annotation
#KT-14800 Fixed Target versions 1.1.5
2017-08-23 13:18:42 +03:00
Vyacheslav Gerasimov
cb3a8d87d0 Android Extensions: Correctly handle namespaces in layout xml
#KT-19451 Fixed Target versions 1.1.5
2017-08-23 13:18:34 +03:00
Simon Ogorodnik
1dfa05fe49 KT-19769: Optimize PerModulePackageCacheService
#KT-19769 fixed
2017-08-22 19:37:22 +03:00
Denis Zharkov
ad9fe53ee2 Avoid local var entry for continuation parameter in suspend function
The primary reason is getting rid of redundant stack spilling, but also
it's not very sensible to have such entry since the parameter
is synthetic
2017-08-22 18:43:31 +03:00
Denis Zharkov
fcd7677a3f Fix compatibility of suspend functions with strict bytecode analyzers
In short, some of the bytecode analyzers assume that there could be
no stores instructions into parameter vars with value of different
types (even when the value type is a subtype)

See the issue for details

 #KT-19713 Fixed
2017-08-22 18:43:26 +03:00
Sergey Igushkin
d5f0607cef Add tests for java-library support. 2017-08-21 17:21:12 +03:00
Sergey Igushkin
1848bc1840 Support java-library plugin: register Kotlin output for consumers
Issue #KT-18497 Fixed
2017-08-21 17:21:03 +03:00
Vyacheslav Gerasimov
f941186f75 UAST: Properly handle annotations on local variables 2017-08-21 15:02:01 +03:00
Vyacheslav Gerasimov
c549c63100 Light Classes: Correctly handle annotations for property parameters
When getting annotations for KtLightParameter which is property parameter we should return annotations for parameter instead of property

#KT-19671 Fixed
2017-08-21 15:01:51 +03:00
Mikhael Bogdanov
1e73921200 Update changelog for 1.1.4-2 2017-08-18 18:23:10 +02:00
Pavel V. Talanov
c132f3b0d1 KT-19276: Drop exception logging on loading script definitions failure
See YT discussion
Have to come up with more meaningful diagnostics on definition loading

#KT-19276 Fixed
2017-08-18 19:11:35 +03:00
Pavel V. Talanov
6424b6760f Remove StorageComponentContainerContributor::onContainerComposed
Rename addDeclarations -> registerModuleComponents
Use it to provide SamWithReceiverResolver extensions instead

Post construction on container composition can be achieved
    but manually inserting injections where it seems appropriate
    is bug prone
This fixes a bug where SamWithReceiverPlugin extension was not registered
    for some containers in IDE which led to incorrect highlighting in IDE
Add IDE test for applying SamWithReceiver plugin

 #KT-18062 Fixed
2017-08-18 19:11:25 +03:00
Yan Zhulanow
6f180416b1 Pass SamConversionResolver explicitly cause it should be call site module-local 2017-08-18 19:11:21 +03:00
Toshiaki Kameyama
f0f6a252a5 Offer to make INVISIBLE_MEMBER protected if referenced from subclass
So #KT-19614 Fixed
2017-08-18 15:53:41 +03:00
Mikhail Glukhikh
0adf1d210f Make KtPureElement.getParent() nullable #KT-19760 Fixed
The reason is KtFile.getParent() is a containing directory which is nullable
2017-08-18 15:36:41 +03:00
Amane Nikaido
0fd5c6f1ca KT-19634: Fix <boxed_value> == <primitive_value> converted to reference equality
#KT-19634 fixed
2017-08-18 15:20:26 +03:00
Mikhail Glukhikh
9dc5354f24 Eliminate some warnings (mostly redundant is checks in whens) 2017-08-18 15:16:59 +03:00
Mikhail Glukhikh
3623f581b8 Eliminate a set of warnings, mostly nullability ones 2017-08-18 15:10:27 +03:00
Toshiaki Kameyama
82fc221470 Add "flip equals" intention for String.equals extension from stdlib
So #KT-19282 Fixed
2017-08-18 14:34:14 +03:00
Alexander Udalov
0efdcb59fa Increase -XX:ReservedCodeCacheSize for other IDEA run configurations
See 4092d754c6
2017-08-18 12:36:21 +03:00
Mikhail Glukhikh
2b90a67bc1 Minor: report "redundant override" only on 'override fun'
Related to KT-19428
2017-08-18 12:23:21 +03:00
takahirom
806aa7d4c1 Add inspection for redundant overrides that only calls the super method
So #KT-19428 Fixed
2017-08-18 12:05:02 +03:00
Mikhael Bogdanov
8af7a25f8e Update maxStack on synthetic instruction insertion
#KT-19723 Fixed
2017-08-17 20:02:29 +02:00
Dmitry Jemerov
39599fc7c9 Don't detect library kind for pure JVM projects
Also require .kjsm to detect JS libraries; don't detect jars containing
only .js files as JS libraries

 #KT-19717 Fixed
2017-08-17 16:55:50 +02:00
Dmitry Jemerov
99a402ee30 Correctly show quick doc for lookup elements that only have descriptors
#KT-19716 Fixed
2017-08-17 16:53:54 +02:00
Alexander Udalov
4d2fbf1801 Fix reflection for local delegated properties inside interface
#KT-19690
2017-08-17 15:35:11 +02:00
Mikhael Bogdanov
97d46e76f5 Use 'DefaultImpls' as owner for interface local delegated properties
#KT-19690 Fixed
2017-08-17 15:35:10 +02:00
Toshiaki Kameyama
905b8cc4e9 long == <int_literal> in Java converted to red code in Kotlin #KT-19393 Fixed 2017-08-17 16:01:48 +03:00
Mikhael Bogdanov
79ecc7fd5c Don't recognize nullable function types as inlinable
#KT-19679 Fixed
2017-08-17 14:24:00 +02:00
Nicolay Mitropolsky
1b2e28d467 SpringKotlinAutowiringInspection: workaround for nameless property (EA-104960) 2017-08-17 14:31:24 +03:00
Nicolay Mitropolsky
f7a1c71b54 Ultimate tests repair: SpringInspectionTestGenerated.testAutowiring_inspectionData_Inspections_test (KT-18847) 2017-08-17 14:31:24 +03:00
Alexander Udalov
770441c212 Merge "diagnostic with Java 8" tests with general diagnostic tests 2017-08-17 13:15:18 +03:00
Alexander Udalov
8db736e2b4 Support FULL_JDK directive in diagnostic tests 2017-08-17 12:35:56 +03:00
Alexander Udalov
7601666ec0 Minor, remove unused AbstractDiagnosticsWithFullJdkTest 2017-08-17 12:35:55 +03:00
André Oriani
a24c9a987f Improve Boolean infix functions' documentation (#1249) 2017-08-17 11:53:39 +03:00
Toshiaki Kameyama
be664e26f7 KT-18232: Kotlin code converter misses annotations
#KT-18232 Fixed
2017-08-17 02:30:06 +03:00
Dmitry Jemerov
4092d754c6 Increase -XX:ReservedCodeCacheSize to avoid warning in debug IDEA 2017-08-16 17:44:44 +02:00
xiexed
12eb4ef37a KotlinUastLanguagePlugin#convertElementWithParent NPE fix when parent is null (#1247) 2017-08-16 17:47:40 +03:00
Dmitry Jemerov
a2a018eadb Pluggable platforms in IDE plugin 2017-08-16 15:51:41 +02:00
Dmitry Jemerov
f7c17d6a64 Naming convention inspections 2017-08-16 15:45:33 +02:00
Anton Bannykh
6a5d8dcc82 JS: reduce HashMap memory footprint 2017-08-16 13:23:36 +03:00
Anton Bannykh
070e35bc15 JS: removed app-module-path dependency from integration tests 2017-08-16 13:21:46 +03:00
Anton Bannykh
a641838368 JS: clean up the unit test intergartion tests build file 2017-08-16 13:21:46 +03:00
Anton Bannykh
226ffb6c7e JS: write integration test outputs to a file to prevent polluting the log with expected test failures 2017-08-16 13:21:46 +03:00
xiexed
6a4ea8b669 toUElement() made work with KtAnnotationEntry (#1240)
* `KotlinUastLanguagePlugin#convertElement` made work with `KtAnnotationEntry`

* `KotlinUastLanguagePlugin#convertElementWithParent` searches for parent `KotlinUNamedExpression`
2017-08-16 13:01:37 +03:00
Mikhail Glukhikh
a12877e51c Add feature support for "smart casts on variables in closures"
So #KT-14486 Fixed
2017-08-16 12:34:04 +03:00
Mikhail Glukhikh
a086863561 Preliminary: support smart casts on variables in closures
No feature support yet
So #KT-14486 In Progress
2017-08-16 12:33:52 +03:00
Mikhail Glukhikh
b2d931fb1f Support smart casts after if (nullable ?: boolean) #KT-8492 Fixed 2017-08-16 12:33:35 +03:00
Mikhail Glukhikh
9be5cf89b4 Minor fix to ensure correct compilation in 1.2
Related to KT-4565
2017-08-16 12:33:23 +03:00
Mikhail Glukhikh
80b6aaa802 Support smart casts to Type after x as? Type null check #KT-4565 Fixed 2017-08-16 12:33:12 +03:00
Dmitry Jemerov
5bd04a6d22 Fix ultimate tests: add idea-gradle to main project classpath 2017-08-16 11:01:12 +02:00
Alexey Sedunov
787bbe9a4c Safe Delete: Support header/impl declarations
#KT-18433 Fixed
2017-08-15 19:08:29 +03:00
Alexey Sedunov
1215b2864b Safe Delete: Use actual usage PSI in UsageInfo instead of declaration
#KT-19161 Fixed
2017-08-15 19:08:28 +03:00
Alexey Sedunov
2f556e1bea Refactorings: Support header/impl functions in member hierarchy transformations
#KT-18904 Fixed
 #KT-18905 Fixed
2017-08-15 19:08:28 +03:00
Alexey Sedunov
537c1fd063 Convert Function Type Parameter to Receiver: Drop redundant arrows 2017-08-15 19:08:28 +03:00
Alexey Sedunov
f80fcc7146 Parameter <-> Receiver Conversion: Support header/impl declarations
#KT-18907 Fixed
2017-08-15 19:08:27 +03:00
Alexey Sedunov
d3a9d122e6 Add 'operator' Intention: Support header/impl functions
#KT-18851 Fixed
2017-08-15 19:08:27 +03:00
Alexey Sedunov
cd5c382179 Convert member to extension: Support members of header/impl classes
#KT-18883 Fixed
2017-08-15 19:08:27 +03:00
Alexey Sedunov
4dbde03c3b Rename: Support parameters of header/impl functions
#KT-18393 Fixed
2017-08-15 19:08:27 +03:00
Alexey Sedunov
f5c7db8270 Change Signature: Support constructors of header/impl classes 2017-08-15 19:08:26 +03:00
Alexey Sedunov
7f9110b4e6 Change Signature: Fix exception on applying to impl declaration 2017-08-15 19:08:26 +03:00
Alexey Sedunov
0b44386800 Change Signature: Fix NPE on rendering empty parameter names 2017-08-15 19:08:26 +03:00
Alexey Sedunov
8439e15c6e Change Signature: Support members of header/impl classes 2017-08-15 19:08:26 +03:00
Alexey Sedunov
e4f70a3568 Rename: Support members of header/impl classes
#KT-18885 Fixed
 #KT-18898 Fixed
 #KT-18899 Fixed
2017-08-15 19:08:26 +03:00
Alexey Sedunov
62ca3bab31 Move: Do not skip usages of declarations without light elements
#KT-18873 Fixed
2017-08-15 19:08:25 +03:00
Alexey Sedunov
f455f06a9e Change Signature: Fix replacement of implicit Unit return type 2017-08-15 19:08:25 +03:00
Alexey Sedunov
386b1fc002 Line Marking: Fix search of overriding methods in platform modules
#KT-19212 Fixed
2017-08-15 19:08:25 +03:00
Alexey Sedunov
98eb990f30 Line Marking: Place header/impl markers after override/inheritance
#KT-19074 Fixed
2017-08-15 19:08:25 +03:00
Dmitry Jemerov
e3963fccf4 Move Gradle-related classes to idea-gradle module 2017-08-15 16:51:42 +02:00
Yan Zhulanow
57d209f599 Kapt: Do not use awkward ('$' -> '/') logic for KAPT3 class builder mode
So (for the most often reproduction case) #KT-19433 Fixed

Before this commit, internal names for nested classes were written as test/Foo/Bar (comparing to test/Foo$Bar in the normal mode), as getting qualified names from such internal names was trivial. But, because of IC, we needed to write class files to the disk, so our decompiler could find such "broken" classes and read it in a wrong way.
2017-08-15 17:48:51 +03:00
Dmitry Jemerov
e5e5b56af0 Add test for parameter hints on invoke() 2017-08-15 16:37:32 +02:00
Dmitry Jemerov
04464024fe Don't try to resolve call if we won't show any hints anyway 2017-08-15 16:37:21 +02:00
Zalim Bashorov
9bb7ed5e02 Use proper property name to get a tag to publish.
Also:
* remove obsolete kotlin.compiler.* properties
* move --tag argument to proper place (from npm to publish-to-npm)
2017-08-15 17:20:42 +03:00
Dmitry Jemerov
34681b1459 Before searching for descriptor of method, check if it can be property 2017-08-15 11:41:25 +02:00
Dmitry Jemerov
1fe3f84071 Don't search twice for the same declaration 2017-08-15 11:39:40 +02:00
Mikhail Glukhikh
5b72159967 Fix of EA-103829 (do not try to get module info for disposed module) 2017-08-15 11:16:31 +03:00
e5l
e315249624 Add tests on jsr305 annotations warnings 2017-08-15 11:01:08 +03:00
e5l
5501cdf049 Add warnings for jsr305 nullable annotations
#KT-19115 Fixed
2017-08-15 11:01:08 +03:00
e5l
746de612ad Move Jsr305State to util.runtime 2017-08-15 11:01:08 +03:00
e5l
5fd8f93b0e Fix a typo: Defaul -> Default 2017-08-15 11:01:08 +03:00
Sergey Igushkin
71bf649b1e Fix compilation error in AbstractLookupTrackerTest.kt 2017-08-14 19:27:50 +03:00
Sergey Igushkin
bf98e26bc2 Fix nullable javaPackagePrefix used as @Input, resulting in build failure 2017-08-14 18:59:17 +03:00
Mikhail Glukhikh
718ee01a48 Fix of EA-105681 in KotlinProximityStatistician 2017-08-14 17:39:44 +03:00
Mikhail Glukhikh
830b543879 Fix of EA-105681 in KotlinRunLineMarkerContributor 2017-08-14 17:37:05 +03:00
Mikhail Glukhikh
165707c46c Fix of EA-101845 in referenceProviders.kt 2017-08-14 17:36:18 +03:00
Mikhail Glukhikh
88bc74551b Fix of EA-91690 (NPE in OverloadReducer via flexible types) 2017-08-14 17:14:03 +03:00
Sergey Igushkin
7986250dbe Add a test for javaPackagePrefix 2017-08-14 16:13:48 +03:00
Sergey Igushkin
192d569e54 Support Java package prefix in Gradle plugin
Issue #KT-17150 Fixed
2017-08-14 16:13:13 +03:00
Vyacheslav Gerasimov
4cf2bf6ca5 UAST: Implement getFunctionalInterfaceType for KotlinULambdaExpression 2017-08-14 15:41:40 +03:00
Sergey Igushkin
3d6622ae1b Fix ExecutionStrategyJsIT failing due to platform-dependent fileTreeWalk 2017-08-14 15:05:55 +03:00
Alexey Tsvetkov
0226d15d29 Normalize paths in AbstractLookupTrackerTest
Otherwise the tests are failing on Windows
2017-08-11 20:51:06 +03:00
Sergey Igushkin
cd40968b72 Fix tests failing due to dev builds bundled into Gradle. Push AGP to beta. 2017-08-11 20:22:41 +03:00
Sergey Igushkin
6cd409d379 Fix tests assuming '_main' in default module names 2017-08-11 19:56:20 +03:00
Sergey Igushkin
80131d8359 Fix generate stubs task not being assigned a source set name 2017-08-11 13:38:22 +03:00
Nikolay Krasko
4b2b5dec75 Download asm-all sources for idea 172 2017-08-11 12:17:39 +03:00
Nikolay Krasko
f8de17b039 Remove guava usage from KotlinCodegenFacade - fix maven build 2017-08-11 12:17:39 +03:00
Dmitry Petrov
a8c82b64a1 Do not check bounds in type alias expansion if checkBounds is false
This happens when we resolve bounds for type parameters, causing wrong
UPPER_BOUND_VIOLATED to be reported on type parameter whose bounds were
not resolved yet.

 #KT-19601 Fixed Target versions 1.1.5
2017-08-11 11:29:59 +03:00
Denis Zharkov
ce37ab81ba Fix types enhancement for properties' getters overrides in Java
Prior to the 1.1.4, nullability related annotations were stored
in types that became hard to maintain at some moment and
we got rid of it (see 57b7b91444)

But enhancement for properties overrides stopped working
because there were effectively no annotations in the
resulting descriptor

 #KT-19409 Fixed

 #KT-19409 Fixed
2017-08-11 10:19:55 +07:00
Denis Zharkov
9962fc88ca Minor. Move type qualifiers computation to their first usage 2017-08-11 10:19:55 +07:00
Denis Zharkov
8898455352 Add tests on foreign annotations without them in classpath
#KT-19419 Fixed
2017-08-11 10:18:41 +07:00
Denis Zharkov
8948023a26 Add built-in support for ParametersAre(Non)nullByDefault annotation
#KT-19419 In Progress
2017-08-11 10:18:41 +07:00
Denis Zharkov
964f60d0a4 Resolve qualifier nicknames to default annotations without JSR305 jar
#KT-19419 In Progress
2017-08-11 10:18:41 +07:00
Denis Zharkov
f8f0c0b6d7 Load enum/array annotation arguments for not found classes
It's necessary to load type qualifier related annotations
without JSR305 annotations being in the classpath

 #KT-19419 In Progress
2017-08-11 10:18:41 +07:00
Denis Zharkov
a82e313d14 Minor. Fix wrong target in test data for foreign annotations 2017-08-11 10:18:41 +07:00
Nikolay Krasko
6d66fb35d6 Fix AbstractGenerateSpringDependencyActionTest.kt in branch 172 2017-08-10 22:05:49 +03:00
Nikolay Krasko
10bf49118a Update spring test data for 172 idea 2017-08-10 22:05:49 +03:00
Nikolay Krasko
46bbf55acd Special value for class literal expression
Starting from Idea 172 evaluator gives non-null value for class literal
expression. Probably behaviour was changed in

65ddb4c454
2017-08-10 22:05:49 +03:00
Nikolay Krasko
eeede71d9d Drop usage of deprecated ProjectDataManager in branch 172 2017-08-10 22:05:49 +03:00
Nikolay Krasko
2cf4da8564 Fix test behaviour in branch 172 2017-08-10 22:05:49 +03:00
Nikolay Krasko
d8c20ed9c0 Fix debugger test in 172 (KT-18848)
#KT-18848 Fixed
2017-08-10 22:05:49 +03:00
Nikolay Krasko
0d6cf19896 Don't pack jps services into compiler 2017-08-10 22:05:49 +03:00
Nikolay Krasko
c2b54c3e8a Ignore absent net.jpountz.lz4.LZ4Factory in proguard 2017-08-10 22:05:48 +03:00
Vyacheslav Gerasimov
bb7521a142 Build against UAST bundled in IDEA 2017-08-10 22:05:48 +03:00
Alexey Tsvetkov
99439620d4 JPS: completely skip chunk containing only dummy targets
Such chunks were added in intellij-community, see
commit fdeae7754c593e78b6748dfa66ce7198c2780d35
(fdeae7754c)
2017-08-10 22:05:48 +03:00
Mikhael Bogdanov
2954c41848 Fix 'isProjectOrWorkspaceFile' import 2017-08-10 22:05:48 +03:00
xiexed
f94569c995 KotlinCommonIntentionActionsFactory is able to remove constructors parameters (EA-104621) (#1187) 2017-08-10 22:05:48 +03:00
Mikhael Bogdanov
4e868c5232 Update AndroidProjectKey package 2017-08-10 22:05:48 +03:00
Nicolay Mitropolsky
62dc3c8da4 A check for AbstractSpringClassAnnotatorTest that ultimate plugin is properly set up 2017-08-10 22:05:48 +03:00
Nicolay Mitropolsky
384ae8d8b5 Ultimate tests repair (KT-18847)
Repaired all except:
GenerateSpringDependencyActionTestGenerated.testAutowiredDependencies_MultiplePropertiesAnnotationConfig - Not a Kotlin issue
SpringClassAnnotatorTestGenerated.testAutowiredBeanCandidates_AutowiredBeanCandidates - Bug with multiple light objects for same PSI element
SpringInspectionTestGenerated.testAutowiring_inspectionData_Inspections_test - Not a Kotlin issue (presumably IDEA-175971)
SpringQuickFixTestGenerated$AddQualifierAnnotation.testAmbiguousBean - Not a Kotlin issue (IDEA-175971)
2017-08-10 22:05:48 +03:00
Nicolay Mitropolsky
532560ef43 Spring dependency-generations actions: runWriteAction moved to the proper place (KT-18385) 2017-08-10 22:05:48 +03:00
Nicolay Mitropolsky
ca19ea8205 KotlinSpringClassAnnotator ignores duplicate gutter handlers (IDEA-173995, KT-18298) 2017-08-10 22:05:47 +03:00
Nicolay Mitropolsky
ce77751349 Spring Constructor Injection falling test 2017-08-10 22:05:47 +03:00
Nicolay Mitropolsky
6ae247ba61 "Final Kotlin class or function with Spring annotation" inspection deprecation and disabling by default (KT-18506) 2017-08-10 22:05:47 +03:00
Ilya Gorbunov
13349086ac Pass required Project parameter to constructor of NullableNotNullManager 2017-08-10 22:05:47 +03:00
xiexed
a36cbad7cd KotlinCommonIntentionActionsFactory extensions for IDEA-85507 and KT-11906 (#1093)
* `KotlinCommonModifications` renamed to `KotlinCommonIntentionActionsFactory`

* IDEA-85507: KotlinCommonIntentionActionsFactory#createAddMethodAction implementation

* KT-11906 `KotlinCommonIntentionActionsFactory#createAddBeanPropertyActions` implementation

* `KotlinCommonIntentionActionsFactory#createAddMethodAction` now uses a `CallableBuilder` for making a function

* `KotlinCommonIntentionActionsFactory#createAddBeanPropertyActions` privides a "TODO" initializer and also suggests a `lateinit` property

* KT-11980 `KotlinCommonIntentionActionsFactory#createAddConstructorActions` implementation

* `KotlinCommonIntentionActionsFactory` upgraded to new `JvmCommonIntentionActionsFactory`-api

* KT-11980 `KotlinCommonIntentionActionsFactory` is able to change primary constructors

* `JvmCommonIntentionActionsFactory` api update
2017-08-10 22:05:47 +03:00
Mikhail Glukhikh
4a15870e59 Make 172 plugin applicable for IDEA 173 2017-08-10 22:05:47 +03:00
Alexey Andreev
e56f9f6040 Fix compilation for IDEA 172 2017-08-10 22:05:47 +03:00
Mikhail Glukhikh
85ecde6ec9 Correct 172 plugin 'since' field (no more compatible with 171) 2017-08-10 22:05:47 +03:00
Alexey Andreev
4d72f0ef66 Add missing implementation of abstract method to MockPsiManager 2017-08-10 22:05:47 +03:00
Alexey Andreev
11086192bc Fix test compilation errors 2017-08-10 22:05:46 +03:00
Ilya Gorbunov
08673bfb0c Fixup for "JvmCommonIntentionActionsFactory in Kotlin"
'forLanguage' now returns explicitly nullable type.
2017-08-10 22:05:46 +03:00
Nicolay Mitropolsky
0694f2d0c5 JvmCommonIntentionActionsFactory in Kotlin 2017-08-10 22:05:46 +03:00
Dmitry Jemerov
548e86285c Fix 'ant dist' build against 172 branch 2017-08-10 22:05:46 +03:00
Dmitry Jemerov
20d0d49cc3 Advance Guava version 2017-08-10 22:05:46 +03:00
Dmitry Jemerov
48d4f5f5c2 Compilation fixes for 172 branch 2017-08-10 22:05:46 +03:00
Vyacheslav Gerasimov
c1cfd70ae7 Fix tests compilation 2017-08-10 22:05:46 +03:00
Vyacheslav Gerasimov
b825a8db43 Fix compilation AndroidResourceReferenceAnnotator 2017-08-10 22:05:46 +03:00
Vyacheslav Gerasimov
23e606d179 Fix compilation MockUpdateParameterInfoContext 2017-08-10 22:05:46 +03:00
Vyacheslav Gerasimov
cf4d0fb977 Fix guava version 2017-08-10 22:05:45 +03:00
Vyacheslav Gerasimov
83a8395287 Fix compilation AbstractKotlinEvaluateExpressionTest 2017-08-10 22:05:45 +03:00
Dmitry Jemerov
282da4cab5 Move Kotlin UAST registration to main plugin.xml
The UAST needs to be available also when the Android plugin is disabled.
2017-08-10 22:05:45 +03:00
Vyacheslav Gerasimov
298d29a962 Android Extensions: Allow to disable IDE support (KT-12741) 2017-08-10 22:05:45 +03:00
Dmitry Jemerov
62e583903e Fix compilation gotoResourceHelper, KotlinAndroidTestCase 2017-08-10 22:05:45 +03:00
Mikhail Glukhikh
c675824c0a Fix compilation PlatformAndroidGradleDetector 2017-08-10 22:05:45 +03:00
Yan Zhulanow
6336c4ee98 Fix compilation androidUtil, MyReferredResourceFieldInfo requires module 2017-08-10 22:05:45 +03:00
Dmitry Jemerov
be1022db2b Fix compilation NewKotlinActivityAction, gradle sync classes moved 2017-08-10 22:05:45 +03:00
Yan Zhulanow
a142c2f8fa Fix compilation IntelliJLintClient, IntelliJLintProject, IDEAndroidLayoutXmlFileManager 2017-08-10 22:05:45 +03:00
Vyacheslav Gerasimov
c07096c9d7 Fix compilation AbstractParameterInfoTest 2017-08-10 22:05:45 +03:00
Vyacheslav Gerasimov
768305adc8 Fix compilation KotlinModuleBuilder 2017-08-10 22:05:44 +03:00
Vyacheslav Gerasimov
e8d2782089 Bump guava to 21.0 in update_dependencies.xml 2017-08-10 22:05:44 +03:00
Dmitry Jemerov
b50d5fb998 Download IDEA from 172 branch 2017-08-10 22:05:44 +03:00
Dmitry Jemerov
7fffb7b553 Remove UAST services registration from Kotlin plugin 2017-08-10 22:05:44 +03:00
Sergey Igushkin
b938206234 Add @Input to moduleName, to incorporate it into the up-to-date checks 2017-08-10 21:23:07 +03:00
Sergey Igushkin
84e1e9f8aa Change default module name from project.name to archivesBaseName;
Get rid of `_main` for the main module.

Issue #KT-17355 Fixed
2017-08-10 21:23:07 +03:00
Alexey Tsvetkov
239943867b Add JS specific proto comparison test 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
0d3b882852 Add proto comparison tests where members annotations are changed 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
6354d9d54f Treat SEALED_SUBCLASS_FQ_NAME_LIST change as a class signature change
#KT-19580
2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
856276328e Treat JS class annotation list change as class signature change 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
e0ef08cf18 Add raw ProtoCompareGenerated output to proto comparison test data 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
642c5414a3 Minor: rename js.result.out->result-js.out
This way result.out and result-js.out are closer in
a list of files (e.g. in Intellij project view).
2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
46a3a59b81 Fix missing lookups from deserialized JS descriptors 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
7e7fcd352c Compare lookups after comparing build logs
This way tests are more informative when
compilation goes wrong.
2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
82c977f2d2 Add JS lookup tracker tests 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
6cfd090b20 Extract JVM lookup tracker tests 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
e2190ea956 Use lookup tracker in JS compiler 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
f3f7ca4b95 Show in lookup tracker log if there is no lookups in file 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
ab90221a93 Minor: reformat AbstractLookupTrackerTest#runCompiler 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
485e2345a9 Decouple lookup tracker tests from JPS 2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
bb2fab5b5d Extract LookupTracker service from IncrementalCompilationComponents
We don't need a `TargetId` to `IncrementalCache` mapping in JS
2017-08-10 21:19:42 +03:00
Alexey Tsvetkov
a4c7dbd693 Remove .touch actions for lookup test cases that fail to compile
It is useless to touch and recompile, because the first compilation
has failed anyway
2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
61b3c1c429 Do not print NONE changes in proto tests
otherwise MainKt: NONE is added in all js tests
2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
c601890151 Fix comparing repeated proto extensions
Previously ProtoCompareGenerated could
go out of bounds when comparing protos
with different number of annotations.

That happend because JsProtoBuf.parameterAnnotation
is a repeated extension, but the generated code for
comparing repeated extensions was incorrect.

JvmProtoBuf does not have repeated extensions (at least for
the class and package descriptors),
so the problem was not detected before.
2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
1cce1ef1f6 Isolate JS compiler in proto tests
Proto tests are still in the 'jps-tests' module
which is included in non-compiler tests.

It is not safe to call the compiler
directly in non-compiler tests
because it might affect IDE tests.
2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
ed5b6e07aa Implement JS proto comparison 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
23afaeec2f Extract TestMessageCollector 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
f5e77c740d Introduce services to pass data between IC and JS compiler 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
8ffd141d17 Minor tweak to proto test data format 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
1921950a1b Extract JVM specific proto comparison test 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
cc24b9f4ad Always print class id in proto comparison test
A name of class file was used for added and removed classes
before the change.
The change is required for reusing the test data in js proto comparison
tests (there is no classfiles in js, so it is hard to
emulate jvm classfiles names for inner/nested classes).
2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
5dd4e4cdd4 Move JVM specific proto comparison tests to separate dir 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
9ab7c92b4b Convert SimpleOutputItem: step 2 2017-08-10 21:19:41 +03:00
Alexey Tsvetkov
8fbab94c5c Convert SimpleOutputItem: step 1 2017-08-10 21:19:41 +03:00
Mikhael Bogdanov
6ca06265cf Rename and disable test on JS 2017-08-10 16:16:28 +02:00
Nikolay Krasko
a41e5fff6b Regenerate ultimate tests - update copyright 2017-08-10 15:58:15 +03:00
Dmitry Petrov
674d30cd76 Report deprecation on typealias companion object for deprecated alias 2017-08-10 15:45:44 +03:00
Dmitry Petrov
c180de563f Support DslMarker on type aliases 2017-08-10 15:45:44 +03:00
Nikolay Krasko
223acbcfeb Clear static application in GenericReplTest 2017-08-10 15:43:54 +03:00
Nikolay Krasko
e35b262827 Clear application in CompilerApiTest 2017-08-10 15:43:54 +03:00
Nikolay Krasko
4e190248cd Add resetApplicationToNull utility with old application 2017-08-10 15:43:54 +03:00
Mikhael Bogdanov
3fd6dd3572 Add test for quoted class name 2017-08-10 12:10:25 +02:00
Dmitry Jemerov
022430cb59 Set correct library kind for transitive dependencies 2017-08-10 11:43:35 +02:00
Mikhail Zarechenskiy
974dad571c [NI] Report errors about inapplicable wrong receiver
Now it's possible because we don't commit trace with inapplicable `provideDelegate` operator (20e105c274)
2017-08-09 17:37:44 +03:00
Vyacheslav Gerasimov
2ac7b6a534 UAST: Fix DeclarationDescriptor.toSource return first found source element
instead of null, when multiple descriptors found

 #KT-18837 Fixed
2017-08-09 15:34:41 +03:00
Vyacheslav Gerasimov
915f47133b UAST: Fix KotlinUMethod annotation handling, properly handle use site targets
#KT-16834 Fixed
 #KT-18893 Fixed
2017-08-09 15:34:34 +03:00
Vyacheslav Gerasimov
f24488915a UAST: Log error when failed to create light class for UObjectLiteralExpression 2017-08-09 15:34:27 +03:00
Vyacheslav Gerasimov
adfc481c7a Add ProjectImportProvider for *.gradle.kts file to import it as module
#KT-19466 Fixed
2017-08-09 15:34:19 +03:00
Vyacheslav Gerasimov
4405021f85 Add ProjectOpenProcessor for *.gradle.kts file to open it as project
#KT-19024 Fixed
2017-08-09 15:34:11 +03:00
Dmitry Jemerov
73a4da6c56 Cache list of dependent modules in modification tracker 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
a7bbf3d1f8 Don't increase OOCB count when a REPL line is modified 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
3415853cac Add ModuleDescriptor.assertValid() for ensuring consistency 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
ac96c31a7d Retrieve module descriptors for implementing modules on demand 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
0b45d25bb1 Fix compilation after rebase 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
bdbe134b60 Recreate module descriptors for affected modules only on a change 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
07794c8188 On-demand creation of ModuleDescriptors 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
dde1f4b8f3 Fix OOCB updates for code fragments 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
36cabf1bfc Move entire logic for ModuleDescriptor setup into ResolverForProjectImpl 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
d6a9a49968 Disable tracking of Kotlin files by Java OOCB listener 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
aafe7e6f1b Refactoring: move createResolverForModule() into ResolverForProjectImpl 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
fcc067435e Refactoring: streamline module resolver setup code 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
194deccd09 Remove one level of indirection from ModuleResolverProvider creation 2017-08-09 13:26:09 +02:00
Dmitry Jemerov
3debca09ea Remove callback hell from LazyModuleDependencies 2017-08-09 13:26:09 +02:00
Mikhail Zarechenskiy
cfbc559a97 [NI] Propagate tracking binding trace into context 2017-08-09 14:01:04 +03:00
Mikhail Zarechenskiy
4a74ca568c [NI] Don't forget to deparenthesize expression before type checking 2017-08-09 14:01:00 +03:00
Mikhail Zarechenskiy
053b02e0df [NI] Fold { Lower | Upper } & Equality constraints if it's possible 2017-08-09 14:00:53 +03:00
Mikhail Zarechenskiy
20e105c274 Don't commit trace with inapplicable provideDelegate operator
This helps in NI as there we have different logic for delegates inference
2017-08-09 13:50:50 +03:00
Mikhael Bogdanov
82c3637d91 Wide visibility in ir common stuff 2017-08-09 12:07:38 +02:00
Mikhail Zarechenskiy
46d0ea3eed Use operation reference as lookup element to preserve old behaviour
See related changes in fb72726f08
2017-08-09 00:59:12 +03:00
Alexey Sedunov
cf3615d279 Kotlin Facet: Fix element ordering in compiler arguments XML
Do not rely on method list as it's ordered differently
2017-08-09 00:03:28 +03:00
Valentin Kipyatkov
e52c3b4c81 Rewritten KDoc-link resolve and completion to work more reasonably 2017-08-08 22:06:04 +03:00
Valentin Kipyatkov
998814b1a1 Support for import aliases in both resolve and completion in KDoc 2017-08-08 22:06:04 +03:00
Valentin Kipyatkov
9361cd895c Support for import aliases in code completion
#KT-8848 Fixed
2017-08-08 22:06:04 +03:00
Mikhail Zarechenskiy
48246e5f34 [NI] Add resolution part to check for abstract super call 2017-08-08 15:44:31 +03:00
Mikhail Zarechenskiy
b6e195128c [NI] Resolution diagnostics don't produce errors as is 2017-08-08 15:44:30 +03:00
Mikhail Zarechenskiy
5486f4e612 [NI] Don't report NI error for recorded info about smartcasts 2017-08-08 15:44:28 +03:00
Mikhail Zarechenskiy
64b722d4f6 Minor, reduce nesting 2017-08-08 15:44:20 +03:00
Nikolay Krasko
9c37d0a007 Disable building dependencies caches in configure GSK tests 2017-08-08 15:26:16 +03:00
Nikolay Krasko
60e330b6f3 Update configure tests after binding comments and spaces to script body 2017-08-08 15:26:16 +03:00
Denis Zharkov
ff0736f09e Fix exception after combination of while (true) + stack-spilling
FixStack transformation divides on phases:
- Fixing stack before break/continue
- Fixing stack for inline markers/try-catch blocks

After the first stage all ALWAYS_TRUE markers are replaced
with simple GOTO's and if we're skipping break/continue edges
we won't reach the code after while (true) statement.

At the same time it's fine to not to skip them in the second phase
as the stack for them is already corrected in the first phase

 #KT-19475 Fixed
2017-08-08 18:52:21 +07:00
Denis Zharkov
45d5f6a950 Add test for obsolete issue
#KT-19467 Obsolete
2017-08-08 18:52:21 +07:00
Mikhael Bogdanov
3ae084b1b3 Get rid of reification from 'deepCopyWithVariables' 2017-08-08 13:33:20 +02:00
Mikhael Bogdanov
49612063dc Wide visibility in ir common stuff 2017-08-08 13:25:49 +02:00
Mikhael Bogdanov
07c5702861 Add missed 'version' in core modules facets 2017-08-08 13:09:48 +02:00
Mikhael Bogdanov
6e4b02a94b Disable 'areEqualByValue' 2017-08-08 13:09:48 +02:00
Mikhael Bogdanov
6305abdf9f Wide visibility in ir common stuff 2017-08-08 13:09:47 +02:00
Valentin Kipyatkov
ca418c727e KT-19278 Optimize imports on the fly should not remove incomplete import while it's being typed
#KT-19278 Fixed
2017-08-08 12:27:16 +03:00
Valentin Kipyatkov
8a17e6c1c9 WIP 2017-08-08 12:27:15 +03:00
Valentin Kipyatkov
e53b1a1e92 KT-19277 Optimize imports on the fly should not work in test data files
#KT-19277 Fixed
2017-08-08 12:27:15 +03:00
Mikhail Glukhikh
5904b7f257 Remove ModalityState.any() from J2kPostProcessor #KT-19453 Fixed 2017-08-08 11:33:32 +03:00
Mikhael Bogdanov
15f401a473 Copy annotation and attributes on class transformation during inline 2017-08-08 09:50:42 +02:00
Mikhael Bogdanov
11ba805181 Convert MethodBodyVisitor to Kotlin 2017-08-08 09:50:41 +02:00
Mikhael Bogdanov
5ecdf2af9e Rename MethodBodyVisitor.java to MethodBodyVisitor.kt 2017-08-08 09:50:41 +02:00
Mikhael Bogdanov
fca1500d48 Clean code 2017-08-08 09:50:40 +02:00
Mikhail Zarechenskiy
e2dcf47b3b Fix highlighting range of diagnostic in test data
Because of ae3497c6ce
2017-08-08 00:29:18 +03:00
Sergey Igushkin
52f923c5ff Fix internals of an android-library not accessible in its androidTest
Issue #KT-19370 Fixed
2017-08-07 20:33:18 +03:00
Mikhail Zarechenskiy
ae3497c6ce Reduce highlighting range for UNCHECKED_CAST
#KT-18985 Fixed
2017-08-07 18:49:58 +03:00
Mikhail Zarechenskiy
8f8143d3ed Fix IAE for wrong use-site @file annotation
#EA-100189 Fixed
2017-08-07 18:49:57 +03:00
Mikhail Zarechenskiy
4d4c39939f Report full package FQ name in compilation errors related to visibility
#KT-18966 Fixed
2017-08-07 18:49:55 +03:00
Mikhail Zarechenskiy
216ab1c6d1 Fix error message for inapplicable operator on getValue function
#KT-11739 Fixed
2017-08-07 18:49:52 +03:00
Mikhail Zarechenskiy
7ba073206d Add test for obsolete issue about SAMs
#KT-11951 Obsolete
2017-08-07 18:36:07 +03:00
Mikhail Zarechenskiy
7693f64dee [NI] Take into account safe call when updating recorded type 2017-08-07 18:01:21 +03:00
Mikhail Zarechenskiy
9e018fa094 [NI] Try to analyze each lambda at least once 2017-08-07 18:01:20 +03:00
Mikhail Zarechenskiy
07a4496054 [NI] Resolve lambda even if there is contradiction in CS
To avoid exceptions about non-recorded lambda
2017-08-07 18:01:19 +03:00
Mikhail Zarechenskiy
a13442b12b [NI] Fix data flow for arguments in special calls 2017-08-07 18:01:18 +03:00
Mikhail Zarechenskiy
dc83e5ca3a Fix test which is correctly work in old inference 2017-08-07 18:01:17 +03:00
Mikhail Zarechenskiy
3fb865e07c Move test for NI to diagnostic tests and add "todo" 2017-08-07 18:01:16 +03:00
Mikhail Zarechenskiy
fb72726f08 Resolve right part of equality with given descriptors 2017-08-07 18:01:15 +03:00
Stanislav Erokhin
6680f01cfe [NI] Fix assertion error at FlexibleTypeImpl
Use KotlinTypeFactory for FlexibleType creation
2017-08-07 18:01:14 +03:00
Mikhail Zarechenskiy
e7cd615450 [NI] Introduce type depth in CS calculator to avoid SOE 2017-08-07 18:01:13 +03:00
Mikhail Zarechenskiy
cf75afba66 [NI] Fix type intersection for equal types 2017-08-07 18:01:12 +03:00
Mikhail Zarechenskiy
ac507e721c [NI] Do not add non-dynamic candidates when there is dynamic extension 2017-08-07 18:01:11 +03:00
Mikhail Zarechenskiy
21c5187c9e [NI] Handle dynamic types in type intersector 2017-08-07 18:01:10 +03:00
Mikhail Zarechenskiy
0d464f06d1 [NI] Consider CS as nullable if one of the types isn't subtype of Any
Note that this isn't fully correct, consider the following situation:

S : T, T : Any?
=> CS(S, T) = T, but for now it will be T?, which is reliable but not so specific as just T
2017-08-07 18:01:09 +03:00
Mikhail Zarechenskiy
39349abd39 [NI] Preserve name of parameters for functional types 2017-08-07 18:01:07 +03:00
Mikhail Zarechenskiy
5ec8d4920f [NI] Translate new resolved call to old one to avoid CCE 2017-08-07 18:01:06 +03:00
Dmitry Petrov
c0d6eff97c [NI] Select variable with proper non-trivial constraint first 2017-08-07 18:01:05 +03:00
Dmitry Petrov
0bf81aeec0 [NI] Extract InferenceStepResolver into a separate component 2017-08-07 18:01:04 +03:00
Dmitry Petrov
258a5aea28 [NI] Minor cleanup in FixationOrderCalculator 2017-08-07 18:01:03 +03:00
Stanislav Erokhin
ab2f99542a [NI] Redo how we take care of postpone arguments
The main change here is the following: before callable reference
resolution starts directly after choosing candidate. Since now we
start resolution before call completion.
2017-08-07 18:01:02 +03:00
Stanislav Erokhin
b344865c15 [NI] Minor. Fixes after review 2017-08-07 18:01:01 +03:00
Stanislav Erokhin
93d80c252f [NI] Refactoring. Move properties from KotlinCall to external component 2017-08-07 18:01:00 +03:00
Stanislav Erokhin
ef93088a42 [NI] Move most of KotlinCallDiagnostic to one file
Now there is 3 kind of KotlinCallDiagnostic:
  - ResolutionDiagnostic
  - ConstraintSystemCallDiagnostic
  - other common diagnostic

Also SpecialResolutionParts were merged into other ResolutionParts
2017-08-07 18:00:59 +03:00
Stanislav Erokhin
9378bff65c [NI] Move irrelevant code from KotlinCallCompleter
Extract code about smart cast diagnostic to new component
AdditionalDiagnosticReporter
2017-08-07 18:00:58 +03:00
Stanislav Erokhin
3450340d7f [NI] Refactoring. Introduced PostponableCallArgument
Also here argument resolution was divided to two parts:
for SimpleCallArguments and for PostponableCallArguments.
Call Resolution for SimpleCallArguments also used for CheckReceivers
and lambda result arguments checks
2017-08-07 18:00:57 +03:00
Stanislav Erokhin
1bc68e073d [NI] Minor. Clarified type for arguments from lambda 2017-08-07 18:00:56 +03:00
Stanislav Erokhin
4848f8e3da [NI] Use correct type in TypeApproximator for Invariant projection 2017-08-07 18:00:56 +03:00
Stanislav Erokhin
85e34163bb [NI] Temporary fix for cases related callable reference and if
For cases like if (..) ::foo else ::bar we didn't write stub resolved
calls for ::foo before call completion. Because of this, and strange
code in if we get null inside type info.
2017-08-07 18:00:54 +03:00
Stanislav Erokhin
455c43afa8 [NI] Some improvements in callable reference resolution 2017-08-07 18:00:53 +03:00
Stanislav Erokhin
f1144c9f01 [NI] Use resolved lhsType as unbound receiver. 2017-08-07 18:00:53 +03:00
Stanislav Erokhin
c752e1580e [NI] Check receivers for callable reference resolution. 2017-08-07 18:00:52 +03:00
Stanislav Erokhin
a5dffafacd [NI] Fix provideDelegate resolution.
For provideDelegate there is no real psi for resolution,
so we write corresponding call via special trace key.
2017-08-07 18:00:51 +03:00
Mikhail Zarechenskiy
7802492b08 [NI] Fix resulting type when there are no proper constraints 2017-08-07 18:00:50 +03:00
Mikhail Zarechenskiy
6be726854f [NI] Preserve type abbreviation during type substitution 2017-08-07 18:00:49 +03:00
Mikhail Zarechenskiy
76d013a33f [NI] Resolve % to mod if candidates have wrong receivers 2017-08-07 18:00:48 +03:00
Dmitry Petrov
4963580f90 [NI] Take into account return without expression in lambdas 2017-08-07 18:00:47 +03:00
Mikhail Zarechenskiy
17cdbcca03 [NI] Approximate substituted type arguments for non-members 2017-08-07 18:00:46 +03:00
Stanislav Erokhin
915ac32bfb [NI] Improve type inference for T vs Captured(in Smt)
If we has Inv<T> <: Inv<Captured(in Foo)> then we should get:
- T <: Captured(in Foo)
- Captured(in Foo) <: T

Before this commit we got: T <: Foo instead first constraint.
2017-08-07 18:00:45 +03:00
Stanislav Erokhin
91241a34d1 [NI] Run checks for captured types only once in NewTypeSubstitutor
Sometimes we can get Enum<Captured(*)> type here, so, supertype for
Captured(*) is Enum<Capture(*)> and we go into SO.
2017-08-07 18:00:44 +03:00
Stanislav Erokhin
d58c6e245f Minor. rename type parameters for debug purposes. 2017-08-07 18:00:43 +03:00
Mikhail Zarechenskiy
e74a02eb94 [NI] Approximate implicit return type for functions 2017-08-07 18:00:42 +03:00
Mikhail Zarechenskiy
ffc130f5fb [NI] Always approximate captured types for property descriptors 2017-08-07 18:00:41 +03:00
Stanislav Erokhin
5f2cc75718 [NI] Support INAPPLICABLE_WRONG_RECEIVER candidate applicability
It is important for provideDelegate resolution, because if scope has
provideDelegate with wrong receiver we shouldn't resolve to it and
report any errors.
2017-08-07 18:00:40 +03:00
Stanislav Erokhin
e4b73fcdbd [NI] Create SubCallArgument for variable in VariableAsFunctionCall
If variable is generic call, then we should complete inference only
after invoke resolution. It means that explicit receiver for invoke
should be SubKotlinCallArgument.
But, if this property has no generics,
for example local property, then this property can have smartcast and
such call has no type arguments -> no completion required.
For such call we should store information about smart casts.
2017-08-07 18:00:39 +03:00
Dmitry Petrov
756f7d6e9c [NI] Fix tests (was a type checker bug, see KT-18380) 2017-08-07 18:00:38 +03:00
Dmitry Petrov
d4e8a30dcf [NI] Fix nullability for captured type in input types approximation 2017-08-07 18:00:37 +03:00
Dmitry Petrov
e5c87fdad7 [NI] Filter out duplicates types in commonSuperTypeForNotNullTypes 2017-08-07 18:00:36 +03:00
Dmitry Petrov
b336919db3 [NI] In NI mode, use return type from special call resolution for '!!' 2017-08-07 18:00:35 +03:00
Dmitry Petrov
397e04f382 [NI] Do not use return type from 'onlyResolvedCall' 2017-08-07 18:00:34 +03:00
Dmitry Petrov
5b2e66f0ca [NI] Invoke checkType for arguments
checkType performs various actions required by BE
(e.g., record nullability assertions information for JVM BE).
2017-08-07 18:00:33 +03:00
Dmitry Petrov
dc453e6d8b [NI] Update lambda argument expression type when return type is known 2017-08-07 18:00:32 +03:00
Dmitry Petrov
ba068c2d65 Use original descriptor for enum constructor symbol 2017-08-07 18:00:31 +03:00
Mikhail Zarechenskiy
def0816095 [NI] Write info about hidden descriptor to candidate 2017-08-07 18:00:30 +03:00
Mikhail Zarechenskiy
38d9123a57 [NI] Use weaker upper constraint for case {T & Any} <: S 2017-08-07 18:00:29 +03:00
Stanislav Erokhin
18961cc5a9 [NI] Analyze lambda in independent context if it isn't call argument 2017-08-07 18:00:28 +03:00
Dmitry Petrov
8599763cb9 Do not perform type checks for function literals in visitor in NI mode
They are type-checked as arguments for the corresponding expressions.
2017-08-07 18:00:27 +03:00
Dmitry Petrov
fbad16567b [NI] Fix number type adjustment for greatest lower bound calculation
Compute common supertype (regardless of whether the given set of
lower bounds contains number types, intersection types, or whatever).

If the result type S is a possibly nullable intersection X1 & ... & Xn,
N = {Xi | Xi is a primitive number type},
R = {Xi | Xi is not a primitive number type},
M = default primitive number type for {Nj},
then adjusted type T* = M & R1 & ... Rm with the same nullability as S.

NB: IntegerValueType(_) = Int & Byte & Short & Long
2017-08-07 18:00:26 +03:00
Dmitry Petrov
1ae4278cfd Minor: fix formatting 2017-08-07 18:00:25 +03:00
Mikhail Zarechenskiy
bc2a8555a3 [NI] Resolve collection literals arguments as postponed ones 2017-08-07 18:00:24 +03:00
Stanislav Erokhin
c0c94910e2 [NI] Fix StackOverflow in TypeApproximator
For cases like Enum<Captured(*)> where Captured(*) has supertype
Enum<Captured(*)> we get SO in TypeApproximator.
To prevent this argument depth was introduced.
2017-08-07 18:00:23 +03:00
Dmitry Petrov
9fa3bce73a [NI] Fix special case of captured type handling in subtyping
Given the subtyping constraint
  X <: CapturedType(in Y)
we should check only
  X <: Y
if X contains type variables.
2017-08-07 18:00:22 +03:00
Dmitry Petrov
26cc08be65 Fix anonymous function literals handling in type checker
- [NI] Create type info directly if the expected type is functional.
- Properly handle suspended function expected type.
2017-08-07 18:00:21 +03:00
Dmitry Petrov
6facdcb7ea Minor: lambda arguments formatting 2017-08-07 18:00:20 +03:00
Mikhail Zarechenskiy
badbf777df [NI] Use data flow info from arguments in parenthesis to resolve lambda
Fixes 'javaObjectType' and 'javaPrimitiveType'
2017-08-07 18:00:19 +03:00
Stanislav Erokhin
5eb56dca60 [NI] Check type compatibility before fixation.
If for type variable we have upper and lower bounds, then sometimes
our approximation before fixation give us incorrect result for type
variable and we should chose other bound as result.

Example: Int & Byte <: T <: Byte. If we run approximation for lower
bound we get Int as result and it isn't subtype of Byte.
2017-08-07 18:00:18 +03:00
Mikhail Zarechenskiy
d1263c5dc3 [NI] Coerce to unit for empty lambda block
Fixes 'kt3903'
2017-08-07 18:00:17 +03:00
Mikhail Zarechenskiy
cf55674109 [NI] Support fallback resolve to operator mod if needed
Fixes:
  - assignmentOperations
  - percentAsModOnBigIntegerWithoutRem
2017-08-07 18:00:16 +03:00
Dmitry Petrov
f578d07b00 [NI] Fix lambda return type when expected type is not functional type
Introduce a fresh type variable for lambda return type.

We can't set expected lambda return type to 'Any?', because we can't
infer the actual type from return expressions in lambda in that case.
2017-08-07 18:00:15 +03:00
Dmitry Petrov
f637ebe9ff Minor: formatting for lambda arguments 2017-08-07 18:00:14 +03:00
Stanislav Erokhin
b7c894a6d3 [NI] Capture types from smart-cast types.
Sometimes we have something like if (a is Foo<*>) a.bar()
where bar declared: fun <T> Foo<T>.bar().
For such case we should create receiver with possible types Capture(*).
2017-08-07 18:00:13 +03:00
Mikhail Zarechenskiy
b6bb171b67 [NI] Extension function wins member if it's infix call
Fixes 'infixFunctionOverBuiltinMember'
2017-08-07 18:00:12 +03:00
Mikhail Zarechenskiy
8670d2abba [NI] Propagate information about safe call to receiver argument 2017-08-07 18:00:11 +03:00
Mikhail Zarechenskiy
72d14bfe0d [NI] Record type of callable reference to trace 2017-08-07 18:00:10 +03:00
Dmitry Petrov
a303888e66 [NI] Fix expected return type for function literals
It should actually be Unit, as told in FunctionExpression comments
(was null, later defaulted to Any?).
2017-08-07 18:00:09 +03:00
Dmitry Petrov
0136be3500 [NI] Fix traversing delegated constructor call chain
Use original descriptor instead of possibly substituted one: even though
the substitution is always trivial here, delegated constructor call is
recorded for the original constructor descriptor. So the code that
traverses the delegated constructor call chain should use original
descriptor, too.
2017-08-07 18:00:08 +03:00
Mikhail Zarechenskiy
0634025229 [NI] Propagate known type substitutor to resolution part
This commit fixes 'functionNtoStringGeneric' and 'superConstructor'
2017-08-07 18:00:07 +03:00
Mikhail Zarechenskiy
c6fcbf6172 [NI] Check for unwrapped descriptor when generating accessible function
In new inference we get copy of sam constructor and therefore should check original descriptor in BE.

 This fixes 'protectedSamConstructor' test
2017-08-07 18:00:06 +03:00
Stanislav Erokhin
e12eb66572 [NI] Fix COERCION_TO_UNIT in NI. 2017-08-07 18:00:05 +03:00
Stanislav Erokhin
de17604fe7 [NI] Bind all new resolved calls before update arguments. 2017-08-07 18:00:04 +03:00
Stanislav Erokhin
42438bd363 [NI] Do not calculate lambda return type in Visitor if NI enabled. 2017-08-07 18:00:03 +03:00
Stanislav Erokhin
85248676d2 [NI] Update lambda result arguments after resolution. 2017-08-07 18:00:02 +03:00
Stanislav Erokhin
b9e9243e9d [NI] Add hacks for property delegation resolution. 2017-08-07 18:00:00 +03:00
Stanislav Erokhin
af138e7403 Minor. Extract object to inner class. 2017-08-07 17:59:59 +03:00
Stanislav Erokhin
5bb61d2d02 [NI] Small improvements in callable reference resolution.
I'm not sure in this commit, but it fix some test -> let it be for now.
And yes, now I do not know correct way for callable reference resolution,
so for now it is just proposals.
2017-08-07 17:59:58 +03:00
Stanislav Erokhin
7eabdeffb3 [NI] Fix variable to proper upper type even if direction is TO_SUBTYPE. 2017-08-07 17:59:57 +03:00
Stanislav Erokhin
b3be21146c [NI] Add more hacks. 2017-08-07 17:59:56 +03:00
Stanislav Erokhin
0f0d834c23 [NI] Minor. Fix IOE. 2017-08-07 17:59:55 +03:00
Stanislav Erokhin
55181541af [NI] Change lambda analysis -- create arguments for return statements. 2017-08-07 17:59:54 +03:00
Stanislav Erokhin
58f73bd82a [NI] Use right DFI for arguments smart-casts. 2017-08-07 17:59:53 +03:00
Stanislav Erokhin
30f7396803 [NI] Substitute lambda return type with current substitutor
We should do this because return type even it still not proper
can contain fixed type variables
2017-08-07 17:59:52 +03:00
Stanislav Erokhin
89ac3bd5cf [NI] Do not add useless constraints to constraint system
Skipped constraints:
 - T <: Any, T >: Nothing
 - T <: T, T <: T?, T >: T, T <: T!, T! <: T
2017-08-07 17:59:51 +03:00
Stanislav Erokhin
3a25405088 [NI] Remove type variables for lambda arguments -- use existing instead. 2017-08-07 17:59:50 +03:00
Stanislav Erokhin
ff6a28b64c Add util method to BuildIns is kotlin.Function type. 2017-08-07 17:59:49 +03:00
Stanislav Erokhin
acc6e48172 [NI] Added isSuspend for lambdas. 2017-08-07 17:59:48 +03:00
Stanislav Erokhin
29e2a26ad6 [NI] Write fake ResolvedCall for callable reference. 2017-08-07 17:59:47 +03:00
Stanislav Erokhin
ee16a79612 [NI] Add pre-resolution callable reference argument check.
If expected type for callable reference argument isn't callable type
then make such candidate unsuccessful.
Sometimes expected type is just `T`, where `T` is type variable.
To support such case we take all supertypes and check them instead.
2017-08-07 17:59:46 +03:00
Stanislav Erokhin
55dc2c11f7 [NI] Support callable reference resolution in NI.
Missing parts:
- report results about callable references into trace
2017-08-07 17:59:46 +03:00
Stanislav Erokhin
02f4558683 Add way to create callable reference processor
Priority of variables and function should be the same.
Because of this we create new CompositeSimpleScopeTowerProcessor,
which merge candidates for properties and function into one candidate group
2017-08-07 17:59:44 +03:00
Stanislav Erokhin
36ea9484a9 [NI] Minor. Extract code to function.
Also make KotlinCall unnecessary for TypeVariableFromCallableDescriptor.
2017-08-07 17:59:43 +03:00
Mikhail Zarechenskiy
0b358fb693 Fix collection literals resolve in gradle-based projects
#KT-19441 Fixed
2017-08-07 17:52:08 +03:00
Daniil Vodopian
b24c1bf06c KT-9669: introduced JoinStatementAddSemicolonHandler; registered the handler in plugin.xml; added test coverage (#1232) 2017-08-07 16:20:40 +02:00
Dimach
d624ed4aff KT-18482: "Move lambda argument to parenthesis" action generate uncompilable code fixed (#1226)
* KT-18482 fixed

* Moved code to separate method and changed code to cover few more cases.

* Code style fixes.
2017-08-07 15:43:44 +02:00
Alexey Andreev
a4551fb0fb Fix infinite loop during continuous Gradle build including JS DCE
It's basically a workaround fox bug in Gradle.
See https://github.com/gradle/gradle/issues/2651
2017-08-07 16:36:57 +03:00
Sergey Igushkin
71878b2218 Merge pull request #1225 from nageshs/master
Close the local.properties file after reading
Issue #KT-19397 Fixed
2017-08-07 16:07:51 +03:00
Sergey Igushkin
13a2de1816 Update libraries/ReadMe.MD, add info about plugin markers required for tests 2017-08-07 15:14:37 +03:00
Sergey Igushkin
0cfac71efe (minor) Improve readability of pluginMarkers.gradle, fix indent in file
(minor) Clarify the comment on the setUpSeparateArtifact block
2017-08-07 14:33:35 +03:00
Sergey Igushkin
94036b7cac Add Gradle license 2017-08-07 14:33:33 +03:00
Sergey Igushkin
999db0bc80 Add a test for plugins DSL 2017-08-07 14:32:41 +03:00
Sergey Igushkin
8fd508566a Add Gradle plugin marker artifacts for the Gradle plugins.
This allows for the Gradle plugins DSL to resolve the plugins from
a custom repository.
https://docs.gradle.org/current/userguide/plugins.html#sec:plugin_markers
2017-08-07 14:17:43 +03:00
Toshiaki Kameyama
64eeb479aa Take nullability annotations into account in QF correcting override
So Java NotNull annotated is converted to `Type`
and Java Nullable annotated to `Type?` accordingly

So #KT-19299 Fixed
2017-08-07 13:52:25 +03:00
Mikhail Glukhikh
1264ed7c86 Minor cleanup 2017-08-07 13:20:35 +03:00
Andrius Semionovas
666c241479 KT-19126 Add convert property initializer to getter in interfaces (#1224) 2017-08-07 11:53:37 +02:00
Kirill Rakhman
2536615e0e detect valid extension main functions (#1227)
Fixes #KT-18083
2017-08-07 11:39:34 +02:00
Yujin Jung
4c00119f08 Fix incorrect slack link (#1231) 2017-08-07 11:39:02 +02:00
Nikolay Krasko
7d66af6583 Always assign shebang comment to same position before package 2017-08-07 12:17:20 +03:00
Nikolay Krasko
8d226594ff Put comments and whitespaces under body in script files
It's more consistent to normal function body for IDE.
Doc comments in file beginning are now sticks to declarations
correctly.
Moving declarations at the end of scripts is fixed
2017-08-07 12:17:17 +03:00
Nikolay Krasko
8de6017e53 Minor: rename comments and whitespace binders file 2017-08-07 12:17:14 +03:00
Nikolay Krasko
ae6f38e252 Minor: fix comment about AllCommentsBinder 2017-08-07 12:13:58 +03:00
Nikolay Krasko
6194bc10f8 Move statement out of top-level lambda in scripts (KT-19322)
#KT-19322 Fixed
2017-08-07 12:12:41 +03:00
Dmitry Petrov
656f8bb5cf Turn SwitchCodegenUtil into a class 2017-08-07 10:31:02 +03:00
Dmitry Petrov
435cfeea0a SwitchCodegenUtil: convert to Kotlin and cleanup 2017-08-07 10:31:02 +03:00
Dmitry Petrov
c5772e5549 SwitchCodegenUtil: .java -> .kt 2017-08-07 10:31:02 +03:00
Dmitry Petrov
2ed5a5e368 'when' should use intrinsics for '=='
#KT-19029 Fixed Target versions 1.1.5
 #KT-18818 Fixed Target versions 1.1.5
2017-08-07 10:31:02 +03:00
Jonathan Leitschuh
20cd748377 Add download link for JDK6 on MacOS to Readme.md (#1229)
Reduce the barier to entry for working on Kotlin by providing a
download link for the MacOS JDK6 in the ReadMe.
2017-08-04 22:47:14 +02:00
Toshiaki Kameyama
dbaec43e4d Make abstract both member and class while applying "Make abstract"
So #KT-12613 Fixed
2017-08-04 21:34:21 +03:00
Toshiaki Kameyama
0a9e0ddba9 Use back-ticks correctly in "Add remaining branches" action
So #KT-13985 Fixed
2017-08-04 20:58:46 +03:00
Alexey Sedunov
97a3d343f7 Create Class from Usage: Support nested classes
This covers the case when original expression doesn't contains qualifier
Also for local or inner containing classes:
  - forbid nested objects
  - add 'inner' to nested class declaration

 #KT-16404 Fixed
2017-08-04 16:48:36 +03:00
Alexey Sedunov
d30461afc6 Create Class from Usage: Support multiple containers 2017-08-04 16:48:35 +03:00
Alexey Sedunov
78117b3e7b Create from Usage: Infer expected type from base declarations
#KT-17480 Fixed
2017-08-04 16:48:35 +03:00
Alexey Sedunov
3b4891279e Configuration: Update default settings for Kotlin/JS compiler 2017-08-04 16:48:35 +03:00
Mikhael Bogdanov
d738633981 Switch jvm target to 1.8 in Ultimate plugin and missed version to core modules 2017-08-04 15:45:53 +02:00
Dmitry Jemerov
563472e676 Include org.json classes in Kotlin plugin jar 2017-08-04 15:30:12 +02:00
Mikhael Bogdanov
db9f925bb1 Switch default project jvm target to 1.8, keep 1.6 for core modules 2017-08-04 13:14:50 +02:00
Alexey Sedunov
aed9d3899e Misc: Fix compiler argument usages after refactoring 2017-08-03 19:59:53 +03:00
Kirill Rakhman
41e5840298 Implement inspection for redundant lambda arrow
Fixes #KT-11991
2017-08-03 15:37:04 +02:00
Kirill Rakhman
9ac1a0140c Add inspection for when with only else (#1206)
Fixes #KT-12523
2017-08-03 15:30:28 +02:00
Nikolay Krasko
61b10ac330 Make class prepare request pattern more precise (KT-19429)
Do not bother with check for irrelevant classes.

 #KT-19429 Fixed
2017-08-03 13:11:06 +03:00
Nikolay Krasko
1ef5362edc Fix breakpoints from Kotlin file placed in irrelevant class (KT-19429)
State that there're no locations in given file, if all locations for
line were filtered out because of wrong file name. Need this because
if we throw exception, other positions managers may return locations
without explicit check for file type or file name.

See PositionManagerImpl.java

 #KT-19429 Fixed
2017-08-03 13:11:06 +03:00
Nikolay Krasko
3ea4a7fb47 Drop support for JVM 1.4 in debugger
Kotlin can't run on such JVM anyway.
2017-08-03 13:11:06 +03:00
Mikhail Glukhikh
0e4089ef8e Keep coroutines classes in ProGuard #KT-19433 In Progress 2017-08-03 12:25:11 +03:00
Alexey Sedunov
d10fa8f891 Minor: Fix array detection 2017-08-03 01:55:44 +03:00
Alexey Sedunov
e38cf54dac Minor: Fix facet/project settings editor 2017-08-03 01:55:44 +03:00
Alexey Tsvetkov
f0becd0040 Fix IC with daemon
JPS IC with daemon was not working since
the commit 514635e965

Before that change `IncrementalCompilation.isEnabled`
returned `true` when the corresponding system property was not set.
After the change `isEnabled` returns `true` only if
the system property is set and equals to `"true"`.

The property was never set up for the daemon if `CompilerMode.JPS_COMPILER`
was used (the property was set up in a JPS process or in the daemon in case
it was used with Gradle).

     #KT-19414 fixed
2017-08-02 23:02:11 +03:00
Dmitry Jemerov
82c62b4d8e Add missing read action 2017-08-02 17:11:56 +02:00
Dmitry Jemerov
88420311cb Look at library content to detect library kind when importing 2017-08-02 17:10:01 +02:00
Dmitry Jemerov
b423d58a14 Load JSR-305 annotations for libraries if it's enabled for any module
#KT-19303 Fixed
2017-08-02 15:25:34 +02:00
Mikhail Glukhikh
4ca8d3d6cf J2K: use refactorings and runWriteAction more accurately #KT-19371 Fixed
Do not invoke runWriteAction for post-processings
in Convert(Text)JavaCopyPasteProcessor.
Instead each processing can need write action or not,
and J2kPostProcessor takes this into account.
2017-08-02 15:30:18 +03:00
Mikhail Glukhikh
8d5e69b06c Inline variable: do not show dialog / preview from J2K #KT-19332 Fixed 2017-08-02 15:30:17 +03:00
Mikhael Bogdanov
b56f5593ab Update changelog for 1.1.4-eap-54 2017-08-02 14:09:39 +02:00
Alexey Sedunov
53d12e6cf7 Method Hierarchy: Refactoring
- Do not rely on light methods and Java method hierarchy
- Support val/var parameters
- Support built-in member functions

 #KT-14346 Fixed
2017-08-02 13:08:06 +03:00
Alexey Sedunov
10941ae732 Call Hierarchy: Refactoring
Do not rely on light methods to search usages as some elements
don't have them (e.g. local functions)

 #KT-9288 Fixed
 #KT-14428 Fixed
2017-08-02 13:08:06 +03:00
Alexey Sedunov
0c2ea5d799 Light Classes: Fix equivalence check
Do not consider PsiClass equiavent to KtLightClass
if it's not a light class as well

 #KT-16180 Fixed
2017-08-02 13:08:06 +03:00
Alexey Sedunov
e6f1a3ccf3 Minor: Use Kotlin reflection in usage printing and update test data 2017-08-02 13:08:06 +03:00
Alexey Sedunov
3c0a4a0abf Minor: Fix bug introduced by the refactoring 2017-08-02 13:08:05 +03:00
Dmitry Petrov
c5613888eb Look into proper context when generating backing field access
Problem manifests when a class property name matches a companion object
property name, and class property is referenced in closure context.

 #KT-19367 Fixed Target versions 1.1.5
2017-08-02 11:24:35 +03:00
Dmitry Petrov
05eee9c173 Minor: adjust formatting 2017-08-02 11:24:35 +03:00
Yan Zhulanow
3d7d1b20ab Ensure there won't be the same classpath entries in the resulting classpath 2017-08-02 03:36:57 +03:00
Bill Collins
9a40e9b96d Don't overwrite plugin classpaths detected earlier for annotation processing. Fixes #KT-18022 2017-08-02 03:36:56 +03:00
Yan Zhulanow
3770786075 Minor: Fix test data for CLI test (defaultCacheImplementation option was added in Android Extensions) 2017-08-02 03:36:55 +03:00
Yan Zhulanow
13868f89e8 Minor: Change test format to JUnit 3 2017-08-02 03:35:16 +03:00
Yan Zhulanow
45681ed9eb Fix "'Redundant modality' is not reported with all-open" (KT-18195) 2017-08-02 03:35:15 +03:00
Yan Zhulanow
6002281874 Android Extensions: Downgrade to old Android variant processing logic when 'experimental' flag is disabled (KT-19270) 2017-08-02 03:35:14 +03:00
Yan Zhulanow
3bb7febeb8 AllOpen: Make private members open again because of KT-19047 2017-08-02 03:35:13 +03:00
Yan Zhulanow
5ff014f89d Parcelable, minor: Change error message 2017-08-02 03:35:12 +03:00
Yan Zhulanow
448fa8495a Parcelable, Lint: Do not report "CREATOR field missing" warnings on our '@Parselize' Parcelables 2017-08-02 03:35:11 +03:00
Yan Zhulanow
c1600c9841 Report errors from compiler plugins as compiler PLUGIN_ERRORs (KT-19311) 2017-08-02 03:35:10 +03:00
Yan Zhulanow
9a5a003d0a NoArg: Fix IllegalAccessError on instantiating sealed class child via Java reflection (KT-18245) 2017-08-02 03:21:16 +03:00
Yan Zhulanow
53e193d130 AllOpen: Support @SpringBootTest annotation (KT-18262) 2017-08-02 03:21:15 +03:00
Yan Zhulanow
4dddb00aca Kapt: Fix "Anonymous class types are not rendered properly in stubs" (KT-18682) 2017-08-02 03:21:14 +03:00
Yan Zhulanow
bf2bc1fdc7 Android Extensions: Support smart-casted receivers (KT-18545) 2017-08-02 03:21:13 +03:00
Mikhail Glukhikh
9e9c4f79f5 Make MODIFIERS_ORDER consistent with code style document 2017-08-01 20:42:40 +03:00
Nikolay Krasko
65ea9290ea Skip method check for non-relevant positions (KT-19403)
#KT-19403 Fixed
2017-08-01 20:09:54 +03:00
Nikolay Krasko
2ba89b9e68 Fix bad cast on absent descriptor in field breakpoint (EA-101988) 2017-08-01 20:09:54 +03:00
Alexey Tsvetkov
45ec0e364a Remove Gradle plugin dependency on Apache Commons
We have used `commons-lang` to detect
if current OS is a Windows.
`org.apache.commons.lang.SystemUtils` also
tries to parse JDK version in `clinit` and,
as of AC version 2.4, fails on JDK 9.

I preferred to remove the dependency completely
and copy an implementation of `isWindows` from Intellij
platform, because the code is quite simple
and minimizing unnecessary dependencies will help to avoid
compatibility problems in future.

Gradle plugin also declares a dependency on `commons-io`,
but it seems unused, so the dependency is also removed.

    #KT-18832 fixed
2017-08-01 19:43:25 +03:00
Alexey Sedunov
40163868af Support mutable/immutable compiler arguments 2017-08-01 19:40:37 +03:00
Alexey Sedunov
2984a5a19f Fix reflection-based operations on compiler arguments after conversion 2017-08-01 19:40:22 +03:00
Alexey Sedunov
50599c933f J2K: CommonToolArguments and inheritors 2017-08-01 19:36:49 +03:00
Alexey Sedunov
2e49971989 J2K: CommonToolArguments and inheritors (rename) 2017-08-01 19:36:49 +03:00
Yan Zhulanow
2d8f7419eb Parcelable: Temporarily disable box tests because of OOM 2017-08-01 18:37:27 +03:00
Mikhail Glukhikh
87cdc7635a Do not suggest "can be private" for elements with given annotations
So #KT-19272 Fixed
2017-08-01 18:01:29 +03:00
Mikhail Glukhikh
c5a81691fb Partial code cleanup: can be private and some others applied 2017-08-01 17:08:56 +03:00
Mikhael Bogdanov
42f8a3e65b Generify Symbols class to be able support jvm specific implementation 2017-08-01 15:52:29 +02:00
Mikhael Bogdanov
4dbb82a789 Copy ununsed lowers 2017-08-01 15:52:28 +02:00
Mikhael Bogdanov
df56ef5e3f Copy common lowers 2017-08-01 15:52:28 +02:00
Mikhael Bogdanov
27365dc4be Copy common utils from Native 2017-08-01 15:52:27 +02:00
Nikolay Krasko
5fcefa28a7 Test stub trees compatibility on loadJava/compiledKotlin test data 2017-08-01 16:22:40 +03:00
Mikhail Glukhikh
c2617e89c9 Remove unnecessary check from prepareCodeToInline 2017-08-01 12:32:49 +03:00
Mikhail Glukhikh
1ed1751b63 Report "Make <visibility>" for visibility fixes #KT-19274 Fixed
(instead of "Add <visibility> modifier")
2017-08-01 12:06:28 +03:00
Toshiaki Kameyama
29dba9edb3 Do not report "property can be private" in annotations #KT-19273 Fixed 2017-08-01 11:53:42 +03:00
Nagesh Susarla
b9788bbafd Close the local.properties file after reading 2017-07-31 15:36:18 -07:00
Ilya Gorbunov
050744627d Clean stdlib and reflect before rewriting binary API dump
The change in the run configuration "Binary compatibility tests, overwrite results"
is to prevent incremental compilation of these artifacts.
During the incremental compilation only the declarations in the files being
recompiled are dumped to declarations.json.
This results in incomplete dump and affects the public declarations dump.

This clean step enforces stdlib and reflect libraries to be fully recompiled.
This step can be removed as soon as we do not need declarations.json to dump public API.
2017-07-31 23:13:56 +03:00
Alexey Tsvetkov
69b4d213b7 Ensure IC.isEnabled is not modified by tests 2017-07-31 19:34:59 +03:00
Alexey Tsvetkov
514635e965 IC should be enabled explicitly by build systems
The change only affects JPS on TeamCity (in Intellij IC system property
is always set explicitly; the same holds for Gradle, Maven).
Previous changes have effectively enabled the new IC (which is now default)
for TC JPS builds, which is undesirable as more RAM is used.
2017-07-31 19:34:59 +03:00
Alexey Tsvetkov
5ce3a436c7 Avoid marking dirty dependencies from already compiled chunks
#KT-17397 fixed
2017-07-31 19:34:59 +03:00
Alexey Tsvetkov
7cccba3b9a Refactoring: do not check if IC is enabled in cache
There was a bunch of if-else blocks checking if new IC was enabled or not.
These blocks became useless after `IncrementalCompilation.isExperimental`
was replaced with `IncrementalCompilation.isEnabled`, because when IC is not enabled
we don't use caches anyway.
2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
3f471d1ac6 Minor: add dummy.kt to some IC tests
This makes it impossible to pass the tests
by rebuilding everything.
2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
e602903567 Remove old IC: remove experimental tests 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
534db2d45b Remove old IC: remove experimental cache version 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
a4a0335b20 Remove old IC: update KotlinJpsBuildTest 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
62fdd91947 Remove old IC: remove unnecessary caches 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
aea5293288 Remove old IC: fix constant search test
The tests were not run with the new IC before
2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
8143ca158b Remove old IC: update on-off tests 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
e7afb073d9 Remove old IC: remove experimental-expected-kotlin-caches.txt 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
5af9d29cbe Remove old IC: remove experimental-ic-build.log
This commit moves each experimental-ic-build.log
into a corresponding build.log file.
2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
2bd7d12312 Remove old IC: remove IncrementalCompilation.isExperimental 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
50091bfac8 Remove old IC: remove flags from CompilationResult 2017-07-31 19:34:58 +03:00
Alexey Tsvetkov
840f688bbf Refactoring: simplify proto map API 2017-07-31 19:34:58 +03:00
Alexander Udalov
2e82bb5632 Use correct LanguageVersionSettings in MetadataSerializer
Also, require users of K2MetadataCompiler to pass "-Xmulti-platform"
manually. Gradle and Maven plugins already do that, so only users who
invoke kotlinc directly are going to be affected by this

 #KT-19287 Fixed
2017-07-31 08:47:47 -07:00
Sergey Igushkin
4923589b38 Fix testAndroidExtensionsManyVariants not using experimental flag 2017-07-31 16:56:06 +03:00
Sergey Igushkin
23ea1a1a60 Push Android Gradle plugin version used in tests to 3.0.0-alpha8 2017-07-31 16:52:48 +03:00
Andrius Semionovas
f42808af94 Add when support for USELESS_IS_CHECK quick fix, related to KT-18965 2017-07-31 16:10:41 +03:00
Andrius Semionovas
e0aca97f9f Add quick-fix for USELESS_IS_CHECK #KT-18965 Fixed 2017-07-31 16:10:23 +03:00
Dimach
88fa7c2952 Introduce "double negation" inspection #KT-4748 Fixed 2017-07-31 15:57:31 +03:00
Toshiaki Kameyama
be0b01a1e6 Do not report "can be private" on effectively private / local elements
So #KT-18822 Fixed
2017-07-31 11:58:14 +03:00
Pavel V. Talanov
05ea99441f script.runtime 1.1.4: Update test data implementations 2017-07-30 18:21:35 +03:00
Pavel V. Talanov
b0b2c046b2 script.runtime 1.1.4: IDE and compiler use 'kotlin.script.experimental' 2017-07-30 18:15:41 +03:00
Pavel V. Talanov
d7e62937b2 script.runtime 1.1.4: Remove new API from 'kotlin.script' package
Copy of new API is in 'kotlin.script.experimental' package
2017-07-30 17:38:10 +03:00
Pavel V. Talanov
9a004ceda2 script.runtime 1.1.4: Remove copy of ScriptContents class
This class is not new(experimental) API is not supposed to be moved
2017-07-30 17:17:54 +03:00
Simon Ogorodnik
5e032139cb KT-18040: Enable auto popup when typing after $e. in string template
#KT-18040 fixed
2017-07-30 09:15:16 +03:00
Alexander Udalov
4e77897bfd Pass LanguageSettingsProvider to AnalyzerFacade explicitly
This way is more flexible for example for tests, where configuring the
service implementation may be tricky (it's usually done in
KotlinCoreEnvironment in production code)
2017-07-28 20:15:28 +03:00
Pavel V. Talanov
ca06d38c5b script.runtime 1.1.4: Copy new API to kotlin.script.experimental package
Minor: Move Environment type alias to resolvers_deprecated.kt file
2017-07-28 20:13:59 +03:00
Pavel V. Talanov
d59a72ea75 script.runtime 1.1.4: Undeprecate old API 2017-07-28 20:13:57 +03:00
Pavel V. Talanov
9e34437447 script.runtime: add 'kotlin-runtime' dependency
script.runtime is not built by JPS, this just affects highlighting
2017-07-28 20:13:54 +03:00
Alexander Udalov
82502e1a8b Fix compilation of kotlin-script-util
Compilation was broken in 46a01ec
2017-07-28 19:26:35 +03:00
Leonid Startsev
527ccaff16 Changes required for serialization plugin to work:
* Support for generation of synthetic nested classes (for implementations
of user-defined serial annotations):

    1. Compiler extenstion points for contributing names and descriptoprs
of nested classes

    2. Control on synthetic class primary constructor visibility

* Public functions for generating initializing expressions for optional
properties
2017-07-28 07:04:57 -07:00
Dmitry Petrov
9e6b706a03 Unwrap property imported from object on property access
#KT-18982 Fixed Target versions 1.1.5
2017-07-28 17:01:04 +03:00
Sergey Igushkin
05919244bd Fix testLogLevelForceGC 2017-07-28 16:39:10 +03:00
Sergey Igushkin
7906ac9348 Fix unresolved rhino dependency in testDce. 2017-07-28 16:39:10 +03:00
Pavel V. Talanov
c1fd8fc318 Send roots changed iff combined dependencies of all scripts changed
This reduces total number of reindex requests when working with scripts

ScriptDependenciesCache::onChange logic is independent from ScriptDependenciesUpdater::onChange
2017-07-28 15:45:29 +03:00
Pavel V. Talanov
e115c8b373 Filter out invalid files before contributing them for indexing
#EA-104574
2017-07-28 15:45:26 +03:00
Nikolay Krasko
99555fa843 Retrieve receiver annotation to stubs from compiled code (KT-19209)
#KT-19209 Fixed
2017-07-28 15:01:32 +03:00
Alexander Udalov
8b149db0ec Drop deprecated KotlinPaths.getRuntimePath, use getStdlibPath instead 2017-07-28 14:16:48 +03:00
Alexander Udalov
b988582531 Refactor utilities in AbstractKotlinJpsBuildTestCase 2017-07-28 14:16:47 +03:00
Alexander Udalov
1e6850f198 CLI: improve error message if libraries are not found in Kotlin home
Also support the '-kotlin-home' argument in kotlinc-js

 #KT-18859 Fixed
2017-07-28 14:16:46 +03:00
Alexander Udalov
eb673d6ed3 Do not try to compile if incorrect language/API version is passed 2017-07-28 14:11:35 +03:00
Alexander Udalov
4b42f9e071 Move JPS-related kotlin-home detection code to jps-plugin 2017-07-28 14:11:35 +03:00
Alexander Udalov
46a01ec131 J2K PathUtil: convert and prettify 2017-07-28 14:11:35 +03:00
Alexander Udalov
3beb6a86f7 J2K PathUtil: move .java -> .kt 2017-07-28 14:11:35 +03:00
Dmitry Petrov
67336653e0 Generate SAM wrappers only if they are required for a given argument
SAM interface wrapper for an argument is required,
if in the function descriptor for SAM adapter
type for the corresponding value parameter
doesn't match type of the corresponding value parameter
in the original (Java) descriptor.

 #KT-19251 Fixed Target versions 1.1.5
2017-07-28 08:24:46 +03:00
Dmitry Petrov
c8bc2d9d16 Minor: code cleanup 2017-07-28 08:24:46 +03:00
Dmitry Petrov
5df461c7e0 Add test for KT-19246
The issue was fixed by
904c7f9c64
2017-07-28 08:24:46 +03:00
Nikolay Krasko
24865ba26a Allow deprecated fix for TYPEALIAS_EXPANSION_DEPRECATION 2017-07-28 01:28:56 +03:00
Nikolay Krasko
53373b66b9 Do not replace in alias when constructor has special pattern (KT-19202)
#KT-19202 Fixed
2017-07-28 01:28:56 +03:00
Nikolay Krasko
1b93e2030f Create isCallee utility function 2017-07-28 01:28:56 +03:00
Yan Zhulanow
142a64e039 Minor: Fix Gradle integration test compilation, replace .use() with try&finally 2017-07-27 21:22:06 +03:00
Sergey Igushkin
fabcd6b73c Fix Gradle IT compilation. 2017-07-27 20:44:03 +03:00
Anton Bannykh
e9e81d96a5 Fixed maven multiplatform test 2017-07-27 19:34:14 +03:00
Mikhael Bogdanov
79921b0206 Update changelog for 1.1.4-eap-33 2017-07-27 14:18:35 +02:00
Valentin Kipyatkov
ee7eb3186d Fixed problems with ModuleDescriptor mismatch after ProcessCanceledException 2017-07-27 14:05:45 +03:00
Valentin Kipyatkov
6ba96b1103 Renamed function 2017-07-27 13:56:30 +03:00
Valentin Kipyatkov
7f467f0fdd Minor 2017-07-27 13:56:29 +03:00
Valentin Kipyatkov
d3ea7c3a14 No need to pass fq-names to import when we have bindingContext 2017-07-27 13:56:28 +03:00
Valentin Kipyatkov
996292264b Fixed inline when multiple implicit receivers exist
#KT-17776 Fixed
 #KT-17266 Fixed
2017-07-27 13:55:25 +03:00
Valentin Kipyatkov
0346b31628 Enabled Loop to call chain inspection again 2017-07-27 13:54:59 +03:00
Valentin Kipyatkov
44dafc38e5 A bit more correct fix of KT-14665 2017-07-27 13:33:57 +03:00
Kirill Rakhman
3ff5c95419 Improve inspection message for NullableBooleanElvisInspection
Also report as "should" or "can" depending on severity
So #KT-19006 Fixed
2017-07-27 11:08:26 +03:00
Simon Ogorodnik
c41c5f1916 KT-19145: Enable type completion for extension properties
#KT-19145 fixed
2017-07-27 09:57:11 +03:00
Andrius Semionovas
68659f5a32 Introduce error "ANNOTATION_USED_AS_ANNOTATION_ARGUMENT" along with QF
The relevant inspection has been removed
So #KT-18855 Fixed
2017-07-27 09:54:22 +03:00
Dmitry Petrov
b81ca31aae Record resolved delegation call for primary ctor if single result
Do the same thing as for secondary constructor (looks like it was a
workaround for R&I bug that was used only for secondary constructors
for some reason).

 #KT-17464 Fixed Target versions 1.1.5
2017-07-27 09:24:48 +03:00
Dmitry Petrov
c9ad290ad5 Do not store null for temporary in destructuring assignment
#KT-19256 Fixed Target versions 1.1.5
2017-07-27 09:02:26 +03:00
Dmitry Petrov
b867c46f72 Generate for-in-range loop as counter loop when possible
If an upper bound is a compile-time constant != Int.MAX_VALUE,
we can generate 'for (i in x..N)' as 'for (i in x until N+1)'.
2017-07-27 09:02:26 +03:00
Dmitry Petrov
7450899b87 Minor: extract get*CompileTimeConstant
Get rid of code duplication.
2017-07-27 09:02:26 +03:00
Ilya Gorbunov
ca8bf395c3 Do not create iterator in 'any', 'none', 'all' and 'count' unless necessary
#KT-19133 Fixed
2017-07-26 22:42:29 +03:00
Mikhael Bogdanov
ff676c050f Properly generate inner classes when compiling source for inline
KT-19175: Compiler generates different bytecode when classes are compiled separately or together

 #KT-19175 Fixed
2017-07-26 20:31:14 +02:00
Sergey Igushkin
7da6ff78c1 Fix Kapt3 classes not consumed by kotlinCompile tasks from their friend 2017-07-26 20:19:33 +03:00
Yan Zhulanow
ea1068a822 Parcelable, minor: Rename MagicParcel to Parcelize 2017-07-26 20:19:32 +03:00
Yan Zhulanow
f29cf07fa4 Android Extensions, minor: Fix test 2017-07-26 20:19:32 +03:00
Yan Zhulanow
92558ad183 Minor: Clarify module name in warning message about empty output classpath/output directories 2017-07-26 20:19:31 +03:00
Yan Zhulanow
826672ea1b Kapt: Register kapt classes output directory as Java classes directory (KT-19211)
This is relevant to pure (non-Android) Java projects and Gradle 4.0+.
2017-07-26 20:19:30 +03:00
Yan Zhulanow
725f51056f Kapt: Do not use AbstractCompile as a supertype for KaptTask (KT-19179)
Gradle sometimes tells that kaptCompile is UP-TO-DATE even when it's not true, so the annotation processing step is silently skipped.
Looks like replacing `mapSource {}` with an explicit getter or with manual `source()` invocation does not fix the problem.

This looks like a bug in Gradle appeared since 3.0. The test from this commit works with Gradle 2.14.1.
2017-07-26 20:19:29 +03:00
Yan Zhulanow
53fda33499 Kapt: 'kaptKotlin' task should be invoked only when all task dependencies from kapt configuration is built (KT-19178) 2017-07-26 20:19:28 +03:00
Yan Zhulanow
c2be771486 Android Extensions: Support defaultCacheImplementation in Gradle 2017-07-26 20:19:27 +03:00
Yan Zhulanow
5a1a4bd8bd Android Extensions: Add global cache flag in compiler plugin 2017-07-26 20:19:26 +03:00
Yan Zhulanow
84eff43b49 Parcelable: Support Android Extensions experimental flag 2017-07-26 20:19:25 +03:00
Yan Zhulanow
98a2506eb0 Android Extensions: Add kotlin-android-extensions-runtime only if experimental flag is enabled 2017-07-26 20:19:25 +03:00
Yan Zhulanow
8cdcfc5e67 Android Extensions: Migrate enabled status check to Gradle importer #KT-17641 2017-07-26 20:19:24 +03:00
Yan Zhulanow
38449caaed Parcelable: Fixes after review 2017-07-26 20:19:23 +03:00
Yan Zhulanow
d0e4b236a7 Parcelable: Support SortedSet, NavigableSet, SortedMap, NavigableMap 2017-07-26 20:19:22 +03:00
Yan Zhulanow
cf607a0f14 Parcelable: Report error on unsupported parameter types, add @RawValue annotation support 2017-07-26 20:19:21 +03:00
Yan Zhulanow
4200629347 Parcelable: Support CharSequence, IBinder/IInterface, objects, enums. Serialize Parcelable efficiently if possible 2017-07-26 20:19:20 +03:00
Yan Zhulanow
19eb30b3ae Parcelable: Add test for clinit merging 2017-07-26 20:19:19 +03:00
Yan Zhulanow
3062e72282 Parcelable: Support Parcelizer interface in order to be able to customize serialization 2017-07-26 20:19:18 +03:00
Yan Zhulanow
aa5f9ee3ec Parcelable: Correctly handle writeToParcel() overriding, report errors on custom writeToParcel() and CREATOR 2017-07-26 20:19:18 +03:00
Yan Zhulanow
96c9bcd820 Parcelable: Allow custom describeContents() implementation 2017-07-26 20:19:17 +03:00
Yan Zhulanow
4197380621 Parcelable: Add declaration checker 2017-07-26 20:19:16 +03:00
Yan Zhulanow
c23bca6afe Parcelable: Add Parcelable functionality to Android Extensions plugin 2017-07-26 20:19:15 +03:00
Yan Zhulanow
edd8a0a64e Parcelable: Download Robolectric artifacts in order to use them in tests 2017-07-26 20:19:14 +03:00
Toshiaki Kameyama
5290553184 Fix Math.min with coerceAtMost intention inside qualified expression
So #KT-19232 Fixed
2017-07-26 20:12:53 +03:00
Ilya Chernikov
a82f66cf45 Add tests for client/session flags removal, minor fix in shutdown logic 2017-07-26 17:16:38 +02:00
Ilya Chernikov
dc88e1e16c Fix daemon clients cleanup, fixes hanging daemon processes 2017-07-26 17:16:37 +02:00
Toshiaki Kameyama
c3988ef184 Support "Lift return out of when" for exhaustive when without else
So #KT-18852 Fixed
2017-07-26 17:44:19 +03:00
Mikhail Glukhikh
9781d1fcdf Remove unused variable with constant initializer #KT-13886 Fixed 2017-07-26 15:18:46 +03:00
Mikhail Glukhikh
a08f55cf99 Cast to type quick-fix: handle case with qualified elements correctly
Same fix for 'add !!' fix
So #KT-18368 Fixed
2017-07-26 15:18:38 +03:00
Mikhail Glukhikh
e6872c52a3 More accurate deparenthesize (keeping annotations) in some IDE actions
So #KT-19004 Fixed
2017-07-26 15:18:30 +03:00
Mikhail Glukhikh
7fb78a0372 Code cleanup: replace chained null-checks with safe-calls 2017-07-26 15:18:22 +03:00
Nikolay Krasko
732d1129ab Enable replace for deprecated alias in whole project (KT-14929)
#KT-14929 Fixed
2017-07-26 14:20:59 +03:00
Nikolay Krasko
5df2698f77 Enable ReplaceWith for type aliases (KT-14929)
#KT-14929 Fixed
2017-07-26 14:20:57 +03:00
Alexander Udalov
224df7a1ea Change -Xload-jsr305-annotations argument to -Xjsr305-annotations={ignore|enable}
See https://youtrack.jetbrains.com/issue/KT-19229 for a complete
explanation

 #KT-19229 Fixed
 #KT-10942
2017-07-26 11:45:25 +03:00
Alexander Udalov
2f99f6ad34 Refactor AnalysisFlags and their support in IDE
* Support flags with any value (not just Boolean)
* Support all flags by parsing arguments in KotlinFacetSettings, instead
  of manually listing known flags

 #KT-19210 Fixed
2017-07-26 11:45:24 +03:00
Alexander Udalov
845de7aa4d Minor, change parameter type of parseCommandLineArguments 2017-07-26 11:45:24 +03:00
Alexander Udalov
593f98190d Keep .txt and .caps files in compiler.pro
Files like org/jline/utils/capabilities.txt are needed for jline to
function correctly

 #KT-19237 Fixed
2017-07-26 11:45:23 +03:00
Dmitry Petrov
0391c24ab2 Provide diagnostic for typealias using deprecated class or constructor
#KT-19205 Fixed Target versions 1.1.5
2017-07-26 09:02:45 +03:00
Dmitry Jemerov
c78ad9c047 Correctly detect library kind when not using modules per sourceset
#KT-19219 Fixed
2017-07-25 18:20:45 +02:00
Simon Ogorodnik
fa88fb74c4 Disable completion binding context caching by default
Now it opt-in in internal mode, due duplication problems
 #KT-19191 fixed
2017-07-25 18:26:34 +03:00
Simon Ogorodnik
094125c970 KT-19154: Fix auto-import to check receiver for members properly
#KT-19154 fixed
2017-07-25 16:16:57 +03:00
Alexander Udalov
f313001b2d Update to jline 3.3.1 and jansi 1.16
Note that the history file name was changed (.kotlin_history ->
.kotlinc_history) because the history is now stored in a different
(incompatible) format.

 #KT-11369 Fixed
2017-07-25 11:10:45 +03:00
Ilya Gorbunov
baa6b44567 Deprecate CharSequence.size in JS
#KT-18267 Fixed
2017-07-24 21:14:45 +03:00
Ilya Gorbunov
f10ea03173 Provide extension to get mutable iterator from the mutable map
#KT-18992 Fixed
2017-07-24 21:02:15 +03:00
Dmitry Jemerov
e0dc7a27a0 Migration for pre-1.1.3 JS libraries
#KT-19156 Fixed
2017-07-24 19:53:52 +02:00
Dmitry Jemerov
861219f502 ConfigureKotlinTest refactoring to avoid duplicating production logic 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
63c6ba7e31 Add missing read action 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
f370d74609 Correctly detect stdlib in Gradle projects; move detection out of EDT
To detect whether a module has an stdlib in its dependencies, look at
source root modules and not at base module.
2017-07-24 19:53:52 +02:00
Dmitry Jemerov
0971af803c Check for non-configured modules in background thread
#KT-17835 Fixed
2017-07-24 19:53:52 +02:00
Dmitry Jemerov
e1f7c91728 Use Kotlin/JVM and Kotlin/JS terms in the UI 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
0f2992ddec JavaFrameworkType: J2K 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
079f7690a8 JavaFrameworkType: rename to .kt 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
6dbaec0cc6 Use distinct icon for Kotlin/JS module and libraries 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
6eff8c7b4b JSFrameworkType: J2K 2017-07-24 19:53:52 +02:00
Dmitry Jemerov
57a501ebce JSFrameworkType: rename to .kt 2017-07-24 19:53:52 +02:00
Pavel V. Talanov
8e3f8c4c14 Fix calling GSS.union for empty array
EA-104046
2017-07-24 18:56:19 +03:00
Pavel V. Talanov
d5ca46157a Refactor: Make DependenciesCache and ScriptDependenciesUpdater services
Rename: DependenciesCache -> ScriptDependenciesCache
    (makes sense to make name more specific since it is a service now)
2017-07-24 18:56:16 +03:00
Pavel V. Talanov
f1811e7f0e Minor, more precise error message 2017-07-24 18:56:14 +03:00
Kirill Rakhman
4c7ddbe397 "Use destructuring declaration" should not be available for top-level and class properties (#1205)
Fixes #KT-19167
2017-07-24 14:33:46 +02:00
Dmitry Petrov
f558b4238c Use counter loop in intrinsic array constructors
#KT-19149 Fixed Target versions 1.1.5
2017-07-24 10:17:30 +03:00
Dmitry Petrov
c9d9a8220d Minor: use IntrinsicMethods.INTRINSICS_CLASS_NAME where appropriate 2017-07-24 10:15:27 +03:00
Dmitry Petrov
fda89e9c72 Add test for KT-19128
It looks like the problem was caused by incorrect merging of
StrictBasicValues and was fixed by commit
904c7f9c64.

 #KT-19128 Fixed
2017-07-24 10:15:27 +03:00
Dmitry Petrov
d0c8af5621 Keep track of second receiver type in CallReceiver
#KT-17725 Fixed Target versions 1.1.5
2017-07-24 10:15:27 +03:00
Dmitry Petrov
3f34a97880 Minor: extract CallReceiver to a top-level class, move code around 2017-07-24 10:15:27 +03:00
Simon Ogorodnik
f079ed949c KT-19015: Enable multiarg completion for non-first argument
#KT-19015 fixed
2017-07-24 00:00:11 +03:00
Ilya Gorbunov
ec5c15f190 test-dagger-maven-example: kotlin version comes as a parameter 2017-07-21 20:15:34 +03:00
Ilya Gorbunov
d8ea3ddcc8 Cleanup poms of projects migrated to gradle 2017-07-21 20:15:34 +03:00
Alexander Udalov
f69e96b240 Fix IAE at protoDifferenceUtils.kt on new metadata field
The class_local_variable/package_local_variable JVM extensions were
added in 616d575fb6

 #KT-19155 Fixed
2017-07-21 20:11:43 +03:00
Nikolay Krasko
b6bd3e15c5 Fix outdated highlighting for Kotlin injected fragments (KT-18842)
Do not use cached value for injection in non-dispatch threads and throw
PCE if value isn't ready. Otherwise outdated value may be stored in
highlighting.

 #KT-18842 Fixed
2017-07-21 19:57:21 +03:00
Alexander Udalov
7f8e7c66f5 Suppress FNFE in .kotlin_metadata index
Similarly to VirtualFileKotlinClass.create.

This could happen for example when some files are removed from
kotlin-stdlib-common
2017-07-21 19:03:15 +03:00
Alexander Udalov
ebdf5aa223 Discriminate header classes in favor of non-header type aliases
In the test case, the problem was that Foo.a's type was resolved to the
_class A_, which was written to metadata on JVM instead of the class
AImpl with typealias A as an abbreviation. This metadata was incorrect
because there's no class A from the JVM compiler's point of view; that's
why the error "cannot access class A" was reported

 #KT-19151 Fixed
2017-07-21 19:03:15 +03:00
Mikhail Glukhikh
6ee94dae6f Code cleanup: KotlinSafeDeleteProcessor 2017-07-21 18:59:13 +03:00
Mikhail Glukhikh
d05a525d8d Search for KtTypeAlias in safe delete processor
Related to KT-16046
2017-07-21 18:59:07 +03:00
Mikhail Glukhikh
dd0cf8219e Add type aliases into UnusedSymbolInspection / safe delete
So #KT-16046 Fixed
2017-07-21 18:59:01 +03:00
Mikhail Glukhikh
951e8cd91a Code cleanup: unnecessary local variable applied 2017-07-21 18:58:48 +03:00
Mikhail Glukhikh
202fb19cf6 If-then to safe access: more correct receiver calculation
So #KT-18928 Fixed
2017-07-21 18:58:33 +03:00
Mikhail Glukhikh
31bb1cc0f9 Invoke back setting "show inline dialog for local variables"
So #KT-19130 Fixed
2017-07-21 18:58:27 +03:00
Kirill Rakhman
a7084ceb9b Fix some type hints related issues (#1204)
* Type hints shouldn't appear for negative literals
Fixes #KT-18974

* Make type hints work for destructuring declarations
Fixes #KT-18444

* Hide type hints for generic constructor calls if type arguments are explicitly specified
Fixes #KT-19167
2017-07-21 16:31:46 +02:00
Nikolay Krasko
f4038f7109 Fix slow typing because of counting injected fragments (KT-18842)
- cache result of kotlin injection on modification tracker
- never count injection in dispatch thread, use cached result instead
- compute injection with write action priority, reuse cache if unfinished

 #KT-18842 Fixed
2017-07-21 15:41:06 +03:00
Nikolay Krasko
436b637282 Refactoring: show using ProcessCancelException in method name 2017-07-21 15:41:06 +03:00
Nikolay Krasko
fbe16f7b91 Refactoring: delete unused CachedValueProperty class 2017-07-21 15:41:06 +03:00
Mikhail Glukhikh
1cb6128f2f Minor: J2K test fix 2017-07-21 12:21:04 +03:00
Dmitry Petrov
bf3e896464 Update 'this' extension receiver when there's a smart cast
If 'this' (implicit or explicit) was used as an extension receiver,
and the corresponding call required a smart-cast,
this information was effectively lost in "old" resolution & inference,
but is required by "old" JVM BE to generate proper CHECKCASTs.
2017-07-21 08:58:52 +03:00
Dmitry Petrov
c9d54d7110 Generate proper error candidates for type aliases
#KT-17745 Fixed Target versions 1.1.5
2017-07-21 08:58:12 +03:00
Dmitry Petrov
b4d8337ca5 Ignore test for 'primitive Char == object' in JS (KT-19081) 2017-07-21 08:52:29 +03:00
Dmitry Petrov
709a7e201f Simplify code for specialized BranchedValues 2017-07-21 08:52:29 +03:00
Dmitry Petrov
e1a55e8dec Prefer compact bytecode for primitive/object comparisons with Boolean
'java.lang.Boolean#valueOf' doesn't allocate new objects
(it uses pre-allocated singletons for 'true' and 'false').
2017-07-21 08:52:29 +03:00
Dmitry Petrov
8e9c0294fe Do not box primitives for 'primitive == object'
NB user-defined 'equals' can violate contract for 'Object#equals', e.g.,
it can be asymmetric.
Thus we can't avoid boxing for 'object == primitive'.
2017-07-21 08:52:29 +03:00
Dmitry Petrov
fa42f202fa Avoid boxing on 'primitive == boxed' when possible
Similar to 'boxed == primitive' case, different bytecode due to
evaluation order.
2017-07-21 08:52:29 +03:00
Dmitry Petrov
e440de3494 Minor: GeneratePrimitiveVsObjectEqualityTestData 2017-07-21 08:52:29 +03:00
Dmitry Petrov
98ee83f4a3 Minor: move condition for boxed==primitive to corresponding isApplicable 2017-07-21 08:52:29 +03:00
Dmitry Petrov
4cba600268 Minor: some more evaluation order tests for 'boxed == primitive' 2017-07-21 08:52:29 +03:00
Dmitry Petrov
81609e4c6f Generate complex equality comparison only when RHS can have side effects
In "short" version, LHS is always evaluated before RHS,
and RHS may be not evaluated if LHS is null.
So, it makes sense to use "short" version in cases when RHS can't have
side effects (because of more compact bytecode and more opportunities
for code elimination).
2017-07-21 08:52:29 +03:00
Dmitry Petrov
8aacddb9f0 Avoid primitive boxing for 'boxed == primitive' if possible
This makes sense for non-floating-point primitive type
(boolean, char, byte, short, int, long):
floating-point types use specialized versions of 'areEqual'.
2017-07-21 08:52:29 +03:00
Dmitry Petrov
275c758da1 Cleanup and move code around in BranchedValue
- Cleanup inspections
- Move optimized boxed-vs-primitive comparisons to a separate file
2017-07-21 08:52:29 +03:00
Dmitry Petrov
051ac44759 Verify bytecode after mandatory transformations and after optimizations 2017-07-21 08:52:29 +03:00
Simon Ogorodnik
7ed1669050 KT-19011: Fix import optimizing when extension functional type is used
It should check is extension functional type imported from companion
is actually called on companion instance

 #KT-19011 fixed
2017-07-21 03:08:06 +03:00
Dimach
65e603c1ed KT-13552: Fix J2K to generate else block while converting switch
#KT-13552 fixed
2017-07-20 23:35:11 +03:00
Mikhail Glukhikh
44790eccaf Use "unnecessary variable" inspection in J2K
Unused variables are no more treated as unnecessary
Related to KT-15958
2017-07-20 17:48:27 +03:00
Mikhail Glukhikh
39f1ef390e Do not report "redundant Unit" for generic calls coerced to Unit
So #KT-18999 Fixed
2017-07-20 17:48:20 +03:00
Mikhail Glukhikh
c554bfa20d Move: RemoveSetterParameterTypeInspection to inspections package 2017-07-20 17:48:14 +03:00
Mikhail Glukhikh
e154e4cf75 Move: RedundantUnitReturnTypeInspection to inspections package 2017-07-20 17:48:07 +03:00
Simon Ogorodnik
8f78446bff Minor: Clarify code for KT-18786: Fix J2K to move properties to top 2017-07-20 16:04:07 +03:00
Dmitry Jemerov
9213c4a1ab EA-104855 - (1.1.4) NPE: KotlinCommonBlockKt.isFirstParameter 2017-07-20 12:50:12 +02:00
Dmitry Jemerov
fbcc519098 Fix tests affected by annotation wrapping changes 2017-07-20 12:32:48 +02:00
Alexander Udalov
5128b8a409 Add default implementation for Annotations.findAnnotation 2017-07-20 13:27:34 +03:00
Alexander Udalov
def3f73fdd Use AnnotationDescriptor.fqName instead of type
Also use the annotationClass extension property instead of
TypeUtils.getClassDescriptor(annotation.type)
2017-07-20 13:26:13 +03:00
Alexander Udalov
541b9dab52 Introduce optimized BuiltInAnnotationDescriptor for built-in annotations
It's built on a FQ name and avoids resolution of the annotation class
descriptor as much as possible
2017-07-20 13:26:13 +03:00
Alexander Udalov
f39106f75c Do not use parameter descriptors in AnnotationDescriptorImpl 2017-07-20 13:26:13 +03:00
Alexander Udalov
eb205f620c Do not use parameter descriptors in most annotation implementations
Except AnnotationDescriptorImpl, which is refactored in the subsequent
commit.

Note that we no longer check the presence of parameters with the
corresponding names in the annotation class in
LazyJavaAnnotationDescriptor, this is why test data changed
2017-07-20 13:25:39 +03:00
Alexander Udalov
cc7ed2ba54 Change map key type in AnnotationDescriptor.getAllValueArguments
Turns out, only the parameter's name is needed at all usages of this
method. Such a map is both easier to use (no need to call
ValueParameterDescriptor.getName) and easier to construct (no need to
resolve annotation class, its constructor, its parameters). In this
commit, only usages have changed but the implementations are still using
the old logic, this is going to be refactored in subsequent commits
2017-07-20 13:25:39 +03:00
Alexander Udalov
41ea0e8ef8 Introduce AnnotationDescriptor.fqName
Could be used instead of ".annotationClass.fqName" to avoid the unneeded
resolution of the annotation class descriptor
2017-07-20 13:25:38 +03:00
Alexander Udalov
1d64b61a8f J2K AnnotationDescriptor, refactor implementations 2017-07-20 13:25:38 +03:00
Alexander Udalov
7ec67505c5 Optimize Annotations.isEmpty in some implementations 2017-07-20 13:25:38 +03:00
Alexander Udalov
9ee4b39e1b Provide default implementation for Annotations.findExternalAnnotation 2017-07-20 13:25:38 +03:00
Alexander Udalov
5636318eb4 Optimize DeserializedAnnotations in terms of memory traffic
Do not wrap every annotation object into an AnnotationWithTarget
2017-07-20 13:25:38 +03:00
Alexander Udalov
21197b53aa Do not load annotations on value parameter if there are none
Also fix an error in the doc in descriptors.proto
2017-07-20 13:25:38 +03:00
Alexander Udalov
c197db9c69 Remove some unnecessary lazy computations in LazyJavaClassDescriptor 2017-07-20 13:25:38 +03:00
Mikhail Glukhikh
bdc44ff4cf Unnecessary variable: do not start inlining in write action
So #KT-19110 Fixed

(cherry picked from commit 6325fb1)
2017-07-20 12:39:52 +03:00
Ilya Chernikov
e38aaf3e07 Fix xmx setting for the daemon in tests 2017-07-20 10:54:05 +02:00
Ilya Chernikov
17a189a24b Improve logging and exception handling in the daemon 2017-07-20 10:54:05 +02:00
Denis Zharkov
904c7f9c64 Fix nullable variables spilling in coroutines
See the last comment in testData for clarification

 #KT-18983 Fixed
2017-07-20 10:53:32 +03:00
Denis Zharkov
90e894b171 Use known jvm binary class for package part if possible 2017-07-20 10:53:09 +03:00
Denis Zharkov
99a10d8d63 Minor. Rename compactIfPossible -> compact
As ArrayList can always be compacted
2017-07-20 10:53:09 +03:00
Denis Zharkov
f454858bbb Optimize memory footprint for case of empty annotations in types
It seems that most of the simple types don't have any annotations,
so for that case it's worth removing the field from SimpleTypeImpl

Also introduce a NotNullSimpleType being used when replacing nullability
2017-07-20 10:53:09 +03:00
Denis Zharkov
f8a12a0ec3 Optimize JavaTypeResolver by avoiding using some language features
It's quite a hot point and using local functions with default
parameters seem to affect negatively to overall performance
(at least some of compiler benchmark have shown it)
2017-07-20 10:53:09 +03:00
Denis Zharkov
d7cee95d95 Call compactIfPossible where it's possible in BinaryJava*
It helps to avoid retaining a lot of redundant empty SmartList's
instances
2017-07-20 10:53:09 +03:00
Denis Zharkov
e2ce285ec3 Reduce memory footprint after functions substitution
Do not recreate new instances if descriptors' parts remain
effectively the same
2017-07-20 10:53:09 +03:00
Denis Zharkov
4a73fbb70a Reduce memory footprint of TypeSubstitutor
Avoid creating new instances if types remain unchanged
2017-07-20 10:53:09 +03:00
Denis Zharkov
4385ce8828 Reduce memory footprint for basic case of flexible types
The case is when we have a simple type constructor
(not array nor collection) and type is not raw:
A<T1, >..A<T1>?

Actually these types are almost equal besides of nullability,
but we create and resolve two different simple types,
they have different arguments' lists, etc.

The idea is to add NullableSimpleType subclass with delegate
to another simple type

It should help a lot both with common cases and with corner ones:
flexibles types in spark for Function22 having exponential size
because of its flexibility

 #KT-14375 Fixed
 #KT-14323 Fixed
2017-07-20 10:53:09 +03:00
Denis Zharkov
59f2ba98a6 Avoid creating SimpleType instances for default type 2017-07-20 10:53:09 +03:00
Denis Zharkov
8576054788 Use SmartList instead of SmartSet for overridden descriptors
SmartSet was used because it was the only lightweight collection
available in core, but now there is org.jetbrains.kotlin.utils.SmartList
2017-07-20 10:53:09 +03:00
Denis Zharkov
729f20ed81 Reduce memory size retained by LookupTrackerImpl
By default SmartList is used there for storing values of a multimap,
so a lot of duplicated items is stored there (file names are being
duplicated).

Even although there is a separate interner for these values,
retained memory size has been reduced for 30M when compiling `idea`
module in Kotlin project
2017-07-20 10:53:09 +03:00
Denis Zharkov
c7e6f200da Use SmartList for storing annotations in binary classes
Looks like in the most cases there are <= 1 annotations
in real declarations
2017-07-20 10:53:09 +03:00
Simon Ogorodnik
36ab31f2f7 Minor: fix test after merge 2017-07-20 02:30:34 +03:00
Toshiaki Kameyama
fe599463ac KT-18978 Intention Move to class body generates incorrect code for vararg val/var (#1188)
Intention Move to class body generates incorrect code for vararg val/var #KT-18978 Fixed
2017-07-20 01:29:56 +03:00
Dimach
a59021a25e KT-18786: J2K should move all properties to top of class
#KT-18786 fixed
2017-07-20 01:15:15 +03:00
Simon Ogorodnik
ccfcfd8721 Add benchmark for local completion and improve benchmarking 2017-07-19 21:18:58 +03:00
Dmitry Jemerov
4df6db141c Advance source stub version which wasn't advanced in 5d87276cf
#KT-19113 Fixed
2017-07-19 18:52:29 +02:00
Dmitry Petrov
891799c853 Generate 'Deprecated' annotation on invisible companion object field
Design decision: if the field for a companion object should have
non-public visibility, generate it with @Deprecated annotation in
language version 1.2.

TODO: generate it with proper visibility in 1.3 and later.

KT-11567 Companion object INSTANCE field more visible than companion object class itself
2017-07-19 17:38:17 +03:00
Dmitry Jemerov
951392005b Add options for wrapping local variable and property annotations
#KT-14950 Fixed
2017-07-19 15:03:00 +02:00
Dmitry Jemerov
050ff03b07 Implement wrapping options for enum constants
#KT-14126 Fixed
2017-07-19 15:02:59 +02:00
Dmitry Jemerov
7555bb6c3c Support formatting of 'where' clauses
#KT-14083 Fixed
2017-07-19 15:02:58 +02:00
Dmitry Jemerov
325e950bfe Reformat expression body property accessors
#KT-17394 Fixed
2017-07-19 15:02:52 +02:00
Dmitry Jemerov
4db8639bf8 Consistent name for option controlling spaces around .. 2017-07-19 15:02:50 +02:00
Dmitry Jemerov
31840fa328 Fix GradleLanguageFeatureQuickFixTest on Windows 2017-07-19 13:56:00 +02:00
Toshiaki Kameyama
366b9d1d79 KT-12195 Quickfix @JvmStatic on main() method in an object (#1192)
* Quickfix @JvmStatic on main() method in an object #KT-12195 Fixed

* Fixed #KT-12195
2017-07-19 13:37:12 +02:00
Toshiaki Kameyama
a8da79a130 KT-12504 Intention to make open class with only private constructors sealed (#1193)
* Intention to make open class with only private constructors sealed #KT-12504 Fixed

* Fixed #KT-12504
2017-07-19 13:36:36 +02:00
Nikolay Krasko
dd2a87dbf7 Rewrite test class to make it work on Windows
Stop using dummy file and assert result with assertEqualsToFile().

Previous version didn't work on Windows because of `\r`.
2017-07-19 13:25:17 +03:00
Nikolay Krasko
4e76975a52 Force OOB in accessors for properties without explicit type (KT-19062)
#KT-19062 Fixed
2017-07-19 12:45:06 +03:00
Nikolay Krasko
bcbff98382 Check OOB stays the same for string in super type constructor call 2017-07-19 12:45:06 +03:00
Pavel V. Talanov
41276c950b Update CodegenTestCase after rebasing on latest changes 2017-07-19 12:29:27 +03:00
Pavel V. Talanov
5faad493b4 Catch and report exceptions from DependenciesResolver 2017-07-19 12:29:25 +03:00
Pavel V. Talanov
eb5be038fa ScriptDependenciesUpdater: compute script contents synchronously 2017-07-19 12:29:22 +03:00
Pavel V. Talanov
9eb8cec5cf ScriptDependenciesUpdater: set job to null after processing result
Fix inconsistency introduced after extracting ScriptDependenciesUpdater
2017-07-19 12:29:20 +03:00
Pavel V. Talanov
537b1689b7 DependenciesCache: remove ad-hoc ScriptDependencies comparison 2017-07-19 12:29:17 +03:00
Pavel V. Talanov
b1ac451959 Make sure template classpath is always among script dependencies 2017-07-19 12:29:15 +03:00
Pavel V. Talanov
f84cc7fb5b Offload legacy dependency resolver work to a separate thread pool
This is mainly to improve experience for kdsl users before gradle migrates to new API
2017-07-19 12:29:12 +03:00
Pavel V. Talanov
bc399444ab Fix creating DependenciesResolver with default arguments 2017-07-19 12:29:09 +03:00
Pavel V. Talanov
7aee51fd77 Refactor ScriptDependenciesUpdater: improve readability a bit 2017-07-19 12:29:07 +03:00
Pavel V. Talanov
c0e08c61ee Minor: extract ScriptContentLoader::getEnvironment 2017-07-19 12:29:04 +03:00
Pavel V. Talanov
42629d6f8d ScriptDependenciesUpdater: use Job explicitly instead of futures
Cancel jobs without interrupting
2017-07-19 12:29:02 +03:00
Pavel V. Talanov
999c3c5e76 Rename services related to script dependencies
KotlinScriptConfigurationManager -> ScriptDependenciesManager
KotlinScriptExternalImportsProvider -> ScriptDependenciesProvider
2017-07-19 12:28:59 +03:00
Pavel V. Talanov
96db16a988 ScriptDependenciesUpdater, minor: improve isLastSentRequestCheck 2017-07-19 12:28:56 +03:00
Pavel V. Talanov
aacb9a437a Rename: dependenciesClasspath -> templateClasspath
Clearer distinction from additionalResolverClasspath
2017-07-19 12:28:54 +03:00
Pavel V. Talanov
96d8f685e9 Refactor KotlinScriptConfigurationManager: extract parts
Introduce ScriptDependenciesUpdater, DependenciesCache and ScriptContentLoader
2017-07-19 12:28:51 +03:00
Pavel V. Talanov
1b42095dc1 Support @AcceptedAnnotations for different kinds of resolvers 2017-07-19 12:28:49 +03:00
Pavel V. Talanov
1c412b4068 AsyncDependenciesResolver: provide implementation for sync resolve 2017-07-19 12:28:46 +03:00
Pavel V. Talanov
008c27d547 Compiler build depends on kotlinx-coroutines-core 2017-07-19 12:28:43 +03:00
Pavel V. Talanov
ee70a64e1c Minor, template providers: don't create classloader for empty classpath 2017-07-19 12:28:41 +03:00
Pavel V. Talanov
beb28a1c7d Gradle Kotlin DSL uses compiler-embdeddable jar when loading resolver 2017-07-19 12:28:38 +03:00
Pavel V. Talanov
5c18ab750b GradleScriptTemplateProvider: avoid duplicating template loading code 2017-07-19 12:28:36 +03:00
Pavel V. Talanov
6c3ce7adc1 ScriptTemplatesProvider: refactor dependency loading
Change dependenciesClasspath is of type List<File>
Add additionalResolverClasspath
2017-07-19 12:28:33 +03:00
Pavel V. Talanov
a77cd0ab09 Catch errors when instantiating script templates
If we throw from this code IDE becomes unusable

 #KT-18945 Fixed
2017-07-19 12:28:31 +03:00
Pavel V. Talanov
8ac17400ae ScriptDependenciesFileAttribute: fix TODOs 2017-07-19 12:28:28 +03:00
Pavel V. Talanov
75220e145b Minor: suppress deprecation warning 2017-07-19 12:28:26 +03:00
Pavel V. Talanov
cf57e5a7a1 Script templates: search for parameterless constructor of resolver 2017-07-19 12:28:23 +03:00
Pavel V. Talanov
10e14103b6 Propagate reports from script dependency resolver
Compiler: show as compiler messages
IDE: annotate code in a separate highlighting pass
2017-07-19 12:28:20 +03:00
Pavel V. Talanov
96c2a589c0 Support legacy resolver interface 2017-07-19 12:28:18 +03:00
Pavel V. Talanov
65dba3615c Update project code to use new script.runtime APIs 2017-07-19 12:28:15 +03:00
Pavel V. Talanov
375b058a28 Add coroutines-jdk8 to project 2017-07-19 12:28:13 +03:00
Pavel V. Talanov
1012a24afc Refactor: move KotlinScriptExternalImportsProviderImpl to 'cli' module 2017-07-19 12:28:10 +03:00
Pavel V. Talanov
b6a7d831bf Script IDE API: remove <TF: Any> 2017-07-19 12:28:08 +03:00
Pavel V. Talanov
581176fa90 AbstractScriptConfigurationTest: adapt to changes in API 2017-07-19 12:28:05 +03:00
Pavel V. Talanov
788eaf8a18 Refactor getting dependencies for script files API
Deprecate KotlinScriptDefinition#getDependenciesFor
Expose dependencyResolver as a property
KotlinScriptExternalImportsProvider is the component clients should be asking for dependencies
2017-07-19 12:28:02 +03:00
Pavel V. Talanov
ff391628de KSCM: fix wrong update on null return from Template.getDependenciesFor 2017-07-19 12:28:00 +03:00
Pavel V. Talanov
1834721880 KSCM: persist script dependencies between idea launches 2017-07-19 12:27:55 +03:00
Pavel V. Talanov
930d502b12 KSCM: rework async requests 2017-07-19 12:27:53 +03:00
Pavel V. Talanov
3c511f3f40 KSCM: temporary workaround gradle returning results in unstable order 2017-07-19 12:27:50 +03:00
Pavel V. Talanov
fb0e0e3767 Introduce ScriptDependenciesFileAttribute to persist script dependencies 2017-07-19 12:27:48 +03:00
Pavel V. Talanov
a2aeda7b2c Support async script dependency updates for annotation based templates
Do not try to cache dependencies for every script on startup
Schedule cache updates upon request as opposed to updating them synchronously
2017-07-19 12:27:45 +03:00
Pavel V. Talanov
b7fc909821 Split compiler and ide specific parts of script dependency caching
Move all caching logic to ide specific KotlinScriptConfigurationManager
Clean up apis
Remove logging when updating caches
2017-07-19 12:27:43 +03:00
Anton Bannykh
e43a145614 fixup: updated EXPECTED_REACHABLE_NODES 2017-07-19 12:24:09 +03:00
Anton Bannykh
6ed7eaf546 JS tests: changes to kotlin.test + the way compiler tests are generated. 2017-07-19 12:24:09 +03:00
Alexey Sedunov
eda747c0bf Minor: Fix tests 2017-07-19 11:34:30 +03:00
Roman Elizarov
f2b5f37b22 Support inline suspend functions built with compiler version less than 1.1.4/1.2-M1
The error message is removed and is replaced with a code that adapts
inline suspend functions produced by the old compiler with the
suspension markers that new compiler expects.
2017-07-19 08:59:55 +03:00
Roman Elizarov
9f0810f723 Pull implementations up from AbstractCoroutineContextElemenet
Fixes KT-18671
2017-07-19 08:59:43 +03:00
Alexander Udalov
c9b14c5a45 Reduce classpath for class loader in CodegenTestCase
There's no point in adding JDK (mock or full) roots to it, as well as
stdlib/reflect/test (they are loaded by the parent class loader, created
in ForTestCompileRuntime)
2017-07-18 20:10:07 +03:00
Alexander Udalov
743278d456 Fix ReplInterpreter on Java 9 2017-07-18 20:10:05 +03:00
Alexander Udalov
aa53fa7e15 Fix execution of simple .kts scripts on Java 9 2017-07-18 20:10:05 +03:00
Alexander Udalov
bc2c958a2e Remove unused class GenericRepl 2017-07-18 20:10:05 +03:00
Alexander Udalov
36001ff931 Do not allow to access compiler internals in .kts scripts
Set parent class loader to null explicitly instead of the system class
loader
2017-07-18 20:10:05 +03:00
Alexander Udalov
d1603c4329 Minor, move deserializeToDescriptor to package kotlin.reflect.jvm.internal
To prevent binary-compatibility-validator from reporting it as a public
API; that happens because the signature is different after the
gradle-shadow-plugin is applied
2017-07-18 20:09:24 +03:00
Yan Zhulanow
00225b3de3 Use compiling evaluator only if there is non-inline lambda or a loop in the bytecode 2017-07-18 18:22:30 +03:00
Yan Zhulanow
a6925e0d0f Minor: Fixes after review 2017-07-18 18:22:29 +03:00
Yan Zhulanow
904b693571 Pass byte array more efficiently
Filling byte[] values is especially slow on Android (>3000ms to fill a byte[3000] on emulator).
2017-07-18 18:22:28 +03:00
Yan Zhulanow
069579fd79 Debugger: Disable code interpreting by default in evaluator
Provide the compiled bytecode to debugger instead of interpreting the expression by default.
This significantly increases evaluation speed in numerous cases, e.g. `(1..10000).map { it.toString() }.count()`.
Leave interpreter mode as a fallback.

Android does not provide decent in-memory class loading support.
Moreover, we need to run dex on the compiled classes, and it required significant time.
So for now compiling evaluator for Android is available only in Android O, and only if there're any local classes or non-inline lambdas (evaluator didn't work for them before so we may consider this change as an improvement).
2017-07-18 18:22:28 +03:00
Yan Zhulanow
4851a83a83 Android Extensions: put new functionality under the flag 2017-07-18 18:10:30 +03:00
Yan Zhulanow
77eafb9716 Kapt: Map kaptGenerateStubsKotlin task classpath properly, ensure the destination for compileKotlin isn't in it (KT-18799) 2017-07-18 18:10:29 +03:00
Yan Zhulanow
83f9835e00 Android Exensions: Add kotlin-android-extensions-runtime dependency automatically in Gradle plugin 2017-07-18 18:10:28 +03:00
Yan Zhulanow
b303fa9caa Android Extensions: Fixes after review 2017-07-18 18:10:27 +03:00
Yan Zhulanow
7b238e0b21 Android Extensions: Add SparseArray implementation for the View cache (KT-18250) 2017-07-18 18:10:26 +03:00
Yan Zhulanow
fbfd51e97e Minor: Group plugin modules 2017-07-18 18:10:25 +03:00
Yan Zhulanow
820f914d35 Remove obsolete kapt2 implementation 2017-07-18 18:10:24 +03:00
Yan Zhulanow
423a09e46a Android Extensions: Support LayoutContainer in code generation 2017-07-18 18:10:23 +03:00
Yan Zhulanow
a69f9729e0 Android Extensions: Use Activity and Fragment supertypes in INVOKE_VIRTUAL calls instead of the user implementation class names 2017-07-18 18:10:22 +03:00
Yan Zhulanow
d4b4bc71ee Android Extensions: Support @ContainerOptions in compiler plugin 2017-07-18 18:10:21 +03:00
Yan Zhulanow
6e1dd08fbb Android Extensions: Add runtime library with LayoutContainer and its options 2017-07-18 18:10:20 +03:00
Yan Zhulanow
1a1db5a6f1 Android Extensions: Support cache in custom Views 2017-07-18 18:10:19 +03:00
Yan Zhulanow
c9cd1a4d75 Minor: Android Extensions compiler plugin refactoring 2017-07-18 18:10:18 +03:00
Yan Zhulanow
0494862ce5 Minor: Move Android Extensions compiler plugin tests to some other package 2017-07-18 18:10:17 +03:00
Yan Zhulanow
303b246a49 Minor: Move AndroidExtensionsReportSubmitter to other KAE files 2017-07-18 18:10:16 +03:00
Yan Zhulanow
e037cafe18 Use descriptor modality in IDE inspections/intentions
This fixes KT-18160, KT-18194, KT-18195, KT-18197 ~
2017-07-18 18:10:15 +03:00
Yan Zhulanow
942fa7719a Android Extensions: Add synthetic property highlighting 2017-07-18 18:08:33 +03:00
Yan Zhulanow
f7786a42ab Android Extensions: Show warning on a dot-call of a reference which is missing in some configurations (KT-18012)
When more than one layout configuration is available, a particular resource (view or fragment) may be absent in some of them.
We should show a warning on such resource reference calls as the call may lead to NPE.
2017-07-18 18:08:32 +03:00
Yan Zhulanow
f4acf404ca Android Extensions: Support Android variants and library dependencies (KT-14086, KT-16934) 2017-07-18 18:08:31 +03:00
Yan Zhulanow
8e9a62d553 Kapt: Add gradle warnings for Android projects
1. When the old kapt (aka kapt1) is used
2. (for Android projects) When Kotlin plugin is applied but annotationProcessor (Java-only) dependencies are found
2017-07-18 18:08:29 +03:00
Toshiaki Kameyama
865f9d4c7e Wrong caption "Change to property access" for Quick Fix to convert class instantiation to object reference #KT-13870 Fixed (#1189) 2017-07-18 15:47:43 +02:00
Mikhail Glukhikh
987c7f5be8 Add "unnecessary local variable" inspection #KT-15958 Fixed 2017-07-18 16:37:47 +03:00
Dmitry Neverov
9d06a80519 Do not report "property can be private" on JvmField properties
So #KT-18970 Fixed
2017-07-18 15:48:10 +03:00
Nikolay Krasko
5281602381 Don't ignore filters in smart step over for inline calls 2017-07-18 14:39:55 +03:00
Nikolay Krasko
f664ffb06b Check correspondent call on end token for better step over (KT-18949)
#KT-18949 Fixed
2017-07-18 14:39:54 +03:00
Nikolay Krasko
d282f14eac Don't add double linenumber when return expression is absent (KT-18949)
#KT-18949 Fixed
2017-07-18 14:39:54 +03:00
Nikolay Krasko
a41c9d2476 Avoid state machine build for suspend function with single inline call
#KT-18949 Fixed
2017-07-18 14:39:54 +03:00
Nikolay Krasko
ce4f923ba0 Replace return with nop to avoid merging line instructions (KT-18949)
Dex ignores subsequent line numbers for same instructions and interprets
instruction after inline as if they were inlined. This makes debugger
behaves as if there's nowhere to stop on line with breakpoint.

This also makes stepping through inline function consistent with
non-inline analog. In both context debugger now stops on '}'.

 #KT-18949 Fixed
 #KT-17120 Fixed
2017-07-18 14:39:54 +03:00
Nikolay Krasko
fc685aa03f Refactoring: extract common part to function 2017-07-18 14:39:54 +03:00
Nikolay Krasko
179ec84684 Refactoring: mark getTopmostElementAtOffset() as not-null 2017-07-18 14:39:54 +03:00
Mikhail Glukhikh
c0e1b3ef2d CFG: fix label binding for last instruction of finally block
So #KT-18698 Fixed
2017-07-18 14:37:13 +03:00
Mikhail Glukhikh
ab0e734e7d PseudocodeLabel: add slightly better exception diagnostics 2017-07-18 14:36:42 +03:00
Mikhail Glukhikh
9a5b5393f5 Code cleanup: CFG (several inspections applied) 2017-07-18 14:36:18 +03:00
Mikhail Glukhikh
43f9035d07 Minor test fix 2017-07-18 13:51:27 +03:00
Toshiaki Kameyama
f8cf0f2ab9 Misleading quick fix message for an 'open' modifier on an interface member #KT-18738 Fixed 2017-07-18 18:59:22 +09:00
Alexey Sedunov
d2dbc47454 Create from Usage: Remove extra space before type parameters list
#KT-16352 Fixed
2017-07-17 16:09:57 +03:00
Alexey Sedunov
e98af7bfc1 Create Class from Usage: Use type parameter bounds as supertypes
#KT-15242 Fixed
2017-07-17 16:09:55 +03:00
Alexey Sedunov
95769dc9d3 Create from Usage: Make property lateinit where possible
#KT-17651 Fixed
2017-07-17 16:09:54 +03:00
Alexey Sedunov
e9bf1d2ab8 Create from Usage: Add test for KT-17537
#KT-17537 Fixed
2017-07-17 16:09:53 +03:00
Alexey Sedunov
0365d3a3d6 Create from Usage: Do not create type parameter by constuctor reference
#KT-17353 Fixed
2017-07-17 16:09:52 +03:00
Alexey Sedunov
2e76a76088 Control Flow: Fix CFG usage info for double-colon expressions
#KT-12551 Fixed
 #KT-17092 Fixed
2017-07-17 16:09:51 +03:00
Alexey Sedunov
216b28ec55 Implement Members: Do not generate 'header' keyword
#KT-18466 Fixed
2017-07-17 16:09:50 +03:00
Alexey Sedunov
26d6088c82 Create from Usage: Infer expected type for lambda body
#KT-18186 Fixed
2017-07-17 16:09:49 +03:00
Alexey Sedunov
b48feb257c Create from Usage: Create data class property from destructuring entry
#KT-18540 Fixed
2017-07-17 16:09:48 +03:00
Simon Ogorodnik
a212a1bf72 Put all internal actions under Tools | Kotlin | Internal group 2017-07-17 16:03:10 +03:00
Simon Ogorodnik
4cdc3fdde9 KT-14606: Never compute decompiled text in BasicLookupElementFactory
#KT-14606 fixed
2017-07-17 16:03:07 +03:00
Simon Ogorodnik
6036c95511 Prevent KotlinDecompiledFileViewProvider from reading vfile when possible 2017-07-17 16:03:04 +03:00
Simon Ogorodnik
bc5872dd8f Add completion benchmark to check completion speed 2017-07-17 16:03:02 +03:00
Nikolay Krasko
dfef1f4921 Add reference equality shortcut for equals() in light members 2017-07-17 14:50:59 +03:00
Nikolay Krasko
44ed903303 Implement equivalence of light members by origin when possible
Previous implementation worked through equality that used equality
of method stubs (see LightMemberOriginForCompiledMethod). But method
stubs for compiled element can be recreated when caches are outdated,
including weak reference cleaning (see ClsJavaStubByVirtualFileCache).

This could cause misbehave of find usages when java reference has an
outdated version of light element in resolution cache.
2017-07-17 14:50:59 +03:00
Toshiaki Kameyama
fda097fc3b Correct "before" sample in description for intention Convert to enum class #KT-18722 Fixed (#1196) 2017-07-17 13:03:15 +02:00
Dmitry Jemerov
6baa8614e6 Fix JS tests in AbstractConfigureKotlinTest 2017-07-17 12:09:11 +02:00
Dmitry Jemerov
2c2b64d44a AbstractConfigureKotlinTest: J2K 2017-07-17 12:09:10 +02:00
Dmitry Jemerov
4198a5c3ec AbstractConfigureKotlinTest: rename to .kt 2017-07-17 12:09:09 +02:00
Dmitry Jemerov
0e6c9a96c7 Specify library kind when configuring library in tests 2017-07-17 12:09:04 +02:00
Dmitry Jemerov
060b8e0025 ConfigLibraryUtil: J2K 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
921db30c90 ConfigLibraryUtil: rename to .kt 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
0fa09adf17 Provide library kind for common libraries; get rid of autodetection 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
c7e85ea28f Better encapsulate JS library detection 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
b8d453eec3 Set library kind when importing projects from Maven 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
608f5892f9 Set library kind when importing projects from Gradle 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
902fe1f5ce Implement explicit library kind for JS libraries, don't autodetect 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
1367e6f303 Get library versions directly, not through LibraryPresentationProvider 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
2d1ac69986 JSLibraryStdDescription: J2K 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
5f3366d60b JSLibraryStdDescription: J2K 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
c185730846 KotlinJsModuleConfigurator: J2K 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
ffb3e2fcbc KotlinJsModuleConfigurator: rename to .kt 2017-07-17 11:58:57 +02:00
Dmitry Jemerov
1f6788ac31 Fix CodeConformanceTest on Windows 2017-07-17 11:57:03 +02:00
Nikolay Krasko
b3e9dfcea9 Minor: fix weak warnings and formatting in KotlinReferencesSearcher.kt 2017-07-17 12:25:06 +03:00
Nikolay Krasko
d93e0adc4f Do not wrap to light elements if Kotlin search is requested (KT-19054)
#KT-19054 Fixed
2017-07-17 12:25:06 +03:00
Dmitry Petrov
8c7352e668 Generate constant "" for effectively empty string 2017-07-17 09:18:41 +03:00
Knize
389c7d03b7 KT-6676 Show enum ordinal in quickdoc (#1165)
KT-6676: Show enum ordinal in quickdoc

 #KT-6676 fixed
2017-07-14 22:28:16 +03:00
Simon Ogorodnik
cc8933c82b KT-17074: Make completion respect DslMarker's
#KT-17074 fixed
2017-07-14 21:06:43 +03:00
Alexander Udalov
3c04ca4397 Update KotlinVersion.CURRENT to 1.1.5 2017-07-14 21:03:06 +03:00
Alexander Udalov
2611c7de7e Restore anonymous classes for local delegate metadatas in inline functions
The problem is that now that the local delegated property metadata is in
the $$delegatedProperties array of the containing class, the access to
it from code calling an inline function with a local delegated property
is illegal.

Currently it seems to be a lot of work to support this rather rare case
properly (see the comment in ExpressionCodegen.getVariableMetadataValue)
so we postpone it and return the old behavior of using the anonymous
KProperty subclass for metadata
2017-07-14 15:13:12 +03:00
Alexander Udalov
616d575fb6 Support reflection for local delegated properties
#KT-15222 Fixed
2017-07-14 15:13:12 +03:00
Alexander Udalov
c444c4d10b Ignore $$delegatedProperties in light analysis mode tests
For tests with local delegated properties, this field is generated in
the full mode, but is not generated in the lite mode because local
variables are not analyzed properly in the lite mode
2017-07-14 15:04:05 +03:00
Alexander Udalov
db27a885f1 Rework property metadata generation for local delegated properties
Instead of generating an anonymous class for each delegated local
variable, store metadatas in the $$delegatedProperties array of the
containing class, as is done for member properties
2017-07-14 15:04:05 +03:00
Alexander Udalov
9344f7f42f Remove unused and obsolete code in JVM backend 2017-07-14 15:04:05 +03:00
Alexander Udalov
728de91140 Refactor generation of metadata for delegated properties
In CodegenAnnotatingVisitor, store all delegated properties whose
metadata should be generated in each class (identified by ASM Type).
Use the stored information later, both in the $$delegatedProperties
array generation and in the access to it from property's accessor
methods, instead of an heuristical indexOfDelegatedProperty()
2017-07-14 15:04:04 +03:00
Alexander Udalov
b97589b33e Remove CodegenBinding.LOCAL_VARIABLE_DELEGATE
Calculate this value at call sites explicitly instead
2017-07-14 15:04:04 +03:00
Alexander Udalov
66ea288be7 Minor, extract fakeDescriptorsForReferences.kt 2017-07-14 15:04:04 +03:00
Stanislav Erokhin
9e98c11114 [NI] Minor. Change return type substitute function to not null 2017-07-14 12:43:09 +03:00
Stanislav Erokhin
2602216039 [NI] Use NewTypeSubstitutor when create descriptor with fresh variables. 2017-07-14 12:43:09 +03:00
Stanislav Erokhin
652676dc71 [NI] Introduce transactions for constraint system.
This will be used for callable reference resolution.
2017-07-14 12:43:09 +03:00
Stanislav Erokhin
cb494c46d7 [NI] Add initial constraint to IncorporationConstraintPosition 2017-07-14 12:43:08 +03:00
Stanislav Erokhin
c767545d4c Minor. Remove unused CandidateWithBoundDispatchReceiver#copy 2017-07-14 12:43:08 +03:00
Stanislav Erokhin
ac06060260 [NI] Minor. Drop unused CommonSupertypeCalculator 2017-07-14 12:43:08 +03:00
Stanislav Erokhin
0404fbc092 [NI] Minor. Rename LambdaAnalyzer to KotlinResolutionCallbacks 2017-07-14 12:43:08 +03:00
Dmitry Petrov
178e3e2c98 [NI] Update argument types on call completion using nested calls resolution 2017-07-14 12:43:07 +03:00
Dmitry Petrov
4448637727 [NI] Support calling abstract class constructor in delegating call 2017-07-14 12:43:07 +03:00
Dmitry Petrov
549e8ba668 [NI] Use ALWAYS_SUITABLE_RECEIVER when no receiver is available
(as in "old" resolution & inference)

This fixes issues with Java static members access.
2017-07-14 12:43:07 +03:00
Dmitry Petrov
2bdeef7970 [NI] Postprocess lambda result expressions on call completion
Should update type to denotable, e.g.,
IntegerValueType(x) to proper numeric type.

TODO extract common code into some ValueArgumentPostprocessor
2017-07-14 12:43:07 +03:00
Dmitry Petrov
1d6ed4ef8e [NI] Update lambda result types.
When completing calls, update return types for functional descriptors
for lambdas using type inference results.

Add toString to some Call subclasses (for debugging purposes).
2017-07-14 12:43:06 +03:00
Dmitry Petrov
2bf252afe6 [NI] Introduce lambda result dependency edges
Given a lambda result type R_L with constraint R_L <: T,
for each constituent type variable V in T with variance matching
approximation direction for V, consider a dependency edge V -> R
(lambda-result-dependency).

E.g., given a constraint:
    R <: Out<V>
where V is approximated down (to sub-type).
After R is fixed, we obtain constraint
    Out<T> <: Out<V>
which is incorporated as
    T <: V
which is a relevant constraint for V.
2017-07-14 12:43:06 +03:00
Dmitry Petrov
13e8720ddc [NI] Keep track of fresh type variables created for particular call candidate
Otherwise we can't obtain inferred type arguments for the call,
which is required for reification.
2017-07-14 12:43:06 +03:00
Dmitry Petrov
eb7e9196b5 [NI] Fix some argument mapping problems
1. Value arguments for the resolved call are indexed with resulting
descriptor value parameters (which can be substituted).

2. Simple argument can be a single vararg element if the corresponding
value parameter is a vararg parameter.

3. Resulting descriptor should be approximated to super-type.
This doesn't affect type inference, but the JVM BE expects types with
proper classifiers.
2017-07-14 12:43:06 +03:00
Stanislav Erokhin
0c79949cf1 [NI] Implement NewTypeSubstitutor 2017-07-14 12:43:05 +03:00
Stanislav Erokhin
ff8a57dc26 [NI] Implement New CommonSuperTypeCalculation 2017-07-14 12:43:05 +03:00
Stanislav Erokhin
6aac67aa7e [NI] Approximate captured types when set them into variable.
Also do not store type with captured type inside possible types.
It is hack for now, but without it captured types can flow to
resolution and exception will be thrown.
2017-07-14 12:43:05 +03:00
Stanislav Erokhin
397103f9d0 [NI] Fix smart cast for expression with captured input type. 2017-07-14 12:43:05 +03:00
Stanislav Erokhin
73cc1fdd9c [NI] Resolve type variable to Nothing for TO_SUBTYPE direction. 2017-07-14 12:43:04 +03:00
Stanislav Erokhin
6e24b0f89d [NI] Approximate captured types when we resolve type variable TO_SUPER. 2017-07-14 12:43:04 +03:00
Stanislav Erokhin
53caa84db9 [NI] Add constrains even we try add constraint like TypeVariable <: CapturedType from subtyping.
If such captured type has lower type, then from TypeVariable <: lowerType => TypeVariable <: CapturedType.
2017-07-14 12:43:04 +03:00
Stanislav Erokhin
657c332a1f [NI] Do not run "or" branches for constraint subtyping.
We should never do that, because otherwise we can get unexpected result.
  Example for input constraint: C(in String) <: T.
  If we run usual subtyping algorithm, then we get 2 constraints:
  C(in String) <: T and T <: String.
  Of course such system has contradiction.
2017-07-14 12:43:04 +03:00
Stanislav Erokhin
0fadf0bf70 [NI] Approximate captured types before type variable fixation.
We prefer denotable types when we solve constraint system.
I.e. if for T we have not equality constraint with captured type we can approximate captured type to denotable type.
2017-07-14 12:43:03 +03:00
Stanislav Erokhin
b4bf534d29 [NI] Capture from supertypes of type parameter.
This works by accident in OI, so this should be supported by new inference.
2017-07-14 12:43:03 +03:00
Stanislav Erokhin
c4ddc7a3a6 [NI] Store stub resolved call to trace because some clients read this before all calls are completed.
This is bad idea, but this is how it works in old inference.
Now we just save old behaviour.
Future plan: fix checks where we get unfinished resolved calls.
2017-07-14 12:43:03 +03:00
Stanislav Erokhin
78f8d29a4c [NI] Fix find maximally specific for NI. 2017-07-14 12:43:03 +03:00
Dmitry Petrov
d67b51e91a [NI] Support wrong number of type arguments and integer constants.
- report WRONG_NUMBER_OF_TYPE_ARGUMENTS
- make integral types work again: IntegerValueType is represented as {Int & Byte & Short & Long} in the constraint system
2017-07-14 12:43:02 +03:00
Dmitry Petrov
f5c59b1343 [NI] Report special error message on constant expression type mismatch. 2017-07-14 12:43:02 +03:00
Dmitry Petrov
5afd3e72d6 [NI] Report diagnostic on abstract class instantiation. 2017-07-14 12:43:02 +03:00
Stanislav Erokhin
b012681a53 [NI] New inference -- initial commit. 2017-07-14 12:43:02 +03:00
Dmitry Petrov
036090be91 Support intersection type in TypeUtils.contains(...) 2017-07-14 12:43:01 +03:00
Stanislav Erokhin
e8501c7d54 Add method replaceType for ReceiverValue.
This method will used for capturing from expressions before call resolution.
2017-07-14 12:43:01 +03:00
Nikolay Krasko
1dcdb72a49 Process UastContext service absence (EA-100670) 2017-07-14 12:39:13 +03:00
Dmitry Jemerov
448dba3f78 License-related cleanup 2017-07-14 11:09:45 +02:00
Ilya Chernikov
84a812df19 Drop forced in-process compilation (as interface compatibility is resolved) 2017-07-13 15:45:34 +02:00
Dmitry Jemerov
9b37e76b14 Don't trigger update check when an in-memory file is modified
#KT-18954 Fixed
2017-07-13 12:50:15 +02:00
Mikhail Zarechenskiy
2d3ce89afc Use only completed arguments of special call 2017-07-13 12:26:03 +03:00
Dmitry Petrov
a687dea898 Introduce special IrDeclarationOrigin's for for-loop variables
FOR_LOOP_ITERATOR
 - temporary variable for for-loop iterator

FOR_LOOP_VARIABLE
 - `x` in `for (x in xs)`

FOR_LOOP_IMPLICIT_VARIABLE
 - temporary variable for for-loop with destructuring, e.g.:
   for ((x, y) in xys)
   =>
   for (tmp in xys) {
     val (x, y) = tmp
   }
2017-07-13 10:59:51 +03:00
Andrius Semionovas
1cab0d09ab KT-18979 Add val to proper place for 'Add val/var' intent 2017-07-13 01:20:24 +03:00
Alexander Udalov
f01de3a935 Minor, move lateinit tests into a subdirectory 2017-07-12 18:59:02 +03:00
Alexander Udalov
b2b492447f Maven plugin: initial support for Java 9 modules 2017-07-12 18:58:36 +03:00
Alexander Udalov
848edc14cb Maven plugin: fix warnings, update copyrights 2017-07-12 18:58:35 +03:00
Alexander Udalov
1d46070bd5 Minor, remove unneeded codegen test
This test is already present in compiler/testData/cli/jvm/
2017-07-12 18:58:35 +03:00
Mikhael Bogdanov
b2a7fb9534 Update ChangeLog.md for 1.1.4-EAP-11 2017-07-12 16:33:25 +02:00
Mikhael Bogdanov
b15cfeb0a0 Add 1.1.3-2 changes 2017-07-12 16:33:25 +02:00
Mikhael Bogdanov
ef003db020 Update ChangeLog.md for 1.1.3 2017-07-12 16:33:25 +02:00
baratynskiy
0b6ef5f291 Make idea-full exported in tests-common module because kapt3 tests use KotlinTestUtils.assertEqualsToFile which uses Editor defined in idea-full 2017-07-12 17:25:32 +03:00
baratynskiy
a288b8d318 Add jsr305.jar to intellij-core because guava-19.0 jar depends on Nullable defined in jsr305.jar 2017-07-12 17:25:32 +03:00
Anton Bannykh
0935ed41d4 JS: return exit code from the NodeJs kotlinc-js wrapper 2017-07-12 17:19:59 +03:00
Dmitry Petrov
da404de51e Add comment regarding testData generation to RangeValues.kt 2017-07-12 16:23:36 +03:00
Dmitry Petrov
2849e19af5 Add test for indices.reversed() 2017-07-12 15:56:29 +03:00
Dmitry Petrov
6a673a03e4 Generate test data for in-expression tests, fix bug with indices 2017-07-12 15:56:29 +03:00
7861 changed files with 200308 additions and 49844 deletions

3
.gitignore vendored
View File

@@ -7,7 +7,7 @@
/gh-pages
/ideaSDK
/android-studio/sdk
/out
out/
/tmp
workspace.xml
*.versionsBackup
@@ -21,4 +21,5 @@ workspace.xml
.gradle/
build/
!**/src/**/build
!**/test/**/build

View File

@@ -61,6 +61,9 @@
<element id="module-output" name="ir.psi2ir" />
<element id="module-output" name="annotation-based-compiler-plugins-ide-support" />
<element id="module-output" name="frontend.script" />
<element id="extracted-dir" path="$PROJECT_DIR$/dependencies/json-org.jar" path-in-jar="/" />
<element id="module-output" name="idea-gradle" />
<element id="module-output" name="idea-jvm" />
</element>
<element id="library" level="project" name="javax.inject" />
<element id="directory" name="jps">
@@ -72,6 +75,7 @@
</element>
<element id="archive" name="android-extensions-compiler.jar">
<element id="module-output" name="android-extensions-compiler" />
<element id="module-output" name="android-extensions-runtime" />
</element>
<element id="archive" name="android-lint.jar">
<element id="module-output" name="uast-kotlin" />
@@ -102,9 +106,12 @@
<element id="archive" name="kotlin-gradle-tooling.jar">
<element id="module-output" name="kotlin-gradle-tooling" />
</element>
<element id="library" level="project" name="uast-java" />
<element id="library" level="project" name="kotlinx-coroutines-core" />
<element id="library" level="project" name="javaslang" />
<element id="library" level="project" name="kotlinx-coroutines-jdk8" />
<element id="archive" name="kapt-idea.jar">
<element id="module-output" name="kapt3-idea" />
</element>
</element>
<element id="directory" name="kotlinc">
<element id="dir-copy" path="$PROJECT_DIR$/dist/kotlinc" />

View File

@@ -1,8 +1,10 @@
<component name="ProjectDictionaryState">
<dictionary name="yan">
<words>
<w>deserializes</w>
<w>impls</w>
<w>kapt</w>
<w>parceler</w>
<w>uast</w>
</words>
</dictionary>

7
.idea/dictionaries/yole.xml generated Normal file
View File

@@ -0,0 +1,7 @@
<component name="ProjectDictionaryState">
<dictionary name="yole">
<words>
<w>multiplatform</w>
</words>
</dictionary>
</component>

View File

@@ -235,7 +235,6 @@
<scope name="idea openapi" level="WARNING" enabled="true" />
<scope name="runtime.classes" level="ERROR" enabled="true" />
</inspection_tool>
<inspection_tool class="LoopToCallChain" enabled="false" level="INFO" enabled_by_default="false" />
<inspection_tool class="MethodMayBeStatic" enabled="true" level="WARNING" enabled_by_default="true">
<option name="m_onlyPrivateOrFinal" value="false" />
<option name="m_ignoreEmptyMethods" value="true" />

9
.idea/kotlinc.xml generated
View File

@@ -1,8 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="KotlinCommonCompilerArguments">
<option name="languageVersion" value="1.1" />
<option name="apiVersion" value="1.1" />
<component name="Kotlin2JsCompilerArguments">
<option name="sourceMapPrefix" value="" />
<option name="sourceMapEmbedSources" value="inlining" />
</component>
<component name="Kotlin2JvmCompilerArguments">
<option name="jvmTarget" value="1.8" />
</component>
<component name="KotlinCompilerSettings">
<option name="additionalArguments" value="-version -Xallow-kotlin-package -Xskip-metadata-version-check" />

9
.idea/libraries/android_layoutlib.xml generated Normal file
View File

@@ -0,0 +1,9 @@
<component name="libraryTable">
<library name="android-layoutlib">
<CLASSES>
<root url="jar://$PROJECT_DIR$/ideaSDK/plugins/android/lib/layoutlib.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES />
</library>
</component>

View File

@@ -7,7 +7,7 @@
<CLASSES>
<root url="jar://$PROJECT_DIR$/ideaSDK/core/annotations.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/asm-all.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/guava-19.0.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/guava-21.0.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/intellij-core.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/jdom.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/jna.jar!/" />
@@ -18,12 +18,14 @@
<root url="jar://$PROJECT_DIR$/ideaSDK/core/util.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/xpp3-1.1.4-min.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/core/xstream-1.4.8.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/lib/jsr305.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$PROJECT_DIR$/dependencies/guava-19.0-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/guava-21.0-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/sources/sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/asm-src.zip!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/lib/jsr305.jar!/" />
</SOURCES>
</library>
</component>

View File

@@ -4,11 +4,11 @@
<root url="file://$PROJECT_DIR$/annotations" />
</ANNOTATIONS>
<CLASSES>
<root url="jar://$PROJECT_DIR$/dependencies/jline.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/jline3.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$PROJECT_DIR$/dependencies/jline-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/jline3-sources.jar!/" />
</SOURCES>
</library>
</component>

View File

@@ -0,0 +1,11 @@
<component name="libraryTable">
<library name="kotlinx-coroutines-jdk8">
<CLASSES>
<root url="jar://$PROJECT_DIR$/dependencies/kotlinx-coroutines-jdk8.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$PROJECT_DIR$/dependencies/kotlinx-coroutines-jdk8-sources.jar!/" />
</SOURCES>
</library>
</component>

41
.idea/libraries/robolectric.xml generated Normal file
View File

@@ -0,0 +1,41 @@
<component name="libraryTable">
<library name="robolectric">
<CLASSES>
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/accessibility-test-framework-2.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/android-all-6.0.0_r1-robolectric-0.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/annotations-12.0.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/ant-1.8.0.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/ant-launcher-1.8.0.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/asm-5.0.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/asm-analysis-5.0.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/asm-commons-5.0.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/asm-tree-5.0.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/asm-util-5.0.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/bcprov-jdk16-1.46.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/guava-19.0-rc2.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/hamcrest-core-1.3.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/hamcrest-library-1.3.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/icu4j-53.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/junit-4.8.2.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/maven-ant-tasks-2.1.3.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/protobuf-java-2.6.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-annotations-3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-resources-3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-utils-3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/shadows-core-3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/sqlite4java-0.282.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/vtd-xml-2.11.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/xmlpull-1.1.3.1.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/xpp3_min-1.1.4c.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/xstream-1.4.8.jar!/" />
</CLASSES>
<JAVADOC>
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-3.1-javadoc.jar!/" />
</JAVADOC>
<SOURCES>
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/maven-ant-tasks-2.1.3-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/robolectric/robolectric-3.1-sources.jar!/" />
</SOURCES>
</library>
</component>

View File

@@ -1,15 +1,13 @@
<component name="libraryTable">
<library name="uast-java">
<CLASSES>
<root url="jar://$PROJECT_DIR$/dependencies/uast-common.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/uast-java.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/uast-tests.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/lib/idea.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/lib/openapi.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$PROJECT_DIR$/dependencies/uast-common-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/uast-java-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/dependencies/uast-tests-sources.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/sources/sources.jar!/" />
<root url="jar://$PROJECT_DIR$/ideaSDK/sources/sources.jar!/" />
</SOURCES>
</library>
</component>

16
.idea/modules.xml generated
View File

@@ -9,11 +9,11 @@
<module fileurl="file://$PROJECT_DIR$/plugins/android-extensions/android-extensions-compiler/android-extensions-compiler.iml" filepath="$PROJECT_DIR$/plugins/android-extensions/android-extensions-compiler/android-extensions-compiler.iml" group="plugins/android-extensions" />
<module fileurl="file://$PROJECT_DIR$/plugins/android-extensions/android-extensions-idea/android-extensions-idea.iml" filepath="$PROJECT_DIR$/plugins/android-extensions/android-extensions-idea/android-extensions-idea.iml" group="plugins/android-extensions" />
<module fileurl="file://$PROJECT_DIR$/plugins/android-extensions/android-extensions-jps/android-extensions-jps.iml" filepath="$PROJECT_DIR$/plugins/android-extensions/android-extensions-jps/android-extensions-jps.iml" group="plugins/android-extensions" />
<module fileurl="file://$PROJECT_DIR$/plugins/android-extensions/android-extensions-runtime/android-extensions-runtime.iml" filepath="$PROJECT_DIR$/plugins/android-extensions/android-extensions-runtime/android-extensions-runtime.iml" group="plugins/android-extensions" />
<module fileurl="file://$PROJECT_DIR$/android-studio/android-studio.iml" filepath="$PROJECT_DIR$/android-studio/android-studio.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/compiler/android-tests/android-tests.iml" filepath="$PROJECT_DIR$/compiler/android-tests/android-tests.iml" group="compiler" />
<module fileurl="file://$PROJECT_DIR$/plugins/annotation-based-compiler-plugins-ide-support/annotation-based-compiler-plugins-ide-support.iml" filepath="$PROJECT_DIR$/plugins/annotation-based-compiler-plugins-ide-support/annotation-based-compiler-plugins-ide-support.iml" group="plugins" />
<module fileurl="file://$PROJECT_DIR$/plugins/annotation-collector/annotation-collector.iml" filepath="$PROJECT_DIR$/plugins/annotation-collector/annotation-collector.iml" group="plugins" />
<module fileurl="file://$PROJECT_DIR$/plugins/annotation-processing/annotation-processing.iml" filepath="$PROJECT_DIR$/plugins/annotation-processing/annotation-processing.iml" group="plugins" />
<module fileurl="file://$PROJECT_DIR$/ant/ant.iml" filepath="$PROJECT_DIR$/ant/ant.iml" />
<module fileurl="file://$PROJECT_DIR$/compiler/backend/backend.iml" filepath="$PROJECT_DIR$/compiler/backend/backend.iml" group="compiler/java" />
<module fileurl="file://$PROJECT_DIR$/compiler/backend-common/backend-common.iml" filepath="$PROJECT_DIR$/compiler/backend-common/backend-common.iml" group="compiler" />
@@ -51,7 +51,9 @@
<module fileurl="file://$PROJECT_DIR$/idea/idea-android/idea-android-output-parser/idea-android-output-parser.iml" filepath="$PROJECT_DIR$/idea/idea-android/idea-android-output-parser/idea-android-output-parser.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-completion/idea-completion.iml" filepath="$PROJECT_DIR$/idea/idea-completion/idea-completion.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-core/idea-core.iml" filepath="$PROJECT_DIR$/idea/idea-core/idea-core.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-gradle/idea-gradle.iml" filepath="$PROJECT_DIR$/idea/idea-gradle/idea-gradle.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-jps-common/idea-jps-common.iml" filepath="$PROJECT_DIR$/idea/idea-jps-common/idea-jps-common.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-jvm/idea-jvm.iml" filepath="$PROJECT_DIR$/idea/idea-jvm/idea-jvm.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-live-templates/idea-live-templates.iml" filepath="$PROJECT_DIR$/idea/idea-live-templates/idea-live-templates.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-maven/idea-maven.iml" filepath="$PROJECT_DIR$/idea/idea-maven/idea-maven.iml" group="ide" />
<module fileurl="file://$PROJECT_DIR$/idea/idea-repl/idea-repl.iml" filepath="$PROJECT_DIR$/idea/idea-repl/idea-repl.iml" group="ide" />
@@ -63,7 +65,6 @@
<module fileurl="file://$PROJECT_DIR$/compiler/ir/ir.psi2ir/ir.psi2ir.iml" filepath="$PROJECT_DIR$/compiler/ir/ir.psi2ir/ir.psi2ir.iml" group="compiler/ir" />
<module fileurl="file://$PROJECT_DIR$/compiler/ir/ir.tree/ir.tree.iml" filepath="$PROJECT_DIR$/compiler/ir/ir.tree/ir.tree.iml" group="compiler/ir" />
<module fileurl="file://$PROJECT_DIR$/j2k/j2k.iml" filepath="$PROJECT_DIR$/j2k/j2k.iml" group="j2k" />
<module fileurl="file://$PROJECT_DIR$/plugins/java-model-wrappers/java-model-wrappers.iml" filepath="$PROJECT_DIR$/plugins/java-model-wrappers/java-model-wrappers.iml" group="plugins" />
<module fileurl="file://$PROJECT_DIR$/compiler/javac-wrapper/javac-wrapper.iml" filepath="$PROJECT_DIR$/compiler/javac-wrapper/javac-wrapper.iml" group="compiler" />
<module fileurl="file://$PROJECT_DIR$/jps-plugin/jps-plugin.iml" filepath="$PROJECT_DIR$/jps-plugin/jps-plugin.iml" group="ide/jps" />
<module fileurl="file://$PROJECT_DIR$/jps-plugin/jps-tests/jps-tests.iml" filepath="$PROJECT_DIR$/jps-plugin/jps-tests/jps-tests.iml" group="ide/jps" />
@@ -76,14 +77,15 @@
<module fileurl="file://$PROJECT_DIR$/js/js.tests/js.tests.iml" filepath="$PROJECT_DIR$/js/js.tests/js.tests.iml" group="compiler/js" />
<module fileurl="file://$PROJECT_DIR$/js/js.translator/js.translator.iml" filepath="$PROJECT_DIR$/js/js.translator/js.translator.iml" group="compiler/js" />
<module fileurl="file://$PROJECT_DIR$/jps-plugin/kannotator-jps-plugin-test/kannotator-jps-plugin-test.iml" filepath="$PROJECT_DIR$/jps-plugin/kannotator-jps-plugin-test/kannotator-jps-plugin-test.iml" group="ide/jps" />
<module fileurl="file://$PROJECT_DIR$/plugins/kapt3/kapt3.iml" filepath="$PROJECT_DIR$/plugins/kapt3/kapt3.iml" />
<module fileurl="file://$PROJECT_DIR$/plugins/kapt3/kapt3.iml" filepath="$PROJECT_DIR$/plugins/kapt3/kapt3.iml" group="plugins" />
<module fileurl="file://$PROJECT_DIR$/plugins/kapt3-idea/kapt3-idea.iml" filepath="$PROJECT_DIR$/plugins/kapt3-idea/kapt3-idea.iml" />
<module fileurl="file://$PROJECT_DIR$/idea/kotlin-gradle-tooling/kotlin-gradle-tooling.iml" filepath="$PROJECT_DIR$/idea/kotlin-gradle-tooling/kotlin-gradle-tooling.iml" />
<module fileurl="file://$PROJECT_DIR$/compiler/light-classes/light-classes.iml" filepath="$PROJECT_DIR$/compiler/light-classes/light-classes.iml" group="compiler/java" />
<module fileurl="file://$PROJECT_DIR$/plugins/lint/lint-api/lint-api.iml" filepath="$PROJECT_DIR$/plugins/lint/lint-api/lint-api.iml" group="plugins/lint" />
<module fileurl="file://$PROJECT_DIR$/plugins/lint/lint-checks/lint-checks.iml" filepath="$PROJECT_DIR$/plugins/lint/lint-checks/lint-checks.iml" group="plugins/lint" />
<module fileurl="file://$PROJECT_DIR$/plugins/lint/lint-idea/lint-idea.iml" filepath="$PROJECT_DIR$/plugins/lint/lint-idea/lint-idea.iml" group="plugins/lint" />
<module fileurl="file://$PROJECT_DIR$/plugins/noarg/noarg-cli/noarg-cli.iml" filepath="$PROJECT_DIR$/plugins/noarg/noarg-cli/noarg-cli.iml" />
<module fileurl="file://$PROJECT_DIR$/plugins/noarg/noarg-ide/noarg-ide.iml" filepath="$PROJECT_DIR$/plugins/noarg/noarg-ide/noarg-ide.iml" />
<module fileurl="file://$PROJECT_DIR$/plugins/noarg/noarg-cli/noarg-cli.iml" filepath="$PROJECT_DIR$/plugins/noarg/noarg-cli/noarg-cli.iml" group="plugins/noarg" />
<module fileurl="file://$PROJECT_DIR$/plugins/noarg/noarg-ide/noarg-ide.iml" filepath="$PROJECT_DIR$/plugins/noarg/noarg-ide/noarg-ide.iml" group="plugins/noarg" />
<module fileurl="file://$PROJECT_DIR$/non-compiler-tests/non-compiler-tests.iml" filepath="$PROJECT_DIR$/non-compiler-tests/non-compiler-tests.iml" />
<module fileurl="file://$PROJECT_DIR$/compiler/plugin-api/plugin-api.iml" filepath="$PROJECT_DIR$/compiler/plugin-api/plugin-api.iml" group="compiler" />
<module fileurl="file://$PROJECT_DIR$/plugins/plugins-tests/plugins-tests.iml" filepath="$PROJECT_DIR$/plugins/plugins-tests/plugins-tests.iml" group="plugins" />
@@ -91,8 +93,8 @@
<module fileurl="file://$PROJECT_DIR$/core/reflection.jvm/reflection.jvm.iml" filepath="$PROJECT_DIR$/core/reflection.jvm/reflection.jvm.iml" group="core" />
<module fileurl="file://$PROJECT_DIR$/compiler/resolution/resolution.iml" filepath="$PROJECT_DIR$/compiler/resolution/resolution.iml" group="compiler" />
<module fileurl="file://$PROJECT_DIR$/core/runtime.jvm/runtime.jvm.iml" filepath="$PROJECT_DIR$/core/runtime.jvm/runtime.jvm.iml" group="core" />
<module fileurl="file://$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-cli/sam-with-receiver-cli.iml" filepath="$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-cli/sam-with-receiver-cli.iml" />
<module fileurl="file://$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-ide/sam-with-receiver-ide.iml" filepath="$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-ide/sam-with-receiver-ide.iml" />
<module fileurl="file://$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-cli/sam-with-receiver-cli.iml" filepath="$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-cli/sam-with-receiver-cli.iml" group="plugins/sam-with-receiver" />
<module fileurl="file://$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-ide/sam-with-receiver-ide.iml" filepath="$PROJECT_DIR$/plugins/sam-with-receiver/sam-with-receiver-ide/sam-with-receiver-ide.iml" group="plugins/sam-with-receiver" />
<module fileurl="file://$PROJECT_DIR$/core/script.runtime/script.runtime.iml" filepath="$PROJECT_DIR$/core/script.runtime/script.runtime.iml" group="core" />
<module fileurl="file://$PROJECT_DIR$/compiler/serialization/serialization.iml" filepath="$PROJECT_DIR$/compiler/serialization/serialization.iml" group="compiler" />
<module fileurl="file://$PROJECT_DIR$/plugins/source-sections/source-sections-compiler/source-sections-compiler.iml" filepath="$PROJECT_DIR$/plugins/source-sections/source-sections-compiler/source-sections-compiler.iml" group="plugins" />

View File

@@ -8,7 +8,7 @@
</extension>
<module name="compiler-tests" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="true" />
<option name="ALTERNATIVE_JRE_PATH" value="9-ea" />
<option name="ALTERNATIVE_JRE_PATH" value="9" />
<option name="PACKAGE_NAME" value="org.jetbrains.kotlin.codegen" />
<option name="MAIN_CLASS_NAME" value="org.jetbrains.kotlin.codegen.CodegenJdkCommonTestSuite" />
<option name="METHOD_NAME" value="" />

View File

@@ -8,7 +8,7 @@
</extension>
<module name="compiler-tests" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="true" />
<option name="ALTERNATIVE_JRE_PATH" value="9-ea" />
<option name="ALTERNATIVE_JRE_PATH" value="9" />
<option name="PACKAGE_NAME" value="org.jetbrains.kotlin.codegen" />
<option name="MAIN_CLASS_NAME" value="org.jetbrains.kotlin.codegen.CodegenJdkCommonTestSuite" />
<option name="METHOD_NAME" value="" />

View File

@@ -8,7 +8,7 @@
</extension>
<module name="compiler-tests" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="true" />
<option name="ALTERNATIVE_JRE_PATH" value="9-ea" />
<option name="ALTERNATIVE_JRE_PATH" value="9" />
<option name="PACKAGE_NAME" value="org.jetbrains.kotlin.codegen" />
<option name="MAIN_CLASS_NAME" value="org.jetbrains.kotlin.codegen.CodegenJdkCommonTestSuite" />
<option name="METHOD_NAME" value="" />

View File

@@ -3,7 +3,7 @@
<log_file path="$PROJECT_DIR$/ideaSDK/system-idea/log/idea.log" checked="true" skipped="true" show_all="false" alias="idea.log" />
<extension name="coverage" enabled="false" merge="false" sample_coverage="true" runner="idea" />
<option name="MAIN_CLASS_NAME" value="com.intellij.idea.Main" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=128m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=240m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="PROGRAM_PARAMETERS" value="" />
<option name="WORKING_DIRECTORY" value="file://$PROJECT_DIR$/ideaSDK/bin" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="false" />

View File

@@ -3,7 +3,7 @@
<log_file path="$PROJECT_DIR$/ideaSDK/system-idea/log/idea.log" checked="true" skipped="true" show_all="false" alias="idea.log" />
<extension name="coverage" enabled="false" merge="false" sample_coverage="true" runner="idea" />
<option name="MAIN_CLASS_NAME" value="com.intellij.idea.Main" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=128m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Didea.ProcessCanceledException=disabled -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=240m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Didea.ProcessCanceledException=disabled -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="PROGRAM_PARAMETERS" value="" />
<option name="WORKING_DIRECTORY" value="file://$PROJECT_DIR$/ideaSDK/bin" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="false" />

View File

@@ -8,7 +8,7 @@
</extension>
<module name="compiler-tests-java8" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="true" />
<option name="ALTERNATIVE_JRE_PATH" value="9-ea" />
<option name="ALTERNATIVE_JRE_PATH" value="9" />
<option name="PACKAGE_NAME" value="org.jetbrains.kotlin" />
<option name="MAIN_CLASS_NAME" value="" />
<option name="METHOD_NAME" value="" />

View File

@@ -2,7 +2,7 @@
<configuration default="false" name="Update-Dist-Run" type="Application" factoryName="Application" singleton="true">
<extension name="coverage" enabled="false" merge="false" sample_coverage="true" runner="idea" />
<option name="MAIN_CLASS_NAME" value="com.intellij.idea.Main" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=64m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="VM_PARAMETERS" value="-Xmx1250m -XX:ReservedCodeCacheSize=240m -XX:+HeapDumpOnOutOfMemoryError -ea -Didea.is.internal=true -Didea.debug.mode=true -Didea.system.path=../system-idea -Didea.config.path=../config-idea -Dapple.laf.useScreenMenuBar=true -Dapple.awt.graphics.UseQuartz=true -Dsun.io.useCanonCaches=false -Dplugin.path=$PROJECT_DIR$/out/artifacts/Kotlin -Dkotlin.internal.mode.enabled=true -Didea.additional.classpath=../idea-kotlin-runtime/kotlin-runtime.jar,../idea-kotlin-runtime/kotlin-reflect.jar" />
<option name="PROGRAM_PARAMETERS" value="" />
<option name="WORKING_DIRECTORY" value="file://$PROJECT_DIR$/ideaSDK/bin" />
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="false" />

File diff suppressed because it is too large Load Diff

View File

@@ -26,10 +26,14 @@
<excludeFolder url="file://$MODULE_DIR$/libraries/examples/kotlin-jsr223-local-example/target" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/common/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/js/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/js/it/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/js/it/node_modules" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/junit/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/kotlin.test/jvm/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/common/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/jdk7/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/jdk8/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/jre7/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/jre8/build" />
<excludeFolder url="file://$MODULE_DIR$/libraries/stdlib/js/build" />

View File

@@ -1,3 +1,4 @@
[![official project](http://jb.gg/badges/official.svg)](https://confluence.jetbrains.com/display/ALL/JetBrains+on+GitHub)
<a href="http://slack.kotlinlang.org/"><img src="http://slack.kotlinlang.org/badge.svg" height="20"></a>
[![TeamCity (simple build status)](https://img.shields.io/teamcity/http/teamcity.jetbrains.com/s/bt345.svg)](https://teamcity.jetbrains.com/viewType.html?buildTypeId=bt345&branch_Kotlin=%3Cdefault%3E&tab=buildTypeStatusDiv)
[![Maven Central](https://img.shields.io/maven-central/v/org.jetbrains.kotlin/kotlin-maven-plugin.svg)](http://search.maven.org/#search%7Cga%7C1%7Cg%3A%22org.jetbrains.kotlin%22)
@@ -37,6 +38,8 @@ In order to build Kotlin distribution you need to have:
JDK_17="path to JDK 1.7"
JDK_18="path to JDK 1.8"
> Note: The JDK 6 for MacOS is not available on Oracle's site. You can [download it here](https://support.apple.com/kb/DL1572).
## Building
To build this project, first time you try to build you need to run this:
@@ -113,7 +116,7 @@ From this root project there are Run/Debug Configurations for running IDEA or th
We love contributions! There's [lots to do on Kotlin](https://youtrack.jetbrains.com/issues/KT) and on the
[standard library](https://youtrack.jetbrains.com/issues/KT?q=%23Kotlin%20%23Unresolved%20and%20(links:%20KT-2554,%20KT-4089%20or%20%23Libraries)) so why not chat with us
about what you're interested in doing? Please join the #kontributors channel in [our Slack chat](http://kotlinslackin.herokuapp.com/)
about what you're interested in doing? Please join the #kontributors channel in [our Slack chat](http://slack.kotlinlang.org/)
and let us know about your plans.
If you want to find some issues to start off with, try [this query](https://youtrack.jetbrains.com/issues/KT?q=tag:%20%7BUp%20For%20Grabs%7D%20%23Unresolved) which should find all Kotlin issues that marked as "up-for-grabs".

View File

@@ -39,9 +39,7 @@ class KotlinCompilerAdapter : Javac13() {
return argument
}
override fun getSupportedFileExtensions(): Array<String> {
return super.getSupportedFileExtensions() + KOTLIN_EXTENSIONS
}
override fun getSupportedFileExtensions(): Array<String> = super.getSupportedFileExtensions() + KOTLIN_EXTENSIONS
@Throws(BuildException::class)
override fun execute(): Boolean {

View File

@@ -15,5 +15,7 @@
<orderEntry type="module" module-name="tests-common" scope="TEST" />
<orderEntry type="library" scope="TEST" name="idea-full" level="project" />
<orderEntry type="library" name="kotlin-reflect" level="project" />
<orderEntry type="module" module-name="js.serializer" />
<orderEntry type="module" module-name="js.frontend" />
</component>
</module>

View File

@@ -21,17 +21,15 @@ import org.jetbrains.kotlin.load.kotlin.ModuleMapping
import org.jetbrains.kotlin.utils.sure
import java.io.File
open class GeneratedFile<Target>(
val target: Target,
val sourceFiles: Collection<File>,
val outputFile: File
open class GeneratedFile(
val sourceFiles: Collection<File>,
val outputFile: File
)
class GeneratedJvmClass<Target> (
target: Target,
class GeneratedJvmClass (
sourceFiles: Collection<File>,
outputFile: File
) : GeneratedFile<Target>(target, sourceFiles, outputFile) {
) : GeneratedFile(sourceFiles, outputFile) {
val outputClass = LocalFileKotlinClass.create(outputFile).sure {
"Couldn't load KotlinClass from $outputFile; it may happen because class doesn't have valid Kotlin annotations"
}

View File

@@ -16,13 +16,21 @@
package org.jetbrains.kotlin.compilerRunner;
import com.intellij.util.containers.ContainerUtil;
import kotlin.jvm.JvmClassMappingKt;
import kotlin.reflect.KClass;
import kotlin.reflect.KProperty1;
import kotlin.reflect.KVisibility;
import kotlin.reflect.full.KClasses;
import kotlin.reflect.jvm.ReflectJvmMapping;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.cli.common.arguments.Argument;
import org.jetbrains.kotlin.cli.common.arguments.CommonToolArguments;
import org.jetbrains.kotlin.cli.common.arguments.ParseCommandLineArgumentsKt;
import org.jetbrains.kotlin.utils.StringsKt;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
@@ -33,39 +41,35 @@ public class ArgumentUtils {
@NotNull
public static List<String> convertArgumentsToStringList(@NotNull CommonToolArguments arguments)
throws InstantiationException, IllegalAccessException {
throws InstantiationException, IllegalAccessException, InvocationTargetException {
List<String> result = new ArrayList<>();
convertArgumentsToStringList(arguments, arguments.getClass().newInstance(), arguments.getClass(), result);
result.addAll(arguments.freeArgs);
Class<? extends CommonToolArguments> argumentsClass = arguments.getClass();
convertArgumentsToStringList(arguments, argumentsClass.newInstance(), JvmClassMappingKt.getKotlinClass(argumentsClass), result);
result.addAll(arguments.getFreeArgs());
return result;
}
@SuppressWarnings("unchecked")
private static void convertArgumentsToStringList(
@NotNull CommonToolArguments arguments,
@NotNull CommonToolArguments defaultArguments,
@NotNull Class<?> clazz,
@NotNull KClass<?> clazz,
@NotNull List<String> result
) throws IllegalAccessException, InstantiationException {
for (Field field : clazz.getDeclaredFields()) {
Argument argument = field.getAnnotation(Argument.class);
) throws IllegalAccessException, InstantiationException, InvocationTargetException {
for (KProperty1 property : KClasses.getMemberProperties(clazz)) {
Argument argument = ContainerUtil.findInstance(property.getAnnotations(), Argument.class);
if (argument == null) continue;
Object value;
Object defaultValue;
try {
value = field.get(arguments);
defaultValue = field.get(defaultArguments);
}
catch (IllegalAccessException ignored) {
// skip this field
continue;
}
if (property.getVisibility() != KVisibility.PUBLIC) continue;
Object value = property.get(arguments);
Object defaultValue = property.get(defaultArguments);
if (value == null || Objects.equals(value, defaultValue)) continue;
Class<?> fieldType = field.getType();
Type propertyJavaType = ReflectJvmMapping.getJavaType(property.getReturnType());
if (fieldType.isArray()) {
if (propertyJavaType instanceof Class && ((Class) propertyJavaType).isArray()) {
Object[] values = (Object[]) value;
if (values.length == 0) continue;
value = StringsKt.join(Arrays.asList(values), ",");
@@ -73,7 +77,7 @@ public class ArgumentUtils {
result.add(argument.value());
if (fieldType == boolean.class || fieldType == Boolean.class) continue;
if (propertyJavaType == boolean.class || propertyJavaType == Boolean.class) continue;
if (ParseCommandLineArgumentsKt.isAdvanced(argument)) {
result.set(result.size() - 1, argument.value() + "=" + value.toString());
@@ -82,10 +86,5 @@ public class ArgumentUtils {
result.add(value.toString());
}
}
Class<?> superClazz = clazz.getSuperclass();
if (superClazz != null) {
convertArgumentsToStringList(arguments, defaultArguments, superClazz, result);
}
}
}

View File

@@ -0,0 +1,35 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.compilerRunner
import org.jetbrains.kotlin.cli.common.messages.CompilerMessageLocation
import org.jetbrains.kotlin.cli.common.messages.CompilerMessageSeverity
import org.jetbrains.kotlin.cli.common.messages.MessageCollector
import org.jetbrains.kotlin.cli.common.messages.OutputMessageUtil
class MessageCollectorToOutputItemsCollectorAdapter(
private val delegate: MessageCollector,
private val outputCollector: OutputItemsCollector
) : MessageCollector by delegate {
override fun report(severity: CompilerMessageSeverity, message: String, location: CompilerMessageLocation?) {
// TODO: consider adding some other way of passing input -> output mapping from compiler, e.g. dedicated service
OutputMessageUtil.parseOutputMessage(message)?.let {
outputCollector.add(it.sourceFiles, it.outputFile)
}
delegate.report(severity, message, location)
}
}

View File

@@ -1,47 +0,0 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.compilerRunner;
import org.jetbrains.annotations.NotNull;
import java.io.File;
import java.util.Collection;
public class SimpleOutputItem {
private final Collection<File> sourceFiles;
private final File outputFile;
public SimpleOutputItem(@NotNull Collection<File> sourceFiles, @NotNull File outputFile) {
this.sourceFiles = sourceFiles;
this.outputFile = outputFile;
}
@NotNull
public Collection<File> getSourceFiles() {
return sourceFiles;
}
@NotNull
public File getOutputFile() {
return outputFile;
}
@Override
public String toString() {
return sourceFiles + " -> " + outputFile;
}
}

View File

@@ -0,0 +1,32 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.compilerRunner
import org.jetbrains.kotlin.build.GeneratedFile
import org.jetbrains.kotlin.build.GeneratedJvmClass
import java.io.File
data class SimpleOutputItem(val sourceFiles: Collection<File>, val outputFile: File) {
override fun toString(): String =
"$sourceFiles->$outputFile"
}
fun SimpleOutputItem.toGeneratedFile(): GeneratedFile =
when {
outputFile.name.endsWith(".class") -> GeneratedJvmClass(sourceFiles, outputFile)
else -> GeneratedFile(sourceFiles, outputFile)
}

View File

@@ -24,11 +24,9 @@ import java.io.File
import java.io.IOException
private val NORMAL_VERSION = 8
private val EXPERIMENTAL_VERSION = 4
private val DATA_CONTAINER_VERSION = 2
private val NORMAL_VERSION_FILE_NAME = "format-version.txt"
private val EXPERIMENTAL_VERSION_FILE_NAME = "experimental-format-version.txt"
private val DATA_CONTAINER_VERSION_FILE_NAME = "data-container-format-version.txt"
class CacheVersion(
@@ -92,32 +90,23 @@ class CacheVersion(
REBUILD_ALL_KOTLIN,
REBUILD_CHUNK,
CLEAN_NORMAL_CACHES,
CLEAN_EXPERIMENTAL_CACHES,
CLEAN_DATA_CONTAINER,
DO_NOTHING
}
}
fun normalCacheVersion(dataRoot: File): CacheVersion =
fun normalCacheVersion(dataRoot: File, enabled: Boolean? = null): CacheVersion =
CacheVersion(ownVersion = NORMAL_VERSION,
versionFile = File(dataRoot, NORMAL_VERSION_FILE_NAME),
whenVersionChanged = CacheVersion.Action.REBUILD_CHUNK,
whenTurnedOn = CacheVersion.Action.REBUILD_CHUNK,
whenTurnedOff = CacheVersion.Action.CLEAN_NORMAL_CACHES,
isEnabled = { IncrementalCompilation.isEnabled() })
isEnabled = { enabled ?: IncrementalCompilation.isEnabled() })
fun experimentalCacheVersion(dataRoot: File): CacheVersion =
CacheVersion(ownVersion = EXPERIMENTAL_VERSION,
versionFile = File(dataRoot, EXPERIMENTAL_VERSION_FILE_NAME),
whenVersionChanged = CacheVersion.Action.REBUILD_CHUNK,
whenTurnedOn = CacheVersion.Action.REBUILD_CHUNK,
whenTurnedOff = CacheVersion.Action.CLEAN_EXPERIMENTAL_CACHES,
isEnabled = { IncrementalCompilation.isExperimental() })
fun dataContainerCacheVersion(dataRoot: File): CacheVersion =
fun dataContainerCacheVersion(dataRoot: File, enabled: Boolean? = null): CacheVersion =
CacheVersion(ownVersion = DATA_CONTAINER_VERSION,
versionFile = File(dataRoot, DATA_CONTAINER_VERSION_FILE_NAME),
whenVersionChanged = CacheVersion.Action.REBUILD_ALL_KOTLIN,
whenTurnedOn = CacheVersion.Action.REBUILD_ALL_KOTLIN,
whenTurnedOff = CacheVersion.Action.CLEAN_DATA_CONTAINER,
isEnabled = { IncrementalCompilation.isExperimental() })
isEnabled = { enabled ?: IncrementalCompilation.isEnabled() })

View File

@@ -0,0 +1,189 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.incremental
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.protobuf.MessageLite
import org.jetbrains.kotlin.serialization.Flags
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
class ChangesCollector {
private val removedMembers = hashMapOf<FqName, MutableSet<String>>()
private val changedMembers = hashMapOf<FqName, MutableSet<String>>()
private val areSubclassesAffected = hashMapOf<FqName, Boolean>()
fun changes(): List<ChangeInfo> {
val changes = arrayListOf<ChangeInfo>()
for ((fqName, members) in removedMembers) {
if (members.isNotEmpty()) {
changes.add(ChangeInfo.Removed(fqName, members))
}
}
for ((fqName, members) in changedMembers) {
if (members.isNotEmpty()) {
changes.add(ChangeInfo.MembersChanged(fqName, members))
}
}
for ((fqName, areSubclassesAffected) in areSubclassesAffected) {
changes.add(ChangeInfo.SignatureChanged(fqName, areSubclassesAffected))
}
return changes
}
private fun <T, R> MutableMap<T, MutableSet<R>>.getSet(key: T) =
getOrPut(key) { HashSet() }
private fun collectChangedMember(scope: FqName, name: String) {
changedMembers.getSet(scope).add(name)
}
private fun collectRemovedMember(scope: FqName, name: String) {
removedMembers.getSet(scope).add(name)
}
private fun collectChangedMembers(scope: FqName, names: Collection<String>) {
if (names.isNotEmpty()) {
changedMembers.getSet(scope).addAll(names)
}
}
private fun collectRemovedMembers(scope: FqName, names: Collection<String>) {
if (names.isNotEmpty()) {
removedMembers.getSet(scope).addAll(names)
}
}
fun collectProtoChanges(oldData: ProtoData?, newData: ProtoData?) {
if (oldData == null && newData == null) {
throw IllegalStateException("Old and new value are null")
}
if (oldData == null) {
newData!!.collectAll(isRemoved = false)
return
}
if (newData == null) {
oldData.collectAll(isRemoved = true)
return
}
when (oldData) {
is ClassProtoData -> {
when (newData) {
is ClassProtoData -> {
val fqName = oldData.nameResolver.getClassId(oldData.proto.fqName).asSingleFqName()
val diff = DifferenceCalculatorForClass(oldData, newData).difference()
if (diff.isClassAffected) {
collectSignature(oldData, diff.areSubclassesAffected)
}
collectChangedMembers(fqName, diff.changedMembersNames)
}
is PackagePartProtoData -> {
collectSignature(oldData, areSubclassesAffected = true)
}
}
}
is PackagePartProtoData -> {
when (newData) {
is ClassProtoData -> {
collectSignature(newData, areSubclassesAffected = false)
}
is PackagePartProtoData -> {
val diff = DifferenceCalculatorForPackageFacade(oldData, newData).difference()
collectChangedMembers(oldData.packageFqName, diff.changedMembersNames)
}
}
}
}
}
private fun <T> T.getNonPrivateNames(nameResolver: NameResolver, vararg members: T.() -> List<MessageLite>): Set<String> =
members.flatMap { this.it().filterNot { it.isPrivate }.names(nameResolver) }.toSet()
private fun ProtoData.collectAll(isRemoved: Boolean) =
when (this) {
is PackagePartProtoData -> collectAllFromPackage(isRemoved)
is ClassProtoData -> collectAllFromClass(isRemoved)
}
private fun PackagePartProtoData.collectAllFromPackage(isRemoved: Boolean) {
val memberNames =
proto.getNonPrivateNames(
nameResolver,
ProtoBuf.Package::getFunctionList,
ProtoBuf.Package::getPropertyList
)
if (isRemoved) {
collectRemovedMembers(packageFqName, memberNames)
}
else {
collectChangedMembers(packageFqName, memberNames)
}
}
private fun ClassProtoData.collectAllFromClass(isRemoved: Boolean) {
val classFqName = nameResolver.getClassId(proto.fqName).asSingleFqName()
val kind = Flags.CLASS_KIND.get(proto.flags)
if (kind == ProtoBuf.Class.Kind.COMPANION_OBJECT) {
val memberNames =
proto.getNonPrivateNames(
nameResolver,
ProtoBuf.Class::getConstructorList,
ProtoBuf.Class::getFunctionList,
ProtoBuf.Class::getPropertyList
) + proto.enumEntryList.map { nameResolver.getString(it.name) }
val collectMember = if (isRemoved) this@ChangesCollector::collectRemovedMember else this@ChangesCollector::collectChangedMember
collectMember(classFqName.parent(), classFqName.shortName().asString())
memberNames.forEach { collectMember(classFqName, it) }
}
else {
collectSignature(classFqName, areSubclassesAffected = true)
}
}
fun collectMemberIfValueWasChanged(scope: FqName, name: String, oldValue: Any?, newValue: Any?) {
if (oldValue == null && newValue == null) {
throw IllegalStateException("Old and new value are null for $scope#$name")
}
if (oldValue != null && newValue == null) {
collectRemovedMember(scope, name)
}
else if (oldValue != newValue) {
collectChangedMember(scope, name)
}
}
private fun collectSignature(classData: ClassProtoData, areSubclassesAffected: Boolean) {
val fqName = classData.nameResolver.getClassId(classData.proto.fqName).asSingleFqName()
collectSignature(fqName, areSubclassesAffected)
}
fun collectSignature(fqName: FqName, areSubclassesAffected: Boolean) {
val prevValue = this.areSubclassesAffected[fqName] ?: false
this.areSubclassesAffected[fqName] = prevValue || areSubclassesAffected
}
}

View File

@@ -0,0 +1,119 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.incremental
import com.intellij.util.io.EnumeratorStringDescriptor
import org.jetbrains.kotlin.incremental.storage.*
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
import org.jetbrains.kotlin.serialization.deserialization.supertypes
import java.io.File
/**
* Incremental cache common for JVM and JS
*/
abstract class IncrementalCacheCommon(workingDir: File) : BasicMapsOwner(workingDir) {
companion object {
private val SUBTYPES = "subtypes"
private val SUPERTYPES = "supertypes"
private val CLASS_FQ_NAME_TO_SOURCE = "class-fq-name-to-source"
}
private val dependents = arrayListOf<IncrementalCacheCommon>()
fun addDependentCache(cache: IncrementalCacheCommon) {
dependents.add(cache)
}
val thisWithDependentCaches: Iterable<IncrementalCacheCommon> by lazy {
val result = arrayListOf(this)
result.addAll(dependents)
result
}
private val subtypesMap = registerMap(SubtypesMap(SUBTYPES.storageFile))
private val supertypesMap = registerMap(SupertypesMap(SUPERTYPES.storageFile))
protected val classFqNameToSourceMap = registerMap(ClassFqNameToSourceMap(CLASS_FQ_NAME_TO_SOURCE.storageFile))
fun getSubtypesOf(className: FqName): Sequence<FqName> =
subtypesMap[className].asSequence()
fun getSourceFileIfClass(fqName: FqName): File? =
classFqNameToSourceMap[fqName]
abstract fun markDirty(removedAndCompiledSources: List<File>)
protected fun addToClassStorage(proto: ProtoBuf.Class, nameResolver: NameResolver, srcFile: File) {
val supertypes = proto.supertypes(TypeTable(proto.typeTable))
val parents = supertypes.map { nameResolver.getClassId(it.className).asSingleFqName() }
.filter { it.asString() != "kotlin.Any" }
.toSet()
val child = nameResolver.getClassId(proto.fqName).asSingleFqName()
parents.forEach { subtypesMap.add(it, child) }
val removedSupertypes = supertypesMap[child].filter { it !in parents }
removedSupertypes.forEach { subtypesMap.removeValues(it, setOf(child)) }
supertypesMap[child] = parents
classFqNameToSourceMap[child] = srcFile
}
protected fun removeAllFromClassStorage(removedClasses: Collection<FqName>) {
if (removedClasses.isEmpty()) return
val removedFqNames = removedClasses.toSet()
for (cache in thisWithDependentCaches) {
val parentsFqNames = hashSetOf<FqName>()
val childrenFqNames = hashSetOf<FqName>()
for (removedFqName in removedFqNames) {
parentsFqNames.addAll(cache.supertypesMap[removedFqName])
childrenFqNames.addAll(cache.subtypesMap[removedFqName])
cache.supertypesMap.remove(removedFqName)
cache.subtypesMap.remove(removedFqName)
}
for (child in childrenFqNames) {
cache.supertypesMap.removeValues(child, removedFqNames)
}
for (parent in parentsFqNames) {
cache.subtypesMap.removeValues(parent, removedFqNames)
}
}
removedFqNames.forEach { classFqNameToSourceMap.remove(it) }
}
protected class ClassFqNameToSourceMap(storageFile: File) : BasicStringMap<String>(storageFile, EnumeratorStringDescriptor(), PathStringDescriptor) {
operator fun set(fqName: FqName, sourceFile: File) {
storage[fqName.asString()] = sourceFile.canonicalPath
}
operator fun get(fqName: FqName): File? =
storage[fqName.asString()]?.let(::File)
fun remove(fqName: FqName) {
storage.remove(fqName.asString())
}
override fun dumpValue(value: String) = value
}
}

View File

@@ -1,834 +0,0 @@
/*
* Copyright 2010-2016 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.incremental
import com.intellij.openapi.util.io.FileUtil
import com.intellij.openapi.util.io.FileUtil.toSystemIndependentName
import com.intellij.util.SmartList
import com.intellij.util.io.BooleanDataDescriptor
import com.intellij.util.io.EnumeratorStringDescriptor
import gnu.trove.THashSet
import org.jetbrains.annotations.TestOnly
import org.jetbrains.kotlin.build.GeneratedJvmClass
import org.jetbrains.kotlin.config.IncrementalCompilation
import org.jetbrains.kotlin.incremental.ChangeInfo.MembersChanged
import org.jetbrains.kotlin.incremental.ChangeInfo.Removed
import org.jetbrains.kotlin.incremental.storage.*
import org.jetbrains.kotlin.inline.inlineFunctionsJvmNames
import org.jetbrains.kotlin.load.kotlin.ModuleMapping
import org.jetbrains.kotlin.load.kotlin.header.KotlinClassHeader
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCache
import org.jetbrains.kotlin.load.kotlin.incremental.components.JvmPackagePartProto
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.protobuf.MessageLite
import org.jetbrains.kotlin.resolve.jvm.JvmClassName
import org.jetbrains.kotlin.serialization.Flags
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.serialization.deserialization.TypeTable
import org.jetbrains.kotlin.serialization.deserialization.supertypes
import org.jetbrains.kotlin.serialization.jvm.BitEncoding
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBufUtil
import org.jetbrains.org.objectweb.asm.*
import java.io.File
import java.security.MessageDigest
import java.util.*
val KOTLIN_CACHE_DIRECTORY_NAME = "kotlin"
open class IncrementalCacheImpl<Target>(
private val targetDataRoot: File,
targetOutputDir: File?,
target: Target
) : BasicMapsOwner(), IncrementalCache {
companion object {
private val PROTO_MAP = "proto"
private val CONSTANTS_MAP = "constants"
private val PACKAGE_PARTS = "package-parts"
private val MULTIFILE_CLASS_FACADES = "multifile-class-facades"
private val MULTIFILE_CLASS_PARTS = "multifile-class-parts"
private val SOURCE_TO_CLASSES = "source-to-classes"
private val DIRTY_OUTPUT_CLASSES = "dirty-output-classes"
private val INLINE_FUNCTIONS = "inline-functions"
private val SUBTYPES = "subtypes"
private val SUPERTYPES = "supertypes"
private val CLASS_FQ_NAME_TO_SOURCE = "class-fq-name-to-source"
private val INTERNAL_NAME_TO_SOURCE = "internal-name-to-source"
private val MODULE_MAPPING_FILE_NAME = "." + ModuleMapping.MAPPING_FILE_EXT
}
private val baseDir = File(targetDataRoot, KOTLIN_CACHE_DIRECTORY_NAME)
private val experimentalMaps = arrayListOf<BasicMap<*, *>>()
private fun <K, V, M : BasicMap<K, V>> registerExperimentalMap(map: M): M {
experimentalMaps.add(map)
return registerMap(map)
}
protected val String.storageFile: File
get() = File(baseDir, this + "." + CACHE_EXTENSION)
private val protoMap = registerMap(ProtoMap(PROTO_MAP.storageFile))
private val constantsMap = registerMap(ConstantsMap(CONSTANTS_MAP.storageFile))
private val packagePartMap = registerMap(PackagePartMap(PACKAGE_PARTS.storageFile))
private val multifileFacadeToParts = registerMap(MultifileClassFacadeMap(MULTIFILE_CLASS_FACADES.storageFile))
private val partToMultifileFacade = registerMap(MultifileClassPartMap(MULTIFILE_CLASS_PARTS.storageFile))
private val sourceToClassesMap = registerMap(SourceToClassesMap(SOURCE_TO_CLASSES.storageFile))
private val dirtyOutputClassesMap = registerMap(DirtyOutputClassesMap(DIRTY_OUTPUT_CLASSES.storageFile))
private val inlineFunctionsMap = registerMap(InlineFunctionsMap(INLINE_FUNCTIONS.storageFile))
private val subtypesMap = registerExperimentalMap(SubtypesMap(SUBTYPES.storageFile))
private val supertypesMap = registerExperimentalMap(SupertypesMap(SUPERTYPES.storageFile))
private val classFqNameToSourceMap = registerExperimentalMap(ClassFqNameToSourceMap(CLASS_FQ_NAME_TO_SOURCE.storageFile))
// todo: try to use internal names only?
private val internalNameToSource = registerExperimentalMap(InternalNameToSourcesMap(INTERNAL_NAME_TO_SOURCE.storageFile))
private val dependents = arrayListOf<IncrementalCacheImpl<Target>>()
private val outputDir by lazy(LazyThreadSafetyMode.NONE) { requireNotNull(targetOutputDir) { "Target is expected to have output directory: $target" } }
val thisWithDependentCaches: Iterable<IncrementalCacheImpl<Target>> by lazy {
val result = arrayListOf(this)
result.addAll(dependents)
result
}
override fun registerInline(fromPath: String, jvmSignature: String, toPath: String) {
}
protected open fun debugLog(message: String) {}
fun addDependentCache(cache: IncrementalCacheImpl<Target>) {
dependents.add(cache)
}
fun markOutputClassesDirty(removedAndCompiledSources: List<File>) {
for (sourceFile in removedAndCompiledSources) {
val classes = sourceToClassesMap[sourceFile]
classes.forEach {
dirtyOutputClassesMap.markDirty(it.internalName)
}
sourceToClassesMap.clearOutputsForSource(sourceFile)
}
}
// used in gradle
@Suppress("unused")
fun classesBySources(sources: Iterable<File>): Iterable<JvmClassName> =
sources.flatMap { sourceToClassesMap[it] }
fun getSubtypesOf(className: FqName): Sequence<FqName> =
subtypesMap[className].asSequence()
fun getSourceFileIfClass(fqName: FqName): File? =
classFqNameToSourceMap[fqName]
fun sourcesByInternalName(internalName: String): Collection<File> =
internalNameToSource[internalName]
fun isMultifileFacade(className: JvmClassName): Boolean =
className.internalName in multifileFacadeToParts
override fun getClassFilePath(internalClassName: String): String {
return toSystemIndependentName(File(outputDir, "$internalClassName.class").canonicalPath)
}
fun saveModuleMappingToCache(sourceFiles: Collection<File>, file: File): CompilationResult {
val jvmClassName = JvmClassName.byInternalName(MODULE_MAPPING_FILE_NAME)
protoMap.process(jvmClassName, file.readBytes(), emptyArray<String>(), isPackage = false, checkChangesIsOpenPart = false)
dirtyOutputClassesMap.notDirty(MODULE_MAPPING_FILE_NAME)
sourceFiles.forEach { sourceToClassesMap.add(it, jvmClassName) }
return CompilationResult.NO_CHANGES
}
open fun saveFileToCache(generatedClass: GeneratedJvmClass<Target>): CompilationResult {
val sourceFiles: Collection<File> = generatedClass.sourceFiles
val kotlinClass: LocalFileKotlinClass = generatedClass.outputClass
val className = kotlinClass.className
dirtyOutputClassesMap.notDirty(className.internalName)
sourceFiles.forEach {
sourceToClassesMap.add(it, className)
}
if (IncrementalCompilation.isExperimental()) {
internalNameToSource[className.internalName] = sourceFiles
}
if (kotlinClass.classId.isLocal) {
return CompilationResult.NO_CHANGES
}
val header = kotlinClass.classHeader
val changesInfo = when (header.kind) {
KotlinClassHeader.Kind.FILE_FACADE -> {
assert(sourceFiles.size == 1) { "Package part from several source files: $sourceFiles" }
packagePartMap.addPackagePart(className)
protoMap.process(kotlinClass, isPackage = true) +
constantsMap.process(kotlinClass, isPackage = true) +
inlineFunctionsMap.process(kotlinClass, isPackage = true)
}
KotlinClassHeader.Kind.MULTIFILE_CLASS -> {
val partNames = kotlinClass.classHeader.data?.toList()
?: throw AssertionError("Multifile class has no parts: ${kotlinClass.className}")
multifileFacadeToParts[className] = partNames
// When a class is replaced with a facade with the same name,
// the class' proto wouldn't ever be deleted,
// because we don't write proto for multifile facades.
// As a workaround we can remove proto values for multifile facades.
val additionalChangeInfo = if (className in protoMap) {
val info = ChangeInfo.SignatureChanged(className.fqNameForClassNameWithoutDollars, areSubclassesAffected = true)
CompilationResult(protoChanged = true, changes = sequenceOf(info))
}
else CompilationResult.NO_CHANGES
protoMap.remove(className)
classFqNameToSourceMap.remove(className.fqNameForClassNameWithoutDollars)
internalNameToSource.remove(className.internalName)
// TODO NO_CHANGES? (delegates only)
constantsMap.process(kotlinClass, isPackage = true) +
inlineFunctionsMap.process(kotlinClass, isPackage = true) +
additionalChangeInfo
}
KotlinClassHeader.Kind.MULTIFILE_CLASS_PART -> {
assert(sourceFiles.size == 1) { "Multifile class part from several source files: $sourceFiles" }
packagePartMap.addPackagePart(className)
partToMultifileFacade.set(className.internalName, header.multifileClassName!!)
protoMap.process(kotlinClass, isPackage = true) +
constantsMap.process(kotlinClass, isPackage = true) +
inlineFunctionsMap.process(kotlinClass, isPackage = true)
}
KotlinClassHeader.Kind.CLASS -> {
assert(sourceFiles.size == 1) { "Class is expected to have only one source file: $sourceFiles" }
addToClassStorage(kotlinClass, sourceFiles.first())
protoMap.process(kotlinClass, isPackage = false) +
constantsMap.process(kotlinClass, isPackage = false) +
inlineFunctionsMap.process(kotlinClass, isPackage = false)
}
else -> CompilationResult.NO_CHANGES
}
changesInfo.logIfSomethingChanged(className)
return changesInfo
}
private fun CompilationResult.logIfSomethingChanged(className: JvmClassName) {
if (this == CompilationResult.NO_CHANGES) return
debugLog("$className is changed: $this")
}
private fun computeChanges(className: JvmClassName, createChangeInfo: (FqName, Collection<String>) -> ChangeInfo): List<ChangeInfo> {
fun <T> T.getNonPrivateNames(nameResolver: NameResolver, vararg members: T.() -> List<MessageLite>): Set<String> =
members.flatMap { this.it().filterNot { it.isPrivate }.names(nameResolver) }.toSet()
if (className.internalName == MODULE_MAPPING_FILE_NAME) return emptyList()
val mapValue = protoMap[className] ?: return emptyList()
return when {
mapValue.isPackageFacade -> {
val packageData = JvmProtoBufUtil.readPackageDataFrom(mapValue.bytes, mapValue.strings)
val memberNames =
packageData.packageProto.getNonPrivateNames(
packageData.nameResolver,
ProtoBuf.Package::getFunctionList,
ProtoBuf.Package::getPropertyList
)
listOf(createChangeInfo(className.packageFqName, memberNames))
}
else -> {
val classData = JvmProtoBufUtil.readClassDataFrom(mapValue.bytes, mapValue.strings)
val classFqName = className.fqNameForClassNameWithoutDollars
val kind = Flags.CLASS_KIND.get(classData.classProto.flags)
if (kind == ProtoBuf.Class.Kind.COMPANION_OBJECT) {
val memberNames =
classData.classProto.getNonPrivateNames(
classData.nameResolver,
ProtoBuf.Class::getConstructorList,
ProtoBuf.Class::getFunctionList,
ProtoBuf.Class::getPropertyList
) + classData.classProto.enumEntryList.map { classData.nameResolver.getString(it.name) }
val companionObjectChanged = createChangeInfo(classFqName.parent(), listOfNotNull(classFqName.shortName().asString()))
val companionObjectMembersChanged = createChangeInfo(classFqName, memberNames)
listOf(companionObjectMembersChanged, companionObjectChanged)
}
else {
listOf(ChangeInfo.SignatureChanged(classFqName, areSubclassesAffected = true))
}
}
}
}
fun clearCacheForRemovedClasses(): CompilationResult {
val dirtyClasses = dirtyOutputClassesMap
.getDirtyOutputClasses()
.map(JvmClassName::byInternalName)
.toList()
val changes =
if (IncrementalCompilation.isExperimental())
dirtyClasses.flatMap { computeChanges(it, ::Removed) }.asSequence()
else
emptySequence<ChangeInfo>()
val changesInfo = dirtyClasses.fold(CompilationResult(changes = changes)) { info, className ->
val newInfo = CompilationResult(protoChanged = className in protoMap,
constantsChanged = className in constantsMap)
newInfo.logIfSomethingChanged(className)
info + newInfo
}
val facadesWithRemovedParts = hashMapOf<JvmClassName, MutableSet<String>>()
for (dirtyClass in dirtyClasses) {
val facade = partToMultifileFacade.get(dirtyClass.internalName) ?: continue
val facadeClassName = JvmClassName.byInternalName(facade)
val removedParts = facadesWithRemovedParts.getOrPut(facadeClassName) { hashSetOf() }
removedParts.add(dirtyClass.internalName)
}
for ((facade, removedParts) in facadesWithRemovedParts.entries) {
val allParts = multifileFacadeToParts[facade.internalName] ?: continue
val notRemovedParts = allParts.filter { it !in removedParts }
if (notRemovedParts.isEmpty()) {
multifileFacadeToParts.remove(facade)
}
else {
multifileFacadeToParts[facade] = notRemovedParts
}
}
dirtyClasses.forEach {
protoMap.remove(it)
packagePartMap.remove(it)
multifileFacadeToParts.remove(it)
partToMultifileFacade.remove(it)
constantsMap.remove(it)
inlineFunctionsMap.remove(it)
internalNameToSource.remove(it.internalName)
}
removeAllFromClassStorage(dirtyClasses)
dirtyOutputClassesMap.clean()
return changesInfo
}
override fun getObsoletePackageParts(): Collection<String> {
val obsoletePackageParts =
dirtyOutputClassesMap.getDirtyOutputClasses().filter { packagePartMap.isPackagePart(JvmClassName.byInternalName(it)) }
debugLog("Obsolete package parts: $obsoletePackageParts")
return obsoletePackageParts
}
override fun getPackagePartData(partInternalName: String): JvmPackagePartProto? {
return protoMap[JvmClassName.byInternalName(partInternalName)]?.let { value ->
JvmPackagePartProto(value.bytes, value.strings)
}
}
override fun getObsoleteMultifileClasses(): Collection<String> {
val obsoleteMultifileClasses = linkedSetOf<String>()
for (dirtyClass in dirtyOutputClassesMap.getDirtyOutputClasses()) {
val dirtyFacade = partToMultifileFacade.get(dirtyClass) ?: continue
obsoleteMultifileClasses.add(dirtyFacade)
}
debugLog("Obsolete multifile class facades: $obsoleteMultifileClasses")
return obsoleteMultifileClasses
}
override fun getStableMultifileFacadeParts(facadeInternalName: String): Collection<String>? {
val partNames = multifileFacadeToParts.get(facadeInternalName) ?: return null
return partNames.filter { !dirtyOutputClassesMap.isDirty(it) }
}
override fun getModuleMappingData(): ByteArray? {
return protoMap[JvmClassName.byInternalName(MODULE_MAPPING_FILE_NAME)]?.bytes
}
override fun clean() {
super.clean()
normalCacheVersion(targetDataRoot).clean()
experimentalCacheVersion(targetDataRoot).clean()
}
fun cleanExperimental() {
experimentalCacheVersion(targetDataRoot).clean()
experimentalMaps.forEach { it.clean() }
}
private inner class ProtoMap(storageFile: File) : BasicStringMap<ProtoMapValue>(storageFile, ProtoMapValueExternalizer) {
fun process(kotlinClass: LocalFileKotlinClass, isPackage: Boolean): CompilationResult {
val header = kotlinClass.classHeader
val bytes = BitEncoding.decodeBytes(header.data!!)
return put(kotlinClass.className, bytes, header.strings!!, isPackage, checkChangesIsOpenPart = true)
}
fun process(className: JvmClassName, data: ByteArray, strings: Array<String>, isPackage: Boolean, checkChangesIsOpenPart: Boolean): CompilationResult {
return put(className, data, strings, isPackage, checkChangesIsOpenPart)
}
private fun put(
className: JvmClassName, bytes: ByteArray, strings: Array<String>, isPackage: Boolean, checkChangesIsOpenPart: Boolean
): CompilationResult {
val key = className.internalName
val oldData = storage[key]
val data = ProtoMapValue(isPackage, bytes, strings)
if (oldData == null ||
!Arrays.equals(bytes, oldData.bytes) ||
!Arrays.equals(strings, oldData.strings) ||
isPackage != oldData.isPackageFacade
) {
storage[key] = data
}
if (!checkChangesIsOpenPart) return CompilationResult(protoChanged = true)
if (oldData == null) {
val changes =
if (IncrementalCompilation.isExperimental())
computeChanges(className, ::MembersChanged).asSequence()
else
emptySequence<ChangeInfo>()
return CompilationResult(protoChanged = true, changes = changes)
}
val difference = difference(oldData, data)
val fqName = if (isPackage) className.packageFqName else className.fqNameForClassNameWithoutDollars
val changeList = SmartList<ChangeInfo>()
if (difference.isClassAffected) {
changeList.add(ChangeInfo.SignatureChanged(fqName, difference.areSubclassesAffected))
}
if (difference.changedMembersNames.isNotEmpty()) {
changeList.add(ChangeInfo.MembersChanged(fqName, difference.changedMembersNames))
}
return CompilationResult(protoChanged = changeList.isNotEmpty(), changes = changeList.asSequence())
}
operator fun contains(className: JvmClassName): Boolean =
className.internalName in storage
operator fun get(className: JvmClassName): ProtoMapValue? =
storage[className.internalName]
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: ProtoMapValue): String {
return (if (value.isPackageFacade) "1" else "0") + java.lang.Long.toHexString(value.bytes.md5())
}
}
private inner class ConstantsMap(storageFile: File) : BasicStringMap<Map<String, Any>>(storageFile, ConstantsMapExternalizer) {
private fun getConstantsMap(bytes: ByteArray): Map<String, Any>? {
val result = HashMap<String, Any>()
ClassReader(bytes).accept(object : ClassVisitor(Opcodes.ASM5) {
override fun visitField(access: Int, name: String, desc: String, signature: String?, value: Any?): FieldVisitor? {
val staticFinal = Opcodes.ACC_STATIC or Opcodes.ACC_FINAL or Opcodes.ACC_PRIVATE
if (value != null && access and staticFinal == Opcodes.ACC_STATIC or Opcodes.ACC_FINAL) {
result[name] = value
}
return null
}
}, ClassReader.SKIP_CODE or ClassReader.SKIP_DEBUG or ClassReader.SKIP_FRAMES)
return if (result.isEmpty()) null else result
}
operator fun contains(className: JvmClassName): Boolean =
className.internalName in storage
fun process(kotlinClass: LocalFileKotlinClass, isPackage: Boolean): CompilationResult {
return put(kotlinClass.className, getConstantsMap(kotlinClass.fileContents), isPackage)
}
private fun put(className: JvmClassName, constantsMap: Map<String, Any>?, isPackage: Boolean): CompilationResult {
val key = className.internalName
val oldMap = storage[key]
if (oldMap == constantsMap) return CompilationResult.NO_CHANGES
if (constantsMap != null) {
storage[key] = constantsMap
}
else {
remove(className)
}
val changes =
if (!IncrementalCompilation.isExperimental() ||
constantsMap == null || constantsMap.isEmpty() ||
oldMap == null || oldMap.isEmpty()
) {
emptySequence<ChangeInfo>()
}
else {
// we need only changed constants everything other should be covered by diff
val changedNames = oldMap.filter { constantsMap.containsKey(it.key) && constantsMap[it.key] != it.value }.map { it.key }
val fqName = if (isPackage) className.packageFqName else className.fqNameForClassNameWithoutDollars
sequenceOf(ChangeInfo.MembersChanged(fqName, changedNames))
}
return CompilationResult(constantsChanged = true, changes = changes)
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Map<String, Any>): String =
value.dumpMap(Any::toString)
}
private inner class PackagePartMap(storageFile: File) : BasicStringMap<Boolean>(storageFile, BooleanDataDescriptor.INSTANCE) {
fun addPackagePart(className: JvmClassName) {
storage[className.internalName] = true
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
fun isPackagePart(className: JvmClassName): Boolean =
className.internalName in storage
override fun dumpValue(value: Boolean) = ""
}
private inner class MultifileClassFacadeMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, StringCollectionExternalizer) {
operator fun set(facadeName: JvmClassName, partNames: Collection<String>) {
storage[facadeName.internalName] = partNames
}
operator fun get(internalName: String): Collection<String>? = storage[internalName]
operator fun contains(internalName: String): Boolean = internalName in storage
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Collection<String>): String = value.dumpCollection()
}
private inner class MultifileClassPartMap(storageFile: File) : BasicStringMap<String>(storageFile, EnumeratorStringDescriptor.INSTANCE) {
fun set(partName: String, facadeName: String) {
storage[partName] = facadeName
}
fun get(partName: String): String? {
return storage.get(partName)
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: String): String = value
}
inner class SourceToClassesMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, PathStringDescriptor, StringCollectionExternalizer) {
fun clearOutputsForSource(sourceFile: File) {
remove(sourceFile.absolutePath)
}
fun add(sourceFile: File, className: JvmClassName) {
storage.append(sourceFile.absolutePath, className.internalName)
}
operator fun get(sourceFile: File): Collection<JvmClassName> =
storage[sourceFile.absolutePath].orEmpty().map { JvmClassName.byInternalName(it) }
override fun dumpValue(value: Collection<String>) = value.dumpCollection()
private fun remove(path: String) {
storage.remove(path)
}
}
inner class ClassFqNameToSourceMap(storageFile: File) : BasicStringMap<String>(storageFile, EnumeratorStringDescriptor(), PathStringDescriptor) {
operator fun set(fqName: FqName, sourceFile: File) {
storage[fqName.asString()] = sourceFile.canonicalPath
}
operator fun get(fqName: FqName): File? =
storage[fqName.asString()]?.let(::File)
fun remove(fqName: FqName) {
storage.remove(fqName.asString())
}
override fun dumpValue(value: String) = value
}
inner class InternalNameToSourcesMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, EnumeratorStringDescriptor(), PathCollectionExternalizer) {
operator fun set(internalName: String, sourceFiles: Iterable<File>) {
storage[internalName] = sourceFiles.map { it.canonicalPath }
}
operator fun get(internalName: String): Collection<File> =
(storage[internalName] ?: emptyList()).map(::File)
fun remove(internalName: String) {
storage.remove(internalName)
}
override fun dumpValue(value: Collection<String>): String =
value.dumpCollection()
}
private fun addToClassStorage(kotlinClass: LocalFileKotlinClass, srcFile: File) {
if (!IncrementalCompilation.isExperimental()) return
val classData = JvmProtoBufUtil.readClassDataFrom(kotlinClass.classHeader.data!!, kotlinClass.classHeader.strings!!)
val supertypes = classData.classProto.supertypes(TypeTable(classData.classProto.typeTable))
val parents = supertypes.map { classData.nameResolver.getClassId(it.className).asSingleFqName() }
.filter { it.asString() != "kotlin.Any" }
.toSet()
val child = kotlinClass.classId.asSingleFqName()
parents.forEach { subtypesMap.add(it, child) }
val removedSupertypes = supertypesMap[child].filter { it !in parents }
removedSupertypes.forEach { subtypesMap.removeValues(it, setOf(child)) }
supertypesMap[child] = parents
classFqNameToSourceMap[kotlinClass.className.fqNameForClassNameWithoutDollars] = srcFile
}
private fun removeAllFromClassStorage(removedClasses: Collection<JvmClassName>) {
if (!IncrementalCompilation.isExperimental() || removedClasses.isEmpty()) return
val removedFqNames = removedClasses.map { it.fqNameForClassNameWithoutDollars }.toSet()
for (cache in thisWithDependentCaches) {
val parentsFqNames = hashSetOf<FqName>()
val childrenFqNames = hashSetOf<FqName>()
for (removedFqName in removedFqNames) {
parentsFqNames.addAll(cache.supertypesMap[removedFqName])
childrenFqNames.addAll(cache.subtypesMap[removedFqName])
cache.supertypesMap.remove(removedFqName)
cache.subtypesMap.remove(removedFqName)
}
for (child in childrenFqNames) {
cache.supertypesMap.removeValues(child, removedFqNames)
}
for (parent in parentsFqNames) {
cache.subtypesMap.removeValues(parent, removedFqNames)
}
}
removedFqNames.forEach { classFqNameToSourceMap.remove(it) }
}
private inner class DirtyOutputClassesMap(storageFile: File) : BasicStringMap<Boolean>(storageFile, BooleanDataDescriptor.INSTANCE) {
fun markDirty(className: String) {
storage[className] = true
}
fun notDirty(className: String) {
storage.remove(className)
}
fun getDirtyOutputClasses(): Collection<String> =
storage.keys
fun isDirty(className: String): Boolean =
storage.contains(className)
override fun dumpValue(value: Boolean) = ""
}
private inner class InlineFunctionsMap(storageFile: File) : BasicStringMap<Map<String, Long>>(storageFile, StringToLongMapExternalizer) {
private fun getInlineFunctionsMap(header: KotlinClassHeader, bytes: ByteArray): Map<String, Long> {
val inlineFunctions = inlineFunctionsJvmNames(header)
if (inlineFunctions.isEmpty()) return emptyMap()
val result = HashMap<String, Long>()
ClassReader(bytes).accept(object : ClassVisitor(Opcodes.ASM5) {
override fun visitMethod(access: Int, name: String, desc: String, signature: String?, exceptions: Array<out String>?): MethodVisitor? {
val dummyClassWriter = ClassWriter(Opcodes.ASM5)
return object : MethodVisitor(Opcodes.ASM5, dummyClassWriter.visitMethod(0, name, desc, null, exceptions)) {
override fun visitEnd() {
val jvmName = name + desc
if (jvmName !in inlineFunctions) return
val dummyBytes = dummyClassWriter.toByteArray()!!
val hash = dummyBytes.md5()
result[jvmName] = hash
}
}
}
}, 0)
return result
}
fun process(kotlinClass: LocalFileKotlinClass, isPackage: Boolean): CompilationResult {
return put(kotlinClass.className, getInlineFunctionsMap(kotlinClass.classHeader, kotlinClass.fileContents), isPackage)
}
private fun put(className: JvmClassName, newMap: Map<String, Long>, isPackage: Boolean): CompilationResult {
val internalName = className.internalName
val oldMap = storage[internalName] ?: emptyMap()
val added = hashSetOf<String>()
val changed = hashSetOf<String>()
val allFunctions = oldMap.keys + newMap.keys
for (fn in allFunctions) {
val oldHash = oldMap[fn]
val newHash = newMap[fn]
when {
oldHash == null -> added.add(fn)
oldHash != newHash -> changed.add(fn)
}
}
when {
newMap.isNotEmpty() -> storage[internalName] = newMap
else -> storage.remove(internalName)
}
val changes =
if (IncrementalCompilation.isExperimental()) {
val fqName = if (isPackage) className.packageFqName else className.fqNameForClassNameWithoutDollars
// TODO get name in better way instead of using substringBefore
(added.asSequence() + changed.asSequence()).map { ChangeInfo.MembersChanged(fqName, listOf(it.substringBefore("("))) }
}
else {
emptySequence<ChangeInfo>()
}
processChangedInlineFunctions(className, changed)
return CompilationResult(inlineChanged = changed.isNotEmpty(),
inlineAdded = added.isNotEmpty(),
changes = changes)
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Map<String, Long>): String =
value.dumpMap { java.lang.Long.toHexString(it) }
}
protected open fun processChangedInlineFunctions(
className: JvmClassName,
changedFunctions: Collection<String>
) {
}
}
private object PathCollectionExternalizer : CollectionExternalizer<String>(PathStringDescriptor, { THashSet(FileUtil.PATH_HASHING_STRATEGY) })
sealed class ChangeInfo(val fqName: FqName) {
open class MembersChanged(fqName: FqName, val names: Collection<String>) : ChangeInfo(fqName) {
override fun toStringProperties(): String = super.toStringProperties() + ", names = $names"
}
class Removed(fqName: FqName, names: Collection<String>) : MembersChanged(fqName, names)
class SignatureChanged(fqName: FqName, val areSubclassesAffected: Boolean) : ChangeInfo(fqName)
protected open fun toStringProperties(): String = "fqName = $fqName"
override fun toString(): String {
return this::class.java.simpleName + "(${toStringProperties()})"
}
}
data class CompilationResult(
val protoChanged: Boolean = false,
val constantsChanged: Boolean = false,
val inlineChanged: Boolean = false,
val inlineAdded: Boolean = false,
val changes: Sequence<ChangeInfo> = emptySequence()
) {
companion object {
val NO_CHANGES: CompilationResult = CompilationResult()
}
operator fun plus(other: CompilationResult): CompilationResult =
CompilationResult(protoChanged || other.protoChanged,
constantsChanged || other.constantsChanged,
inlineChanged || other.inlineChanged,
inlineAdded || other.inlineAdded,
changes + other.changes)
}
fun ByteArray.md5(): Long {
val d = MessageDigest.getInstance("MD5").digest(this)!!
return ((d[0].toLong() and 0xFFL)
or ((d[1].toLong() and 0xFFL) shl 8)
or ((d[2].toLong() and 0xFFL) shl 16)
or ((d[3].toLong() and 0xFFL) shl 24)
or ((d[4].toLong() and 0xFFL) shl 32)
or ((d[5].toLong() and 0xFFL) shl 40)
or ((d[6].toLong() and 0xFFL) shl 48)
or ((d[7].toLong() and 0xFFL) shl 56)
)
}
@TestOnly
fun <K : Comparable<K>, V> Map<K, V>.dumpMap(dumpValue: (V)->String): String =
buildString {
append("{")
for (key in keys.sorted()) {
if (length != 1) {
append(", ")
}
val value = get(key)?.let(dumpValue) ?: "null"
append("$key -> $value")
}
append("}")
}
@TestOnly fun <T : Comparable<T>> Collection<T>.dumpCollection(): String =
"[${sorted().joinToString(", ", transform = Any::toString)}]"

View File

@@ -16,17 +16,13 @@
package org.jetbrains.kotlin.incremental
import org.jetbrains.kotlin.incremental.components.LookupTracker
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCache
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCompilationComponents
import org.jetbrains.kotlin.modules.TargetId
class IncrementalCompilationComponentsImpl(
private val caches: Map<TargetId, IncrementalCache>,
private val lookupTracker: LookupTracker
private val caches: Map<TargetId, IncrementalCache>
): IncrementalCompilationComponents {
override fun getIncrementalCache(target: TargetId): IncrementalCache =
caches[target] ?: throw Exception("Incremental cache for target ${target.name} not found")
override fun getLookupTracker(): LookupTracker = lookupTracker
}

View File

@@ -0,0 +1,226 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.incremental
import com.intellij.util.io.DataExternalizer
import org.jetbrains.kotlin.incremental.js.IncrementalResultsConsumerImpl
import org.jetbrains.kotlin.incremental.js.TranslationResultValue
import org.jetbrains.kotlin.incremental.storage.*
import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolverImpl
import org.jetbrains.kotlin.serialization.js.JsProtoBuf
import org.jetbrains.kotlin.serialization.js.JsSerializerProtocol
import java.io.DataInput
import java.io.DataOutput
import java.io.File
open class IncrementalJsCache(cachesDir: File) : IncrementalCacheCommon(cachesDir) {
companion object {
private val TRANSLATION_RESULT_MAP = "translation-result"
private val SOURCES_TO_CLASSES_FQNS = "sources-to-classes"
private val INLINE_FUNCTIONS = "inline-functions"
private val HEADER_FILE_NAME = "header.meta"
}
private val dirtySources = arrayListOf<File>()
private val translationResults = registerMap(TranslationResultMap(TRANSLATION_RESULT_MAP.storageFile))
private val sourcesToClasses = registerMap(SourceToClassesMap(SOURCES_TO_CLASSES_FQNS.storageFile))
private val inlineFunctions = registerMap(InlineFunctionsMap(INLINE_FUNCTIONS.storageFile))
private val headerFile: File
get() = File(cachesDir, HEADER_FILE_NAME)
var header: ByteArray
get() = headerFile.readBytes()
set(value) {
cachesDir.mkdirs()
headerFile.writeBytes(value)
}
override fun markDirty(removedAndCompiledSources: List<File>) {
dirtySources.addAll(removedAndCompiledSources)
}
fun compareAndUpdate(incrementalResults: IncrementalResultsConsumerImpl, changesCollector: ChangesCollector) {
val translatedFiles = incrementalResults.packageParts
dirtySources.forEach {
if (it !in translatedFiles) {
translationResults.remove(it, changesCollector)
inlineFunctions.remove(it)
}
removeAllFromClassStorage(sourcesToClasses[it])
sourcesToClasses.clearOutputsForSource(it)
}
dirtySources.clear()
for ((srcFile, data) in translatedFiles) {
val (binaryMetadata, binaryAst) = data
val oldProtoMap = translationResults[srcFile]?.metadata?.let { getProtoData(srcFile, it) } ?: emptyMap()
val newProtoMap = getProtoData(srcFile, binaryMetadata)
for (protoData in newProtoMap.values) {
if (protoData is ClassProtoData) {
addToClassStorage(protoData.proto, protoData.nameResolver, srcFile)
}
}
for (classId in oldProtoMap.keys + newProtoMap.keys) {
changesCollector.collectProtoChanges(oldProtoMap[classId], newProtoMap[classId])
}
translationResults.put(srcFile, binaryMetadata, binaryAst)
}
for ((srcFile, inlineDeclarations) in incrementalResults.inlineFunctions) {
inlineFunctions.process(srcFile, inlineDeclarations, changesCollector)
}
}
fun nonDirtyPackageParts(): Map<File, TranslationResultValue> =
hashMapOf<File, TranslationResultValue>().apply {
for (path in translationResults.keys()) {
val file = File(path)
if (file !in dirtySources) {
put(file, translationResults[path]!!)
}
}
}
}
private class SourceToClassesMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, PathStringDescriptor, StringCollectionExternalizer) {
fun clearOutputsForSource(sourceFile: File) {
remove(sourceFile.canonicalPath)
}
fun add(sourceFile: File, className: FqName) {
storage.append(sourceFile.canonicalPath, className.asString())
}
operator fun get(sourceFile: File): Collection<FqName> =
storage[sourceFile.canonicalPath].orEmpty().map { FqName(it) }
override fun dumpValue(value: Collection<String>) = value.dumpCollection()
private fun remove(path: String) {
storage.remove(path)
}
}
private object TranslationResultValueExternalizer : DataExternalizer<TranslationResultValue> {
override fun save(output: DataOutput, value: TranslationResultValue) {
output.writeInt(value.metadata.size)
output.write(value.metadata)
output.writeInt(value.binaryAst.size)
output.write(value.binaryAst)
}
override fun read(input: DataInput): TranslationResultValue {
val metadataSize = input.readInt()
val metadata = ByteArray(metadataSize)
input.readFully(metadata)
val binaryAstSize = input.readInt()
val binaryAst = ByteArray(binaryAstSize)
input.readFully(binaryAst)
return TranslationResultValue(metadata = metadata, binaryAst = binaryAst)
}
}
private class TranslationResultMap(storageFile: File) : BasicStringMap<TranslationResultValue>(storageFile, TranslationResultValueExternalizer) {
override fun dumpValue(value: TranslationResultValue): String =
"Metadata: ${value.metadata.md5()}, Binary AST: ${value.binaryAst.md5()}"
fun put(file: File, newMetadata: ByteArray, newBinaryAst: ByteArray) {
storage[file.canonicalPath] = TranslationResultValue(metadata = newMetadata, binaryAst = newBinaryAst)
}
operator fun get(file: File): TranslationResultValue? =
storage[file.canonicalPath]
operator fun get(key: String): TranslationResultValue? =
storage[key]
fun keys(): Collection<String> =
storage.keys
fun remove(file: File, changesCollector: ChangesCollector) {
val protoBytes = storage[file.canonicalPath]!!.metadata
val protoMap = getProtoData(file, protoBytes)
for ((_, protoData) in protoMap) {
changesCollector.collectProtoChanges(oldData = protoData, newData = null)
}
storage.remove(file.canonicalPath)
}
}
fun getProtoData(sourceFile: File, metadata: ByteArray): Map<ClassId, ProtoData> {
val classes = hashMapOf<ClassId, ProtoData>()
val proto = ProtoBuf.PackageFragment.parseFrom(metadata, JsSerializerProtocol.extensionRegistry)
val nameResolver = NameResolverImpl(proto.strings, proto.qualifiedNames)
proto.class_List.forEach {
val classId = nameResolver.getClassId(it.fqName)
classes[classId] = ClassProtoData(it, nameResolver)
}
proto.`package`.apply {
val packageFqName = if (hasExtension(JsProtoBuf.packageFqName)) {
nameResolver.getPackageFqName(getExtension(JsProtoBuf.packageFqName))
}
else FqName.ROOT
val packagePartClassId = ClassId(packageFqName, Name.identifier(sourceFile.nameWithoutExtension.capitalize() + "Kt"))
classes[packagePartClassId] = PackagePartProtoData(this, nameResolver, packageFqName)
}
return classes
}
private class InlineFunctionsMap(storageFile: File) : BasicStringMap<Map<String, Long>>(storageFile, StringToLongMapExternalizer) {
fun process(srcFile: File, newMap: Map<String, Long>, changesCollector: ChangesCollector) {
val key = srcFile.canonicalPath
val oldMap = storage[key] ?: emptyMap()
if (newMap.isNotEmpty()) {
storage[key] = newMap
}
else {
storage.remove(key)
}
for (fn in oldMap.keys + newMap.keys) {
val fqNameSegments = fn.removePrefix("<get>").removePrefix("<set>").split(".")
val fqName = FqName.fromSegments(fqNameSegments)
changesCollector.collectMemberIfValueWasChanged(fqName.parent(), fqName.shortName().asString(), oldMap[fn], newMap[fn])
}
}
fun remove(sourceFile: File) {
storage.remove(sourceFile.canonicalPath)
}
override fun dumpValue(value: Map<String, Long>): String =
value.dumpMap { java.lang.Long.toHexString(it) }
}

View File

@@ -0,0 +1,562 @@
/*
* Copyright 2010-2016 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.incremental
import com.intellij.openapi.util.io.FileUtil
import com.intellij.openapi.util.io.FileUtil.toSystemIndependentName
import com.intellij.util.io.BooleanDataDescriptor
import com.intellij.util.io.EnumeratorStringDescriptor
import gnu.trove.THashSet
import org.jetbrains.annotations.TestOnly
import org.jetbrains.kotlin.build.GeneratedJvmClass
import org.jetbrains.kotlin.incremental.storage.*
import org.jetbrains.kotlin.inline.inlineFunctionsJvmNames
import org.jetbrains.kotlin.load.kotlin.ModuleMapping
import org.jetbrains.kotlin.load.kotlin.header.KotlinClassHeader
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCache
import org.jetbrains.kotlin.load.kotlin.incremental.components.JvmPackagePartProto
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.resolve.jvm.JvmClassName
import org.jetbrains.kotlin.serialization.jvm.BitEncoding
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBufUtil
import org.jetbrains.org.objectweb.asm.*
import java.io.File
import java.security.MessageDigest
import java.util.*
val KOTLIN_CACHE_DIRECTORY_NAME = "kotlin"
open class IncrementalJvmCache(
private val targetDataRoot: File,
targetOutputDir: File?
) : IncrementalCacheCommon(File(targetDataRoot, KOTLIN_CACHE_DIRECTORY_NAME)), IncrementalCache {
companion object {
private val PROTO_MAP = "proto"
private val CONSTANTS_MAP = "constants"
private val PACKAGE_PARTS = "package-parts"
private val MULTIFILE_CLASS_FACADES = "multifile-class-facades"
private val MULTIFILE_CLASS_PARTS = "multifile-class-parts"
private val SOURCE_TO_CLASSES = "source-to-classes"
private val DIRTY_OUTPUT_CLASSES = "dirty-output-classes"
private val INLINE_FUNCTIONS = "inline-functions"
private val INTERNAL_NAME_TO_SOURCE = "internal-name-to-source"
private val MODULE_MAPPING_FILE_NAME = "." + ModuleMapping.MAPPING_FILE_EXT
}
private val protoMap = registerMap(ProtoMap(PROTO_MAP.storageFile))
private val constantsMap = registerMap(ConstantsMap(CONSTANTS_MAP.storageFile))
private val packagePartMap = registerMap(PackagePartMap(PACKAGE_PARTS.storageFile))
private val multifileFacadeToParts = registerMap(MultifileClassFacadeMap(MULTIFILE_CLASS_FACADES.storageFile))
private val partToMultifileFacade = registerMap(MultifileClassPartMap(MULTIFILE_CLASS_PARTS.storageFile))
private val sourceToClassesMap = registerMap(SourceToClassesMap(SOURCE_TO_CLASSES.storageFile))
private val dirtyOutputClassesMap = registerMap(DirtyOutputClassesMap(DIRTY_OUTPUT_CLASSES.storageFile))
private val inlineFunctionsMap = registerMap(InlineFunctionsMap(INLINE_FUNCTIONS.storageFile))
// todo: try to use internal names only?
private val internalNameToSource = registerMap(InternalNameToSourcesMap(INTERNAL_NAME_TO_SOURCE.storageFile))
private val outputDir by lazy(LazyThreadSafetyMode.NONE) { requireNotNull(targetOutputDir) { "Target is expected to have output directory" } }
protected open fun debugLog(message: String) {}
override fun markDirty(removedAndCompiledSources: List<File>) {
for (sourceFile in removedAndCompiledSources) {
val classes = sourceToClassesMap[sourceFile]
classes.forEach {
dirtyOutputClassesMap.markDirty(it.internalName)
}
sourceToClassesMap.clearOutputsForSource(sourceFile)
}
}
// used in gradle
@Suppress("unused")
fun classesBySources(sources: Iterable<File>): Iterable<JvmClassName> =
sources.flatMap { sourceToClassesMap[it] }
fun sourcesByInternalName(internalName: String): Collection<File> =
internalNameToSource[internalName]
fun isMultifileFacade(className: JvmClassName): Boolean =
className.internalName in multifileFacadeToParts
override fun getClassFilePath(internalClassName: String): String {
return toSystemIndependentName(File(outputDir, "$internalClassName.class").canonicalPath)
}
fun saveModuleMappingToCache(sourceFiles: Collection<File>, file: File) {
val jvmClassName = JvmClassName.byInternalName(MODULE_MAPPING_FILE_NAME)
protoMap.storeModuleMapping(jvmClassName, file.readBytes())
dirtyOutputClassesMap.notDirty(MODULE_MAPPING_FILE_NAME)
sourceFiles.forEach { sourceToClassesMap.add(it, jvmClassName) }
}
open fun saveFileToCache(generatedClass: GeneratedJvmClass, changesCollector: ChangesCollector) {
val sourceFiles: Collection<File> = generatedClass.sourceFiles
val kotlinClass: LocalFileKotlinClass = generatedClass.outputClass
val className = kotlinClass.className
dirtyOutputClassesMap.notDirty(className.internalName)
sourceFiles.forEach {
sourceToClassesMap.add(it, className)
}
internalNameToSource[className.internalName] = sourceFiles
if (kotlinClass.classId.isLocal) return
val header = kotlinClass.classHeader
when (header.kind) {
KotlinClassHeader.Kind.FILE_FACADE -> {
assert(sourceFiles.size == 1) { "Package part from several source files: $sourceFiles" }
packagePartMap.addPackagePart(className)
protoMap.process(kotlinClass, changesCollector)
constantsMap.process(kotlinClass, changesCollector)
inlineFunctionsMap.process(kotlinClass, changesCollector)
}
KotlinClassHeader.Kind.MULTIFILE_CLASS -> {
val partNames = kotlinClass.classHeader.data?.toList()
?: throw AssertionError("Multifile class has no parts: ${kotlinClass.className}")
multifileFacadeToParts[className] = partNames
// When a class is replaced with a facade with the same name,
// the class' proto wouldn't ever be deleted,
// because we don't write proto for multifile facades.
// As a workaround we can remove proto values for multifile facades.
if (className in protoMap) {
changesCollector.collectSignature(className.fqNameForClassNameWithoutDollars, areSubclassesAffected = true)
}
protoMap.remove(className, changesCollector)
classFqNameToSourceMap.remove(className.fqNameForClassNameWithoutDollars)
internalNameToSource.remove(className.internalName)
// TODO NO_CHANGES? (delegates only)
constantsMap.process(kotlinClass, changesCollector)
inlineFunctionsMap.process(kotlinClass, changesCollector)
}
KotlinClassHeader.Kind.MULTIFILE_CLASS_PART -> {
assert(sourceFiles.size == 1) { "Multifile class part from several source files: $sourceFiles" }
packagePartMap.addPackagePart(className)
partToMultifileFacade.set(className.internalName, header.multifileClassName!!)
protoMap.process(kotlinClass, changesCollector)
constantsMap.process(kotlinClass, changesCollector)
inlineFunctionsMap.process(kotlinClass, changesCollector)
}
KotlinClassHeader.Kind.CLASS -> {
assert(sourceFiles.size == 1) { "Class is expected to have only one source file: $sourceFiles" }
addToClassStorage(kotlinClass, sourceFiles.first())
protoMap.process(kotlinClass, changesCollector)
constantsMap.process(kotlinClass, changesCollector)
inlineFunctionsMap.process(kotlinClass, changesCollector)
}
}
}
fun clearCacheForRemovedClasses(changesCollector: ChangesCollector) {
val dirtyClasses = dirtyOutputClassesMap
.getDirtyOutputClasses()
.map(JvmClassName::byInternalName)
.toList()
val facadesWithRemovedParts = hashMapOf<JvmClassName, MutableSet<String>>()
for (dirtyClass in dirtyClasses) {
val facade = partToMultifileFacade.get(dirtyClass.internalName) ?: continue
val facadeClassName = JvmClassName.byInternalName(facade)
val removedParts = facadesWithRemovedParts.getOrPut(facadeClassName) { hashSetOf() }
removedParts.add(dirtyClass.internalName)
}
for ((facade, removedParts) in facadesWithRemovedParts.entries) {
val allParts = multifileFacadeToParts[facade.internalName] ?: continue
val notRemovedParts = allParts.filter { it !in removedParts }
if (notRemovedParts.isEmpty()) {
multifileFacadeToParts.remove(facade)
}
else {
multifileFacadeToParts[facade] = notRemovedParts
}
}
dirtyClasses.forEach {
protoMap.remove(it, changesCollector)
packagePartMap.remove(it)
multifileFacadeToParts.remove(it)
partToMultifileFacade.remove(it)
constantsMap.remove(it)
inlineFunctionsMap.remove(it)
internalNameToSource.remove(it.internalName)
}
removeAllFromClassStorage(dirtyClasses.map { it.fqNameForClassNameWithoutDollars })
dirtyOutputClassesMap.clean()
}
override fun getObsoletePackageParts(): Collection<String> {
val obsoletePackageParts =
dirtyOutputClassesMap.getDirtyOutputClasses().filter { packagePartMap.isPackagePart(JvmClassName.byInternalName(it)) }
debugLog("Obsolete package parts: $obsoletePackageParts")
return obsoletePackageParts
}
override fun getPackagePartData(partInternalName: String): JvmPackagePartProto? {
return protoMap[JvmClassName.byInternalName(partInternalName)]?.let { value ->
JvmPackagePartProto(value.bytes, value.strings)
}
}
override fun getObsoleteMultifileClasses(): Collection<String> {
val obsoleteMultifileClasses = linkedSetOf<String>()
for (dirtyClass in dirtyOutputClassesMap.getDirtyOutputClasses()) {
val dirtyFacade = partToMultifileFacade.get(dirtyClass) ?: continue
obsoleteMultifileClasses.add(dirtyFacade)
}
debugLog("Obsolete multifile class facades: $obsoleteMultifileClasses")
return obsoleteMultifileClasses
}
override fun getStableMultifileFacadeParts(facadeInternalName: String): Collection<String>? {
val partNames = multifileFacadeToParts.get(facadeInternalName) ?: return null
return partNames.filter { !dirtyOutputClassesMap.isDirty(it) }
}
override fun getModuleMappingData(): ByteArray? {
return protoMap[JvmClassName.byInternalName(MODULE_MAPPING_FILE_NAME)]?.bytes
}
override fun clean() {
super.clean()
normalCacheVersion(targetDataRoot).clean()
}
private inner class ProtoMap(storageFile: File) : BasicStringMap<ProtoMapValue>(storageFile, ProtoMapValueExternalizer) {
fun process(kotlinClass: LocalFileKotlinClass, changesCollector: ChangesCollector) {
return put(kotlinClass, changesCollector)
}
// A module mapping (.kotlin_module file) is stored in a cache,
// because a corresponding file will be deleted on each round
// (it is reported as output for each [package part?] source file).
// If a mapping is not preserved, a resulting file will only contain data
// from files compiled during last round.
// However there is no need to compare old and new data in this case
// (also that would fail with exception).
fun storeModuleMapping(className: JvmClassName, bytes: ByteArray) {
storage[className.internalName] = ProtoMapValue(isPackageFacade = false, bytes = bytes, strings = emptyArray())
}
private fun put(kotlinClass: LocalFileKotlinClass, changesCollector: ChangesCollector) {
val header = kotlinClass.classHeader
val key = kotlinClass.className.internalName
val oldData = storage[key]
val newData = ProtoMapValue(header.kind != KotlinClassHeader.Kind.CLASS,
BitEncoding.decodeBytes(header.data!!),
header.strings!!)
storage[key] = newData
val packageFqName = kotlinClass.className.packageFqName
changesCollector.collectProtoChanges(oldData?.toProtoData(packageFqName), newData.toProtoData(packageFqName))
}
operator fun contains(className: JvmClassName): Boolean =
className.internalName in storage
operator fun get(className: JvmClassName): ProtoMapValue? =
storage[className.internalName]
fun remove(className: JvmClassName, changesCollector: ChangesCollector) {
val key = className.internalName
val oldValue = storage[key] ?: return
changesCollector.collectProtoChanges(oldData = oldValue.toProtoData(className.packageFqName), newData = null)
storage.remove(key)
}
override fun dumpValue(value: ProtoMapValue): String {
return (if (value.isPackageFacade) "1" else "0") + java.lang.Long.toHexString(value.bytes.md5())
}
}
// todo: reuse code with InlineFunctionsMap?
private inner class ConstantsMap(storageFile: File) : BasicStringMap<Map<String, Any>>(storageFile, ConstantsMapExternalizer) {
private fun getConstantsMap(bytes: ByteArray): Map<String, Any> {
val result = HashMap<String, Any>()
ClassReader(bytes).accept(object : ClassVisitor(Opcodes.ASM5) {
override fun visitField(access: Int, name: String, desc: String, signature: String?, value: Any?): FieldVisitor? {
val staticFinal = Opcodes.ACC_STATIC or Opcodes.ACC_FINAL or Opcodes.ACC_PRIVATE
if (value != null && access and staticFinal == Opcodes.ACC_STATIC or Opcodes.ACC_FINAL) {
result[name] = value
}
return null
}
}, ClassReader.SKIP_CODE or ClassReader.SKIP_DEBUG or ClassReader.SKIP_FRAMES)
return result
}
operator fun contains(className: JvmClassName): Boolean =
className.internalName in storage
fun process(kotlinClass: LocalFileKotlinClass, changesCollector: ChangesCollector) {
val key = kotlinClass.className.internalName
val oldMap = storage[key] ?: emptyMap()
val newMap = getConstantsMap(kotlinClass.fileContents)
if (newMap.isNotEmpty()) {
storage[key] = newMap
}
else {
storage.remove(key)
}
for (const in oldMap.keys + newMap.keys) {
changesCollector.collectMemberIfValueWasChanged(kotlinClass.scopeFqName(), const, oldMap[const], newMap[const])
}
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Map<String, Any>): String =
value.dumpMap(Any::toString)
}
private inner class PackagePartMap(storageFile: File) : BasicStringMap<Boolean>(storageFile, BooleanDataDescriptor.INSTANCE) {
fun addPackagePart(className: JvmClassName) {
storage[className.internalName] = true
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
fun isPackagePart(className: JvmClassName): Boolean =
className.internalName in storage
override fun dumpValue(value: Boolean) = ""
}
private inner class MultifileClassFacadeMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, StringCollectionExternalizer) {
operator fun set(facadeName: JvmClassName, partNames: Collection<String>) {
storage[facadeName.internalName] = partNames
}
operator fun get(internalName: String): Collection<String>? = storage[internalName]
operator fun contains(internalName: String): Boolean = internalName in storage
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Collection<String>): String = value.dumpCollection()
}
private inner class MultifileClassPartMap(storageFile: File) : BasicStringMap<String>(storageFile, EnumeratorStringDescriptor.INSTANCE) {
fun set(partName: String, facadeName: String) {
storage[partName] = facadeName
}
fun get(partName: String): String? {
return storage.get(partName)
}
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: String): String = value
}
inner class SourceToClassesMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, PathStringDescriptor, StringCollectionExternalizer) {
fun clearOutputsForSource(sourceFile: File) {
remove(sourceFile.absolutePath)
}
fun add(sourceFile: File, className: JvmClassName) {
storage.append(sourceFile.absolutePath, className.internalName)
}
operator fun get(sourceFile: File): Collection<JvmClassName> =
storage[sourceFile.absolutePath].orEmpty().map { JvmClassName.byInternalName(it) }
override fun dumpValue(value: Collection<String>) = value.dumpCollection()
private fun remove(path: String) {
storage.remove(path)
}
}
inner class InternalNameToSourcesMap(storageFile: File) : BasicStringMap<Collection<String>>(storageFile, EnumeratorStringDescriptor(), PathCollectionExternalizer) {
operator fun set(internalName: String, sourceFiles: Iterable<File>) {
storage[internalName] = sourceFiles.map { it.canonicalPath }
}
operator fun get(internalName: String): Collection<File> =
(storage[internalName] ?: emptyList()).map(::File)
fun remove(internalName: String) {
storage.remove(internalName)
}
override fun dumpValue(value: Collection<String>): String =
value.dumpCollection()
}
private fun addToClassStorage(kotlinClass: LocalFileKotlinClass, srcFile: File) {
val (nameResolver, proto) = JvmProtoBufUtil.readClassDataFrom(kotlinClass.classHeader.data!!, kotlinClass.classHeader.strings!!)
addToClassStorage(proto, nameResolver, srcFile)
}
private inner class DirtyOutputClassesMap(storageFile: File) : BasicStringMap<Boolean>(storageFile, BooleanDataDescriptor.INSTANCE) {
fun markDirty(className: String) {
storage[className] = true
}
fun notDirty(className: String) {
storage.remove(className)
}
fun getDirtyOutputClasses(): Collection<String> =
storage.keys
fun isDirty(className: String): Boolean =
storage.contains(className)
override fun dumpValue(value: Boolean) = ""
}
private inner class InlineFunctionsMap(storageFile: File) : BasicStringMap<Map<String, Long>>(storageFile, StringToLongMapExternalizer) {
private fun getInlineFunctionsMap(header: KotlinClassHeader, bytes: ByteArray): Map<String, Long> {
val inlineFunctions = inlineFunctionsJvmNames(header)
if (inlineFunctions.isEmpty()) return emptyMap()
val result = HashMap<String, Long>()
ClassReader(bytes).accept(object : ClassVisitor(Opcodes.ASM5) {
override fun visitMethod(access: Int, name: String, desc: String, signature: String?, exceptions: Array<out String>?): MethodVisitor? {
val dummyClassWriter = ClassWriter(Opcodes.ASM5)
return object : MethodVisitor(Opcodes.ASM5, dummyClassWriter.visitMethod(0, name, desc, null, exceptions)) {
override fun visitEnd() {
val jvmName = name + desc
if (jvmName !in inlineFunctions) return
val dummyBytes = dummyClassWriter.toByteArray()!!
val hash = dummyBytes.md5()
result[jvmName] = hash
}
}
}
}, 0)
return result
}
fun process(kotlinClass: LocalFileKotlinClass, changesCollector: ChangesCollector) {
val key = kotlinClass.className.internalName
val oldMap = storage[key] ?: emptyMap()
val newMap = getInlineFunctionsMap(kotlinClass.classHeader, kotlinClass.fileContents)
if (newMap.isNotEmpty()) {
storage[key] = newMap
}
else {
storage.remove(key)
}
for (fn in oldMap.keys + newMap.keys) {
changesCollector.collectMemberIfValueWasChanged(kotlinClass.scopeFqName(), functionNameBySignature(fn), oldMap[fn], newMap[fn])
}
}
// TODO get name in better way instead of using substringBefore
private fun functionNameBySignature(signature: String): String =
signature.substringBefore("(")
fun remove(className: JvmClassName) {
storage.remove(className.internalName)
}
override fun dumpValue(value: Map<String, Long>): String =
value.dumpMap { java.lang.Long.toHexString(it) }
}
}
private object PathCollectionExternalizer : CollectionExternalizer<String>(PathStringDescriptor, { THashSet(FileUtil.PATH_HASHING_STRATEGY) })
sealed class ChangeInfo(val fqName: FqName) {
open class MembersChanged(fqName: FqName, val names: Collection<String>) : ChangeInfo(fqName) {
override fun toStringProperties(): String = super.toStringProperties() + ", names = $names"
}
class Removed(fqName: FqName, names: Collection<String>) : MembersChanged(fqName, names)
class SignatureChanged(fqName: FqName, val areSubclassesAffected: Boolean) : ChangeInfo(fqName)
protected open fun toStringProperties(): String = "fqName = $fqName"
override fun toString(): String {
return this::class.java.simpleName + "(${toStringProperties()})"
}
}
private fun LocalFileKotlinClass.scopeFqName() =
when (classHeader.kind) {
KotlinClassHeader.Kind.CLASS -> className.fqNameForClassNameWithoutDollars
else -> className.packageFqName
}
fun ByteArray.md5(): Long {
val d = MessageDigest.getInstance("MD5").digest(this)!!
return ((d[0].toLong() and 0xFFL)
or ((d[1].toLong() and 0xFFL) shl 8)
or ((d[2].toLong() and 0xFFL) shl 16)
or ((d[3].toLong() and 0xFFL) shl 24)
or ((d[4].toLong() and 0xFFL) shl 32)
or ((d[5].toLong() and 0xFFL) shl 40)
or ((d[6].toLong() and 0xFFL) shl 48)
or ((d[7].toLong() and 0xFFL) shl 56)
)
}
@TestOnly
fun <K : Comparable<K>, V> Map<K, V>.dumpMap(dumpValue: (V)->String): String =
buildString {
append("{")
for (key in keys.sorted()) {
if (length != 1) {
append(", ")
}
val value = get(key)?.let(dumpValue) ?: "null"
append("$key -> $value")
}
append("}")
}
@TestOnly fun <T : Comparable<T>> Collection<T>.dumpCollection(): String =
"[${sorted().joinToString(", ", transform = Any::toString)}]"

View File

@@ -29,15 +29,12 @@ import java.io.File
import java.util.*
open class LookupStorage(private val targetDataDir: File) : BasicMapsOwner() {
open class LookupStorage(targetDataDir: File) : BasicMapsOwner(targetDataDir) {
companion object {
private val DELETED_TO_SIZE_TRESHOLD = 0.5
private val MINIMUM_GARBAGE_COLLECTIBLE_SIZE = 10000
}
private val String.storageFile: File
get() = File(targetDataDir, this + "." + CACHE_EXTENSION)
private val countersFile = "counters".storageFile
private val idToFile = registerMap(IdToFileMap("id-to-file".storageFile))
private val fileToId = registerMap(FileToIdMap("file-to-id".storageFile))
@@ -197,7 +194,7 @@ open class LookupStorage(private val targetDataDir: File) : BasicMapsOwner() {
}
class LookupTrackerImpl(private val delegate: LookupTracker) : LookupTracker {
val lookups = MultiMap<LookupSymbol, String>()
val lookups = MultiMap.createSet<LookupSymbol, String>()
val pathInterner = StringInterner()
private val interner = StringInterner()

View File

@@ -20,6 +20,7 @@ import org.jetbrains.kotlin.name.ClassId
import org.jetbrains.kotlin.serialization.ProtoBuf
import org.jetbrains.kotlin.serialization.deserialization.NameResolver
import org.jetbrains.kotlin.serialization.jvm.JvmProtoBuf
import org.jetbrains.kotlin.serialization.js.JsProtoBuf
import org.jetbrains.kotlin.utils.Interner
import java.util.*
@@ -56,6 +57,20 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkStringEquals(old.getExtension(JvmProtoBuf.packageModuleName), new.getExtension(JvmProtoBuf.packageModuleName))) return false
}
if (old.getExtensionCount(JvmProtoBuf.packageLocalVariable) != new.getExtensionCount(JvmProtoBuf.packageLocalVariable)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.packageLocalVariable) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.packageLocalVariable, i), new.getExtension(JvmProtoBuf.packageLocalVariable, i))) return false
}
}
if (old.hasExtension(JsProtoBuf.packageFqName) != new.hasExtension(JsProtoBuf.packageFqName)) return false
if (old.hasExtension(JsProtoBuf.packageFqName)) {
if (old.getExtension(JsProtoBuf.packageFqName) != new.getExtension(JsProtoBuf.packageFqName)) return false
}
return true
}
enum class ProtoBufPackageKind {
@@ -64,7 +79,9 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
TYPE_ALIAS_LIST,
TYPE_TABLE,
SINCE_KOTLIN_INFO_TABLE,
PACKAGE_MODULE_NAME
JVM_EXT_PACKAGE_MODULE_NAME,
JVM_EXT_PACKAGE_LOCAL_VARIABLE_LIST,
JS_EXT_PACKAGE_FQ_NAME
}
fun difference(old: ProtoBuf.Package, new: ProtoBuf.Package): EnumSet<ProtoBufPackageKind> {
@@ -86,9 +103,23 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEquals(old.sinceKotlinInfoTable, new.sinceKotlinInfoTable)) result.add(ProtoBufPackageKind.SINCE_KOTLIN_INFO_TABLE)
}
if (old.hasExtension(JvmProtoBuf.packageModuleName) != new.hasExtension(JvmProtoBuf.packageModuleName)) result.add(ProtoBufPackageKind.PACKAGE_MODULE_NAME)
if (old.hasExtension(JvmProtoBuf.packageModuleName) != new.hasExtension(JvmProtoBuf.packageModuleName)) result.add(ProtoBufPackageKind.JVM_EXT_PACKAGE_MODULE_NAME)
if (old.hasExtension(JvmProtoBuf.packageModuleName)) {
if (!checkStringEquals(old.getExtension(JvmProtoBuf.packageModuleName), new.getExtension(JvmProtoBuf.packageModuleName))) result.add(ProtoBufPackageKind.PACKAGE_MODULE_NAME)
if (!checkStringEquals(old.getExtension(JvmProtoBuf.packageModuleName), new.getExtension(JvmProtoBuf.packageModuleName))) result.add(ProtoBufPackageKind.JVM_EXT_PACKAGE_MODULE_NAME)
}
if (old.getExtensionCount(JvmProtoBuf.packageLocalVariable) != new.getExtensionCount(JvmProtoBuf.packageLocalVariable)) {
result.add(ProtoBufPackageKind.JVM_EXT_PACKAGE_LOCAL_VARIABLE_LIST)
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.packageLocalVariable) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.packageLocalVariable, i), new.getExtension(JvmProtoBuf.packageLocalVariable, i))) result.add(ProtoBufPackageKind.JVM_EXT_PACKAGE_LOCAL_VARIABLE_LIST)
}
}
if (old.hasExtension(JsProtoBuf.packageFqName) != new.hasExtension(JsProtoBuf.packageFqName)) result.add(ProtoBufPackageKind.JS_EXT_PACKAGE_FQ_NAME)
if (old.hasExtension(JsProtoBuf.packageFqName)) {
if (old.getExtension(JsProtoBuf.packageFqName) != new.getExtension(JsProtoBuf.packageFqName)) result.add(ProtoBufPackageKind.JS_EXT_PACKAGE_FQ_NAME)
}
return result
@@ -147,6 +178,29 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkStringEquals(old.getExtension(JvmProtoBuf.classModuleName), new.getExtension(JvmProtoBuf.classModuleName))) return false
}
if (old.getExtensionCount(JvmProtoBuf.classLocalVariable) != new.getExtensionCount(JvmProtoBuf.classLocalVariable)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.classLocalVariable) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.classLocalVariable, i), new.getExtension(JvmProtoBuf.classLocalVariable, i))) return false
}
}
if (old.getExtensionCount(JsProtoBuf.classAnnotation) != new.getExtensionCount(JsProtoBuf.classAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.classAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.classAnnotation, i), new.getExtension(JsProtoBuf.classAnnotation, i))) return false
}
}
if (old.hasExtension(JsProtoBuf.classContainingFileId) != new.hasExtension(JsProtoBuf.classContainingFileId)) return false
if (old.hasExtension(JsProtoBuf.classContainingFileId)) {
if (old.getExtension(JsProtoBuf.classContainingFileId) != new.getExtension(JsProtoBuf.classContainingFileId)) return false
}
return true
}
enum class ProtoBufClassKind {
@@ -166,7 +220,10 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
TYPE_TABLE,
SINCE_KOTLIN_INFO,
SINCE_KOTLIN_INFO_TABLE,
CLASS_MODULE_NAME
JVM_EXT_CLASS_MODULE_NAME,
JVM_EXT_CLASS_LOCAL_VARIABLE_LIST,
JS_EXT_CLASS_ANNOTATION_LIST,
JS_EXT_CLASS_CONTAINING_FILE_ID
}
fun difference(old: ProtoBuf.Class, new: ProtoBuf.Class): EnumSet<ProtoBufClassKind> {
@@ -219,9 +276,32 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEquals(old.sinceKotlinInfoTable, new.sinceKotlinInfoTable)) result.add(ProtoBufClassKind.SINCE_KOTLIN_INFO_TABLE)
}
if (old.hasExtension(JvmProtoBuf.classModuleName) != new.hasExtension(JvmProtoBuf.classModuleName)) result.add(ProtoBufClassKind.CLASS_MODULE_NAME)
if (old.hasExtension(JvmProtoBuf.classModuleName) != new.hasExtension(JvmProtoBuf.classModuleName)) result.add(ProtoBufClassKind.JVM_EXT_CLASS_MODULE_NAME)
if (old.hasExtension(JvmProtoBuf.classModuleName)) {
if (!checkStringEquals(old.getExtension(JvmProtoBuf.classModuleName), new.getExtension(JvmProtoBuf.classModuleName))) result.add(ProtoBufClassKind.CLASS_MODULE_NAME)
if (!checkStringEquals(old.getExtension(JvmProtoBuf.classModuleName), new.getExtension(JvmProtoBuf.classModuleName))) result.add(ProtoBufClassKind.JVM_EXT_CLASS_MODULE_NAME)
}
if (old.getExtensionCount(JvmProtoBuf.classLocalVariable) != new.getExtensionCount(JvmProtoBuf.classLocalVariable)) {
result.add(ProtoBufClassKind.JVM_EXT_CLASS_LOCAL_VARIABLE_LIST)
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.classLocalVariable) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.classLocalVariable, i), new.getExtension(JvmProtoBuf.classLocalVariable, i))) result.add(ProtoBufClassKind.JVM_EXT_CLASS_LOCAL_VARIABLE_LIST)
}
}
if (old.getExtensionCount(JsProtoBuf.classAnnotation) != new.getExtensionCount(JsProtoBuf.classAnnotation)) {
result.add(ProtoBufClassKind.JS_EXT_CLASS_ANNOTATION_LIST)
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.classAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.classAnnotation, i), new.getExtension(JsProtoBuf.classAnnotation, i))) result.add(ProtoBufClassKind.JS_EXT_CLASS_ANNOTATION_LIST)
}
}
if (old.hasExtension(JsProtoBuf.classContainingFileId) != new.hasExtension(JsProtoBuf.classContainingFileId)) result.add(ProtoBufClassKind.JS_EXT_CLASS_CONTAINING_FILE_ID)
if (old.hasExtension(JsProtoBuf.classContainingFileId)) {
if (old.getExtension(JsProtoBuf.classContainingFileId) != new.getExtension(JsProtoBuf.classContainingFileId)) result.add(ProtoBufClassKind.JS_EXT_CLASS_CONTAINING_FILE_ID)
}
return result
@@ -279,6 +359,20 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEquals(old.getExtension(JvmProtoBuf.methodSignature), new.getExtension(JvmProtoBuf.methodSignature))) return false
}
if (old.getExtensionCount(JsProtoBuf.functionAnnotation) != new.getExtensionCount(JsProtoBuf.functionAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.functionAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.functionAnnotation, i), new.getExtension(JsProtoBuf.functionAnnotation, i))) return false
}
}
if (old.hasExtension(JsProtoBuf.functionContainingFileId) != new.hasExtension(JsProtoBuf.functionContainingFileId)) return false
if (old.hasExtension(JsProtoBuf.functionContainingFileId)) {
if (old.getExtension(JsProtoBuf.functionContainingFileId) != new.getExtension(JsProtoBuf.functionContainingFileId)) return false
}
return true
}
@@ -342,6 +436,25 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEquals(old.getExtension(JvmProtoBuf.propertySignature), new.getExtension(JvmProtoBuf.propertySignature))) return false
}
if (old.getExtensionCount(JsProtoBuf.propertyAnnotation) != new.getExtensionCount(JsProtoBuf.propertyAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.propertyAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.propertyAnnotation, i), new.getExtension(JsProtoBuf.propertyAnnotation, i))) return false
}
}
if (old.hasExtension(JsProtoBuf.compileTimeValue) != new.hasExtension(JsProtoBuf.compileTimeValue)) return false
if (old.hasExtension(JsProtoBuf.compileTimeValue)) {
if (!checkEquals(old.getExtension(JsProtoBuf.compileTimeValue), new.getExtension(JsProtoBuf.compileTimeValue))) return false
}
if (old.hasExtension(JsProtoBuf.propertyContainingFileId) != new.hasExtension(JsProtoBuf.propertyContainingFileId)) return false
if (old.hasExtension(JsProtoBuf.propertyContainingFileId)) {
if (old.getExtension(JsProtoBuf.propertyContainingFileId) != new.getExtension(JsProtoBuf.propertyContainingFileId)) return false
}
return true
}
@@ -421,10 +534,22 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEqualsTypeParameterUpperBoundId(old, new)) return false
if (old.getExtensionCount(JvmProtoBuf.typeParameterAnnotation) != new.getExtensionCount(JvmProtoBuf.typeParameterAnnotation)) return false
if (old.getExtensionCount(JvmProtoBuf.typeParameterAnnotation) != new.getExtensionCount(JvmProtoBuf.typeParameterAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.typeParameterAnnotation) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.typeParameterAnnotation, i), new.getExtension(JvmProtoBuf.typeParameterAnnotation, i))) return false
}
}
for(i in 0..old.getExtensionCount(JvmProtoBuf.typeParameterAnnotation) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.typeParameterAnnotation, i), new.getExtension(JvmProtoBuf.typeParameterAnnotation, i))) return false
if (old.getExtensionCount(JsProtoBuf.typeParameterAnnotation) != new.getExtensionCount(JsProtoBuf.typeParameterAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.typeParameterAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.typeParameterAnnotation, i), new.getExtension(JsProtoBuf.typeParameterAnnotation, i))) return false
}
}
return true
@@ -498,10 +623,13 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (old.flags != new.flags) return false
}
if (old.getExtensionCount(JvmProtoBuf.typeAnnotation) != new.getExtensionCount(JvmProtoBuf.typeAnnotation)) return false
for(i in 0..old.getExtensionCount(JvmProtoBuf.typeAnnotation) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.typeAnnotation, i), new.getExtension(JvmProtoBuf.typeAnnotation, i))) return false
if (old.getExtensionCount(JvmProtoBuf.typeAnnotation) != new.getExtensionCount(JvmProtoBuf.typeAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JvmProtoBuf.typeAnnotation) - 1) {
if (!checkEquals(old.getExtension(JvmProtoBuf.typeAnnotation, i), new.getExtension(JvmProtoBuf.typeAnnotation, i))) return false
}
}
if (old.hasExtension(JvmProtoBuf.isRaw) != new.hasExtension(JvmProtoBuf.isRaw)) return false
@@ -509,6 +637,15 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (old.getExtension(JvmProtoBuf.isRaw) != new.getExtension(JvmProtoBuf.isRaw)) return false
}
if (old.getExtensionCount(JsProtoBuf.typeAnnotation) != new.getExtensionCount(JsProtoBuf.typeAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.typeAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.typeAnnotation, i), new.getExtension(JsProtoBuf.typeAnnotation, i))) return false
}
}
return true
}
@@ -530,6 +667,15 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkEquals(old.getExtension(JvmProtoBuf.constructorSignature), new.getExtension(JvmProtoBuf.constructorSignature))) return false
}
if (old.getExtensionCount(JsProtoBuf.constructorAnnotation) != new.getExtensionCount(JsProtoBuf.constructorAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.constructorAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.constructorAnnotation, i), new.getExtension(JsProtoBuf.constructorAnnotation, i))) return false
}
}
return true
}
@@ -539,6 +685,23 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (!checkStringEquals(old.name, new.name)) return false
}
if (old.getExtensionCount(JsProtoBuf.enumEntryAnnotation) != new.getExtensionCount(JsProtoBuf.enumEntryAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.enumEntryAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.enumEntryAnnotation, i), new.getExtension(JsProtoBuf.enumEntryAnnotation, i))) return false
}
}
return true
}
open fun checkEquals(old: ProtoBuf.Annotation, new: ProtoBuf.Annotation): Boolean {
if (!checkClassIdEquals(old.id, new.id)) return false
if (!checkEqualsAnnotationArgument(old, new)) return false
return true
}
@@ -570,6 +733,15 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
if (old.varargElementTypeId != new.varargElementTypeId) return false
}
if (old.getExtensionCount(JsProtoBuf.parameterAnnotation) != new.getExtensionCount(JsProtoBuf.parameterAnnotation)) {
return false
}
else {
for(i in 0..old.getExtensionCount(JsProtoBuf.parameterAnnotation) - 1) {
if (!checkEquals(old.getExtension(JsProtoBuf.parameterAnnotation, i), new.getExtension(JsProtoBuf.parameterAnnotation, i))) return false
}
}
return true
}
@@ -611,10 +783,48 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
return true
}
open fun checkEquals(old: ProtoBuf.Annotation, new: ProtoBuf.Annotation): Boolean {
if (!checkClassIdEquals(old.id, new.id)) return false
open fun checkEquals(old: ProtoBuf.Annotation.Argument.Value, new: ProtoBuf.Annotation.Argument.Value): Boolean {
if (old.hasType() != new.hasType()) return false
if (old.hasType()) {
if (old.type != new.type) return false
}
if (!checkEqualsAnnotationArgument(old, new)) return false
if (old.hasIntValue() != new.hasIntValue()) return false
if (old.hasIntValue()) {
if (old.intValue != new.intValue) return false
}
if (old.hasFloatValue() != new.hasFloatValue()) return false
if (old.hasFloatValue()) {
if (old.floatValue != new.floatValue) return false
}
if (old.hasDoubleValue() != new.hasDoubleValue()) return false
if (old.hasDoubleValue()) {
if (old.doubleValue != new.doubleValue) return false
}
if (old.hasStringValue() != new.hasStringValue()) return false
if (old.hasStringValue()) {
if (!checkStringEquals(old.stringValue, new.stringValue)) return false
}
if (old.hasClassId() != new.hasClassId()) return false
if (old.hasClassId()) {
if (!checkClassIdEquals(old.classId, new.classId)) return false
}
if (old.hasEnumValueId() != new.hasEnumValueId()) return false
if (old.hasEnumValueId()) {
if (!checkStringEquals(old.enumValueId, new.enumValueId)) return false
}
if (old.hasAnnotation() != new.hasAnnotation()) return false
if (old.hasAnnotation()) {
if (!checkEquals(old.annotation, new.annotation)) return false
}
if (!checkEqualsAnnotationArgumentValueArrayElement(old, new)) return false
return true
}
@@ -667,6 +877,14 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
return true
}
open fun checkEquals(old: ProtoBuf.Annotation.Argument, new: ProtoBuf.Annotation.Argument): Boolean {
if (!checkStringEquals(old.nameId, new.nameId)) return false
if (!checkEquals(old.value, new.value)) return false
return true
}
open fun checkEquals(old: JvmProtoBuf.JvmFieldSignature, new: JvmProtoBuf.JvmFieldSignature): Boolean {
if (old.hasName() != new.hasName()) return false
if (old.hasName()) {
@@ -681,60 +899,6 @@ open class ProtoCompareGenerated(val oldNameResolver: NameResolver, val newNameR
return true
}
open fun checkEquals(old: ProtoBuf.Annotation.Argument, new: ProtoBuf.Annotation.Argument): Boolean {
if (!checkStringEquals(old.nameId, new.nameId)) return false
if (!checkEquals(old.value, new.value)) return false
return true
}
open fun checkEquals(old: ProtoBuf.Annotation.Argument.Value, new: ProtoBuf.Annotation.Argument.Value): Boolean {
if (old.hasType() != new.hasType()) return false
if (old.hasType()) {
if (old.type != new.type) return false
}
if (old.hasIntValue() != new.hasIntValue()) return false
if (old.hasIntValue()) {
if (old.intValue != new.intValue) return false
}
if (old.hasFloatValue() != new.hasFloatValue()) return false
if (old.hasFloatValue()) {
if (old.floatValue != new.floatValue) return false
}
if (old.hasDoubleValue() != new.hasDoubleValue()) return false
if (old.hasDoubleValue()) {
if (old.doubleValue != new.doubleValue) return false
}
if (old.hasStringValue() != new.hasStringValue()) return false
if (old.hasStringValue()) {
if (!checkStringEquals(old.stringValue, new.stringValue)) return false
}
if (old.hasClassId() != new.hasClassId()) return false
if (old.hasClassId()) {
if (!checkClassIdEquals(old.classId, new.classId)) return false
}
if (old.hasEnumValueId() != new.hasEnumValueId()) return false
if (old.hasEnumValueId()) {
if (!checkStringEquals(old.enumValueId, new.enumValueId)) return false
}
if (old.hasAnnotation() != new.hasAnnotation()) return false
if (old.hasAnnotation()) {
if (!checkEquals(old.annotation, new.annotation)) return false
}
if (!checkEqualsAnnotationArgumentValueArrayElement(old, new)) return false
return true
}
open fun checkEqualsPackageFunction(old: ProtoBuf.Package, new: ProtoBuf.Package): Boolean {
if (old.functionCount != new.functionCount) return false
@@ -1053,6 +1217,14 @@ fun ProtoBuf.Package.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int)
hashCode = 31 * hashCode + stringIndexes(getExtension(JvmProtoBuf.packageModuleName))
}
for(i in 0..getExtensionCount(JvmProtoBuf.packageLocalVariable) - 1) {
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.packageLocalVariable, i).hashCode(stringIndexes, fqNameIndexes)
}
if (hasExtension(JsProtoBuf.packageFqName)) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.packageFqName)
}
return hashCode
}
@@ -1125,6 +1297,18 @@ fun ProtoBuf.Class.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) ->
hashCode = 31 * hashCode + stringIndexes(getExtension(JvmProtoBuf.classModuleName))
}
for(i in 0..getExtensionCount(JvmProtoBuf.classLocalVariable) - 1) {
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.classLocalVariable, i).hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..getExtensionCount(JsProtoBuf.classAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.classAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
if (hasExtension(JsProtoBuf.classContainingFileId)) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.classContainingFileId)
}
return hashCode
}
@@ -1177,6 +1361,14 @@ fun ProtoBuf.Function.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int)
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.methodSignature).hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..getExtensionCount(JsProtoBuf.functionAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.functionAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
if (hasExtension(JsProtoBuf.functionContainingFileId)) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.functionContainingFileId)
}
return hashCode
}
@@ -1233,6 +1425,18 @@ fun ProtoBuf.Property.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int)
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.propertySignature).hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..getExtensionCount(JsProtoBuf.propertyAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.propertyAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
if (hasExtension(JsProtoBuf.compileTimeValue)) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.compileTimeValue).hashCode(stringIndexes, fqNameIndexes)
}
if (hasExtension(JsProtoBuf.propertyContainingFileId)) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.propertyContainingFileId)
}
return hashCode
}
@@ -1327,6 +1531,10 @@ fun ProtoBuf.TypeParameter.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes:
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.typeParameterAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..getExtensionCount(JsProtoBuf.typeParameterAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.typeParameterAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
@@ -1397,6 +1605,10 @@ fun ProtoBuf.Type.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) ->
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.isRaw).hashCode()
}
for(i in 0..getExtensionCount(JsProtoBuf.typeAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.typeAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
@@ -1419,6 +1631,10 @@ fun ProtoBuf.Constructor.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (I
hashCode = 31 * hashCode + getExtension(JvmProtoBuf.constructorSignature).hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..getExtensionCount(JsProtoBuf.constructorAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.constructorAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
@@ -1429,6 +1645,22 @@ fun ProtoBuf.EnumEntry.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int
hashCode = 31 * hashCode + stringIndexes(name)
}
for(i in 0..getExtensionCount(JsProtoBuf.enumEntryAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.enumEntryAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
fun ProtoBuf.Annotation.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
hashCode = 31 * hashCode + fqNameIndexes(id)
for(i in 0..argumentCount - 1) {
hashCode = 31 * hashCode + getArgument(i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
@@ -1457,6 +1689,10 @@ fun ProtoBuf.ValueParameter.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes:
hashCode = 31 * hashCode + varargElementTypeId
}
for(i in 0..getExtensionCount(JsProtoBuf.parameterAnnotation) - 1) {
hashCode = 31 * hashCode + getExtension(JsProtoBuf.parameterAnnotation, i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}
@@ -1496,13 +1732,43 @@ fun JvmProtoBuf.JvmPropertySignature.hashCode(stringIndexes: (Int) -> Int, fqNam
return hashCode
}
fun ProtoBuf.Annotation.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
fun ProtoBuf.Annotation.Argument.Value.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
hashCode = 31 * hashCode + fqNameIndexes(id)
if (hasType()) {
hashCode = 31 * hashCode + type.hashCode()
}
for(i in 0..argumentCount - 1) {
hashCode = 31 * hashCode + getArgument(i).hashCode(stringIndexes, fqNameIndexes)
if (hasIntValue()) {
hashCode = 31 * hashCode + intValue.hashCode()
}
if (hasFloatValue()) {
hashCode = 31 * hashCode + floatValue.hashCode()
}
if (hasDoubleValue()) {
hashCode = 31 * hashCode + doubleValue.hashCode()
}
if (hasStringValue()) {
hashCode = 31 * hashCode + stringIndexes(stringValue)
}
if (hasClassId()) {
hashCode = 31 * hashCode + fqNameIndexes(classId)
}
if (hasEnumValueId()) {
hashCode = 31 * hashCode + stringIndexes(enumValueId)
}
if (hasAnnotation()) {
hashCode = 31 * hashCode + annotation.hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..arrayElementCount - 1) {
hashCode = 31 * hashCode + getArrayElement(i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
@@ -1552,6 +1818,16 @@ fun ProtoBuf.Type.Argument.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes:
return hashCode
}
fun ProtoBuf.Annotation.Argument.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
hashCode = 31 * hashCode + stringIndexes(nameId)
hashCode = 31 * hashCode + value.hashCode(stringIndexes, fqNameIndexes)
return hashCode
}
fun JvmProtoBuf.JvmFieldSignature.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
@@ -1565,55 +1841,3 @@ fun JvmProtoBuf.JvmFieldSignature.hashCode(stringIndexes: (Int) -> Int, fqNameIn
return hashCode
}
fun ProtoBuf.Annotation.Argument.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
hashCode = 31 * hashCode + stringIndexes(nameId)
hashCode = 31 * hashCode + value.hashCode(stringIndexes, fqNameIndexes)
return hashCode
}
fun ProtoBuf.Annotation.Argument.Value.hashCode(stringIndexes: (Int) -> Int, fqNameIndexes: (Int) -> Int): Int {
var hashCode = 1
if (hasType()) {
hashCode = 31 * hashCode + type.hashCode()
}
if (hasIntValue()) {
hashCode = 31 * hashCode + intValue.hashCode()
}
if (hasFloatValue()) {
hashCode = 31 * hashCode + floatValue.hashCode()
}
if (hasDoubleValue()) {
hashCode = 31 * hashCode + doubleValue.hashCode()
}
if (hasStringValue()) {
hashCode = 31 * hashCode + stringIndexes(stringValue)
}
if (hasClassId()) {
hashCode = 31 * hashCode + fqNameIndexes(classId)
}
if (hasEnumValueId()) {
hashCode = 31 * hashCode + stringIndexes(enumValueId)
}
if (hasAnnotation()) {
hashCode = 31 * hashCode + annotation.hashCode(stringIndexes, fqNameIndexes)
}
for(i in 0..arrayElementCount - 1) {
hashCode = 31 * hashCode + getArrayElement(i).hashCode(stringIndexes, fqNameIndexes)
}
return hashCode
}

View File

@@ -14,9 +14,6 @@
* limitations under the License.
*/
// these functions are used in the kotlin gradle plugin
@file:Suppress("unused")
package org.jetbrains.kotlin.incremental
import com.intellij.openapi.util.io.FileUtil
@@ -25,8 +22,6 @@ import org.jetbrains.kotlin.build.GeneratedFile
import org.jetbrains.kotlin.build.GeneratedJvmClass
import org.jetbrains.kotlin.build.JvmSourceRoot
import org.jetbrains.kotlin.build.isModuleMappingFile
import org.jetbrains.kotlin.compilerRunner.OutputItemsCollectorImpl
import org.jetbrains.kotlin.config.IncrementalCompilation
import org.jetbrains.kotlin.config.Services
import org.jetbrains.kotlin.incremental.components.LookupTracker
import org.jetbrains.kotlin.load.kotlin.incremental.components.IncrementalCache
@@ -35,21 +30,24 @@ import org.jetbrains.kotlin.modules.KotlinModuleXmlBuilder
import org.jetbrains.kotlin.modules.TargetId
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.progress.CompilationCanceledStatus
import org.jetbrains.kotlin.utils.keysToMap
import java.io.File
import java.util.*
fun Iterable<File>.javaSourceRoots(roots: Iterable<File>): Iterable<File> =
filter(File::isJavaFile).mapNotNull { findSrcDirRoot(it, roots) }
fun makeModuleFile(name: String, isTest: Boolean, outputDir: File, sourcesToCompile: Iterable<File>, javaSourceRoots: Iterable<File>, classpath: Iterable<File>, friendDirs: Iterable<File>): File {
fun makeModuleFile(
name: String,
isTest: Boolean,
outputDir: File,
sourcesToCompile: Iterable<File>,
javaSourceRoots: Iterable<JvmSourceRoot>,
classpath: Iterable<File>,
friendDirs: Iterable<File>
): File {
val builder = KotlinModuleXmlBuilder()
builder.addModule(
name,
outputDir.absolutePath,
sourcesToCompile,
javaSourceRoots.map { JvmSourceRoot(it) },
javaSourceRoots,
classpath,
null,
"java-production",
@@ -70,72 +68,27 @@ fun makeCompileServices(
compilationCanceledStatus: CompilationCanceledStatus?
): Services =
with(Services.Builder()) {
register(IncrementalCompilationComponents::class.java,
IncrementalCompilationComponentsImpl(incrementalCaches, lookupTracker))
register(LookupTracker::class.java, lookupTracker)
register(IncrementalCompilationComponents::class.java, IncrementalCompilationComponentsImpl(incrementalCaches))
compilationCanceledStatus?.let {
register(CompilationCanceledStatus::class.java, it)
}
build()
}
fun makeLookupTracker(parentLookupTracker: LookupTracker = LookupTracker.DO_NOTHING): LookupTracker =
if (IncrementalCompilation.isExperimental()) LookupTrackerImpl(parentLookupTracker)
else parentLookupTracker
fun<Target> makeIncrementalCachesMap(
targets: Iterable<Target>,
getDependencies: (Target) -> Iterable<Target>,
getCache: (Target) -> IncrementalCacheImpl<Target>,
getTargetId: Target.() -> TargetId
): Map<TargetId, IncrementalCacheImpl<Target>>
{
val dependents = targets.keysToMap { hashSetOf<Target>() }
val targetsWithDependents = targets.toHashSet()
for (target in targets) {
for (dependency in getDependencies(target)) {
if (dependency !in targets) continue
dependents[dependency]!!.add(target)
targetsWithDependents.add(target)
}
}
val caches = targetsWithDependents.keysToMap { getCache(it) }
for ((target, cache) in caches) {
dependents[target]?.forEach {
cache.addDependentCache(caches[it]!!)
}
}
return caches.mapKeys { it.key.getTargetId() }
}
fun<Target> updateIncrementalCaches(
targets: Iterable<Target>,
generatedFiles: List<GeneratedFile<Target>>,
compiledWithErrors: Boolean,
getIncrementalCache: (Target) -> IncrementalCacheImpl<Target>
): CompilationResult {
var changesInfo = CompilationResult.NO_CHANGES
fun updateIncrementalCache(
generatedFiles: Iterable<GeneratedFile>,
cache: IncrementalJvmCache,
changesCollector: ChangesCollector
) {
for (generatedFile in generatedFiles) {
val ic = getIncrementalCache(generatedFile.target)
when {
generatedFile is GeneratedJvmClass<Target> -> changesInfo += ic.saveFileToCache(generatedFile)
generatedFile.outputFile.isModuleMappingFile() -> changesInfo += ic.saveModuleMappingToCache(generatedFile.sourceFiles, generatedFile.outputFile)
generatedFile is GeneratedJvmClass -> cache.saveFileToCache(generatedFile, changesCollector)
generatedFile.outputFile.isModuleMappingFile() -> cache.saveModuleMappingToCache(generatedFile.sourceFiles, generatedFile.outputFile)
}
}
if (!compiledWithErrors) {
targets.forEach {
val newChangesInfo = getIncrementalCache(it).clearCacheForRemovedClasses()
changesInfo += newChangesInfo
}
}
return changesInfo
cache.clearCacheForRemovedClasses(changesCollector)
}
fun LookupStorage.update(
@@ -150,43 +103,19 @@ fun LookupStorage.update(
addAll(lookupTracker.lookups.entrySet(), lookupTracker.pathInterner.values)
}
fun<Target> OutputItemsCollectorImpl.generatedFiles(
targets: Collection<Target>,
representativeTarget: Target,
getSources: (Target) -> Iterable<File>,
getOutputDir: (Target) -> File?
): List<GeneratedFile<Target>> {
// If there's only one target, this map is empty: get() always returns null, and the representativeTarget will be used below
val sourceToTarget =
if (targets.size >1) targets.flatMap { target -> getSources(target).map { Pair(it, target) } }.toMap()
else mapOf<File, Target>()
return outputs.map { outputItem ->
val target =
outputItem.sourceFiles.firstOrNull()?.let { sourceToTarget[it] } ?:
targets.singleOrNull { getOutputDir(it)?.let { outputItem.outputFile.startsWith(it) } ?: false } ?:
representativeTarget
when (outputItem.outputFile.extension) {
"class" -> GeneratedJvmClass(target, outputItem.sourceFiles, outputItem.outputFile)
else -> GeneratedFile(target, outputItem.sourceFiles, outputItem.outputFile)
}
}
}
data class DirtyData(
val dirtyLookupSymbols: Collection<LookupSymbol> = emptyList(),
val dirtyClassesFqNames: Collection<FqName> = emptyList()
)
fun <Target> CompilationResult.getDirtyData(
caches: Iterable<IncrementalCacheImpl<Target>>,
fun ChangesCollector.getDirtyData(
caches: Iterable<IncrementalCacheCommon>,
reporter: ICReporter
): DirtyData {
val dirtyLookupSymbols = HashSet<LookupSymbol>()
val dirtyClassesFqNames = HashSet<FqName>()
for (change in changes) {
for (change in changes()) {
reporter.report { "Process $change" }
if (change is ChangeInfo.SignatureChanged) {
@@ -233,8 +162,8 @@ fun mapLookupSymbolsToFiles(
return dirtyFiles
}
fun <Target> mapClassesFqNamesToFiles(
caches: Iterable<IncrementalCacheImpl<Target>>,
fun mapClassesFqNamesToFiles(
caches: Iterable<IncrementalCacheCommon>,
classesFqNames: Iterable<FqName>,
reporter: ICReporter,
excludes: Set<File> = emptySet()
@@ -254,12 +183,9 @@ fun <Target> mapClassesFqNamesToFiles(
return dirtyFiles
}
private fun findSrcDirRoot(file: File, roots: Iterable<File>): File? =
roots.firstOrNull { FileUtil.isAncestor(it, file, false) }
fun <Target> withSubtypes(
fun withSubtypes(
typeFqName: FqName,
caches: Iterable<IncrementalCacheImpl<Target>>
caches: Iterable<IncrementalCacheCommon>
): Set<FqName> {
val types = LinkedList(listOf(typeFqName))
val subtypes = hashSetOf<FqName>()

View File

@@ -20,6 +20,7 @@ import org.jetbrains.kotlin.descriptors.Visibilities
import org.jetbrains.kotlin.incremental.ProtoCompareGenerated.ProtoBufClassKind
import org.jetbrains.kotlin.incremental.ProtoCompareGenerated.ProtoBufPackageKind
import org.jetbrains.kotlin.incremental.storage.ProtoMapValue
import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.protobuf.MessageLite
import org.jetbrains.kotlin.serialization.Flags
import org.jetbrains.kotlin.serialization.ProtoBuf
@@ -34,21 +35,19 @@ data class Difference(
val changedMembersNames: Set<String> = emptySet()
)
fun difference(oldData: ProtoMapValue, newData: ProtoMapValue): Difference {
if (!oldData.isPackageFacade && newData.isPackageFacade) return Difference(isClassAffected = true, areSubclassesAffected = true)
sealed class ProtoData
data class ClassProtoData(val proto: ProtoBuf.Class, val nameResolver: NameResolver) : ProtoData()
data class PackagePartProtoData(val proto: ProtoBuf.Package, val nameResolver: NameResolver, val packageFqName: FqName) : ProtoData()
if (oldData.isPackageFacade && !newData.isPackageFacade) return Difference(isClassAffected = true)
val differenceObject =
if (oldData.isPackageFacade) {
DifferenceCalculatorForPackageFacade(oldData, newData)
}
else {
DifferenceCalculatorForClass(oldData, newData)
}
return differenceObject.difference()
}
fun ProtoMapValue.toProtoData(packageFqName: FqName): ProtoData =
if (isPackageFacade) {
val packageData = JvmProtoBufUtil.readPackageDataFrom(bytes, strings)
PackagePartProtoData(packageData.packageProto, packageData.nameResolver, packageFqName)
}
else {
val classData = JvmProtoBufUtil.readClassDataFrom(bytes, strings)
ClassProtoData(classData.classProto, classData.nameResolver)
}
internal val MessageLite.isPrivate: Boolean
get() = Visibilities.isPrivate(Deserialization.visibility(
@@ -72,11 +71,8 @@ private fun MessageLite.name(nameResolver: NameResolver): String {
internal fun List<MessageLite>.names(nameResolver: NameResolver): List<String> = map { it.name(nameResolver) }
private abstract class DifferenceCalculator() {
protected abstract val oldNameResolver: NameResolver
protected abstract val newNameResolver: NameResolver
protected val compareObject by lazy { ProtoCompareGenerated(oldNameResolver, newNameResolver) }
abstract class DifferenceCalculator {
protected abstract val compareObject: ProtoCompareGenerated
abstract fun difference(): Difference
@@ -158,19 +154,18 @@ private abstract class DifferenceCalculator() {
}
}
private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: ProtoMapValue) : DifferenceCalculator() {
val oldClassData = JvmProtoBufUtil.readClassDataFrom(oldData.bytes, oldData.strings)
val newClassData = JvmProtoBufUtil.readClassDataFrom(newData.bytes, newData.strings)
val oldProto = oldClassData.classProto
val newProto = newClassData.classProto
override val oldNameResolver = oldClassData.nameResolver
override val newNameResolver = newClassData.nameResolver
val diff = compareObject.difference(oldProto, newProto)
class DifferenceCalculatorForClass(
private val oldData: ClassProtoData,
private val newData: ClassProtoData
) : DifferenceCalculator() {
override val compareObject = ProtoCompareGenerated(oldData.nameResolver, newData.nameResolver)
override fun difference(): Difference {
val (oldProto, oldNameResolver) = oldData
val (newProto, newNameResolver) = newData
val diff = compareObject.difference(oldProto, newProto)
var isClassAffected = false
var areSubclassesAffected = false
val names = hashSetOf<String>()
@@ -186,7 +181,8 @@ private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: Prot
}
for (kind in diff) {
when (kind!!) {
@Suppress("UNUSED_VARIABLE") // To make this 'when' exhaustive
val unused: Any = when (kind!!) {
ProtoBufClassKind.COMPANION_OBJECT_NAME -> {
if (oldProto.hasCompanionObjectName()) oldProto.companionObjectName.oldToNames()
if (newProto.hasCompanionObjectName()) newProto.companionObjectName.newToNames()
@@ -203,10 +199,7 @@ private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: Prot
}
ProtoBufClassKind.CONSTRUCTOR_LIST -> {
val differentNonPrivateConstructors = calcDifferenceForNonPrivateMembers(ProtoBuf.Class::getConstructorList)
if (differentNonPrivateConstructors.isNotEmpty()) {
isClassAffected = true
}
isClassAffected = isClassAffected || differentNonPrivateConstructors.isNotEmpty()
}
ProtoBufClassKind.FUNCTION_LIST ->
names.addAll(calcDifferenceForNonPrivateMembers(ProtoBuf.Class::getFunctionList))
@@ -218,7 +211,15 @@ private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: Prot
isClassAffected = true
}
ProtoBufClassKind.SEALED_SUBCLASS_FQ_NAME_LIST -> {
// TODO
isClassAffected = true
// Subclasses are considered to be affected to fix the case where
// an implementation is added to an nth-level (n > 1) sealed class.
// In case of the following hierarchy:
// Base <- Intermediate <- Impl
// the change of the SEALED_SUBCLASS_FQ_NAME_LIST will be detected in the Intermediate,
// but there can be usages, that should be rebuilt, without direct references to the Intermediate:
// when (x as Base) { is Impl -> ... }
areSubclassesAffected = true
}
ProtoBufClassKind.TYPE_TABLE -> {
// TODO
@@ -231,12 +232,17 @@ private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: Prot
ProtoBufClassKind.FQ_NAME,
ProtoBufClassKind.TYPE_PARAMETER_LIST,
ProtoBufClassKind.SUPERTYPE_LIST,
ProtoBufClassKind.SUPERTYPE_ID_LIST-> {
ProtoBufClassKind.SUPERTYPE_ID_LIST,
ProtoBufClassKind.JS_EXT_CLASS_ANNOTATION_LIST -> {
isClassAffected = true
areSubclassesAffected = true
}
ProtoBufClassKind.CLASS_MODULE_NAME -> {
// TODO
ProtoBufClassKind.JVM_EXT_CLASS_MODULE_NAME,
ProtoBufClassKind.JS_EXT_CLASS_CONTAINING_FILE_ID -> {
// TODO
}
ProtoBufClassKind.JVM_EXT_CLASS_LOCAL_VARIABLE_LIST -> {
// Not affected, local variables are not accessible outside of a file
}
}
}
@@ -245,19 +251,18 @@ private class DifferenceCalculatorForClass(oldData: ProtoMapValue, newData: Prot
}
}
private class DifferenceCalculatorForPackageFacade(oldData: ProtoMapValue, newData: ProtoMapValue) : DifferenceCalculator() {
val oldPackageData = JvmProtoBufUtil.readPackageDataFrom(oldData.bytes, oldData.strings)
val newPackageData = JvmProtoBufUtil.readPackageDataFrom(newData.bytes, newData.strings)
val oldProto = oldPackageData.packageProto
val newProto = newPackageData.packageProto
override val oldNameResolver = oldPackageData.nameResolver
override val newNameResolver = newPackageData.nameResolver
val diff = compareObject.difference(oldProto, newProto)
class DifferenceCalculatorForPackageFacade(
private val oldData: PackagePartProtoData,
private val newData: PackagePartProtoData
) : DifferenceCalculator() {
override val compareObject = ProtoCompareGenerated(oldData.nameResolver, newData.nameResolver)
override fun difference(): Difference {
val oldProto = oldData.proto
val newProto = newData.proto
val diff = compareObject.difference(oldProto, newProto)
val names = hashSetOf<String>()
fun calcDifferenceForNonPrivateMembers(members: (ProtoBuf.Package) -> List<MessageLite>): Collection<String> {
@@ -267,7 +272,8 @@ private class DifferenceCalculatorForPackageFacade(oldData: ProtoMapValue, newDa
}
for (kind in diff) {
when (kind!!) {
@Suppress("UNUSED_VARIABLE") // To make this 'when' exhaustive
val unused: Any = when (kind!!) {
ProtoBufPackageKind.FUNCTION_LIST ->
names.addAll(calcDifferenceForNonPrivateMembers(ProtoBuf.Package::getFunctionList))
ProtoBufPackageKind.PROPERTY_LIST ->
@@ -276,10 +282,13 @@ private class DifferenceCalculatorForPackageFacade(oldData: ProtoMapValue, newDa
names.addAll(calcDifferenceForNonPrivateMembers(ProtoBuf.Package::getTypeAliasList))
ProtoBufPackageKind.TYPE_TABLE,
ProtoBufPackageKind.SINCE_KOTLIN_INFO_TABLE,
ProtoBufPackageKind.PACKAGE_MODULE_NAME -> {
ProtoBufPackageKind.JVM_EXT_PACKAGE_MODULE_NAME,
ProtoBufPackageKind.JS_EXT_PACKAGE_FQ_NAME-> {
// TODO
}
else -> throw IllegalArgumentException("Unsupported kind: $kind")
ProtoBufPackageKind.JVM_EXT_PACKAGE_LOCAL_VARIABLE_LIST -> {
// Not affected, local variables are not accessible outside of a file
}
}
}

View File

@@ -17,14 +17,18 @@
package org.jetbrains.kotlin.incremental.storage
import org.jetbrains.annotations.TestOnly
import java.io.File
open class BasicMapsOwner {
open class BasicMapsOwner(val cachesDir: File) {
private val maps = arrayListOf<BasicMap<*, *>>()
companion object {
val CACHE_EXTENSION = "tab"
}
protected val String.storageFile: File
get() = File(cachesDir, this + "." + CACHE_EXTENSION)
protected fun <K, V, M : BasicMap<K, V>> registerMap(map: M): M {
maps.add(map)
return map

View File

@@ -87,7 +87,7 @@ class LazyStorage<K, V>(
try {
storage?.close()
}
catch (ignored: IOException) {
catch (ignored: Throwable) {
}
PersistentHashMap.deleteFilesStartingWith(storageFile)

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2010-2016 JetBrains s.r.o.
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -17,22 +17,25 @@
package org.jetbrains.kotlin
import com.intellij.openapi.util.io.FileUtil
import junit.framework.TestCase
import org.junit.After
import org.junit.Before
import java.io.File
import kotlin.properties.Delegates
abstract class TestWithWorkingDir {
abstract class TestWithWorkingDir : TestCase() {
protected var workingDir: File by Delegates.notNull()
private set
@Before
open fun setUp() {
workingDir = FileUtil.createTempDirectory(this::class.java.simpleName, null)
public override fun setUp() {
super.setUp()
workingDir = FileUtil.createTempDirectory(this::class.java.simpleName, null, /* deleteOnExit = */ true)
}
@After
open fun tearDown() {
public override fun tearDown() {
workingDir.deleteRecursively()
super.tearDown()
}
}

View File

@@ -18,15 +18,15 @@ package org.jetbrains.kotlin.incremental.testingUtils
import java.io.File
class BuildLogFinder(
private val isExperimentalEnabled: Boolean = false,
data class BuildLogFinder(
private val isDataContainerBuildLogEnabled: Boolean = false,
private val isGradleEnabled: Boolean = false
private val isGradleEnabled: Boolean = false,
private val isJsEnabled: Boolean = false
) {
companion object {
private const val JS_LOG = "js-build.log"
private const val GRADLE_LOG = "gradle-build.log"
private const val DATA_CONTAINER_LOG = "data-container-version-build.log"
private const val EXPERIMENTAL_LOG = "experimental-ic-build.log"
private const val SIMPLE_LOG = "build.log"
}
@@ -34,9 +34,9 @@ class BuildLogFinder(
val names = dir.list() ?: arrayOf()
val files = names.filter { File(dir, it).isFile }.toSet()
val matchedName = when {
isJsEnabled && JS_LOG in files -> JS_LOG
isGradleEnabled && GRADLE_LOG in files -> GRADLE_LOG
isDataContainerBuildLogEnabled && DATA_CONTAINER_LOG in files -> DATA_CONTAINER_LOG
isExperimentalEnabled && EXPERIMENTAL_LOG in files -> EXPERIMENTAL_LOG
SIMPLE_LOG in files -> SIMPLE_LOG
else -> null
}

View File

@@ -128,13 +128,13 @@ fun getModificationsToPerform(
}
abstract class Modification(val path: String) {
abstract fun perform(workDir: File, mapping: MutableMap<File, File>)
abstract fun perform(workDir: File, mapping: MutableMap<File, File>): File?
override fun toString(): String = "${this::class.java.simpleName} $path"
}
class ModifyContent(path: String, val dataFile: File) : Modification(path) {
override fun perform(workDir: File, mapping: MutableMap<File, File>) {
override fun perform(workDir: File, mapping: MutableMap<File, File>): File? {
val file = File(workDir, path)
val oldLastModified = file.lastModified()
@@ -148,11 +148,12 @@ class ModifyContent(path: String, val dataFile: File) : Modification(path) {
}
mapping[file] = dataFile
return file
}
}
class TouchFile(path: String, private val touchPolicy: TouchPolicy) : Modification(path) {
override fun perform(workDir: File, mapping: MutableMap<File, File>) {
override fun perform(workDir: File, mapping: MutableMap<File, File>): File? {
val file = File(workDir, path)
when (touchPolicy) {
@@ -166,16 +167,18 @@ class TouchFile(path: String, private val touchPolicy: TouchPolicy) : Modificati
}
}
return file
}
}
class DeleteFile(path: String) : Modification(path) {
override fun perform(workDir: File, mapping: MutableMap<File, File>) {
override fun perform(workDir: File, mapping: MutableMap<File, File>): File? {
val fileToDelete = File(workDir, path)
if (!fileToDelete.delete()) {
throw AssertionError("Couldn't delete $fileToDelete")
}
mapping.remove(fileToDelete)
return null
}
}

View File

@@ -9743,7 +9743,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
boolean hasFlags();
@@ -9757,7 +9757,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
int getFlags();
@@ -10465,7 +10465,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -10481,7 +10481,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -11826,7 +11826,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -11842,7 +11842,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -11858,7 +11858,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public Builder setFlags(int value) {
@@ -11877,7 +11877,7 @@ public final class DebugProtoBuf {
*ClassKind
*isInner
*isData
*isHeader
*isExpect
* </pre>
*/
public Builder clearFlags() {
@@ -17734,7 +17734,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
boolean hasFlags();
@@ -17752,7 +17752,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
int getFlags();
@@ -18097,7 +18097,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -18117,7 +18117,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -18930,7 +18930,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -18950,7 +18950,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -18970,7 +18970,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public Builder setFlags(int value) {
@@ -18993,7 +18993,7 @@ public final class DebugProtoBuf {
*isTailrec
*isExternal
*isSuspend
*isHeader
*isExpect
* </pre>
*/
public Builder clearFlags() {
@@ -20039,7 +20039,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
boolean hasFlags();
@@ -20059,7 +20059,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
int getFlags();
@@ -20417,7 +20417,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -20439,7 +20439,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -21239,7 +21239,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public boolean hasFlags() {
@@ -21261,7 +21261,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public int getFlags() {
@@ -21283,7 +21283,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public Builder setFlags(int value) {
@@ -21308,7 +21308,7 @@ public final class DebugProtoBuf {
*hasConstant
*isExternal
*isDelegated
*isHeader
*isExpect
* </pre>
*/
public Builder clearFlags() {
@@ -22202,8 +22202,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22213,8 +22213,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22419,8 +22419,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22432,8 +22432,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22913,8 +22913,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22926,8 +22926,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22939,8 +22939,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>
@@ -22955,8 +22955,8 @@ public final class DebugProtoBuf {
* <code>optional int32 flags = 1 [default = 0];</code>
*
* <pre>
*declaresDefault
*hasAnnotations
*declaresDefault
*isCrossinline
*isNoinline
* </pre>

View File

@@ -14,7 +14,9 @@ public final class DebugJvmProtoBuf {
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.isRaw);
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.typeParameterAnnotation);
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.classModuleName);
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.classLocalVariable);
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.packageModuleName);
registry.add(org.jetbrains.kotlin.serialization.jvm.DebugJvmProtoBuf.packageLocalVariable);
}
public interface StringTableTypesOrBuilder extends
// @@protoc_insertion_point(interface_extends:org.jetbrains.kotlin.serialization.jvm.StringTableTypes)
@@ -4586,6 +4588,17 @@ public final class DebugJvmProtoBuf {
.newFileScopedGeneratedExtension(
java.lang.Integer.class,
null);
public static final int CLASS_LOCAL_VARIABLE_FIELD_NUMBER = 102;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Class { ... }</code>
*/
public static final
org.jetbrains.kotlin.protobuf.GeneratedMessage.GeneratedExtension<
org.jetbrains.kotlin.serialization.DebugProtoBuf.Class,
java.util.List<org.jetbrains.kotlin.serialization.DebugProtoBuf.Property>> classLocalVariable = org.jetbrains.kotlin.protobuf.GeneratedMessage
.newFileScopedGeneratedExtension(
org.jetbrains.kotlin.serialization.DebugProtoBuf.Property.class,
org.jetbrains.kotlin.serialization.DebugProtoBuf.Property.getDefaultInstance());
public static final int PACKAGE_MODULE_NAME_FIELD_NUMBER = 101;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Package { ... }</code>
@@ -4597,6 +4610,17 @@ public final class DebugJvmProtoBuf {
.newFileScopedGeneratedExtension(
java.lang.Integer.class,
null);
public static final int PACKAGE_LOCAL_VARIABLE_FIELD_NUMBER = 102;
/**
* <code>extend .org.jetbrains.kotlin.serialization.Package { ... }</code>
*/
public static final
org.jetbrains.kotlin.protobuf.GeneratedMessage.GeneratedExtension<
org.jetbrains.kotlin.serialization.DebugProtoBuf.Package,
java.util.List<org.jetbrains.kotlin.serialization.DebugProtoBuf.Property>> packageLocalVariable = org.jetbrains.kotlin.protobuf.GeneratedMessage
.newFileScopedGeneratedExtension(
org.jetbrains.kotlin.serialization.DebugProtoBuf.Property.class,
org.jetbrains.kotlin.serialization.DebugProtoBuf.Property.getDefaultInstance());
private static final org.jetbrains.kotlin.protobuf.Descriptors.Descriptor
internal_static_org_jetbrains_kotlin_serialization_jvm_StringTableTypes_descriptor;
private static
@@ -4678,9 +4702,15 @@ public final class DebugJvmProtoBuf {
"g.jetbrains.kotlin.serialization.Annotat" +
"ion:J\n\021class_module_name\022).org.jetbrains" +
".kotlin.serialization.Class\030e \001(\005B\004\230\265\030\001:" +
"N\n\023package_module_name\022+.org.jetbrains.k" +
"otlin.serialization.Package\030e \001(\005B\004\230\265\030\001B" +
"\022B\020DebugJvmProtoBuf"
"u\n\024class_local_variable\022).org.jetbrains." +
"kotlin.serialization.Class\030f \003(\0132,.org.j" +
"etbrains.kotlin.serialization.Property:N",
"\n\023package_module_name\022+.org.jetbrains.ko" +
"tlin.serialization.Package\030e \001(\005B\004\230\265\030\001:y" +
"\n\026package_local_variable\022+.org.jetbrains" +
".kotlin.serialization.Package\030f \003(\0132,.or" +
"g.jetbrains.kotlin.serialization.Propert" +
"yB\022B\020DebugJvmProtoBuf"
};
org.jetbrains.kotlin.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner =
new org.jetbrains.kotlin.protobuf.Descriptors.FileDescriptor. InternalDescriptorAssigner() {
@@ -4733,7 +4763,9 @@ public final class DebugJvmProtoBuf {
isRaw.internalInit(descriptor.getExtensions().get(4));
typeParameterAnnotation.internalInit(descriptor.getExtensions().get(5));
classModuleName.internalInit(descriptor.getExtensions().get(6));
packageModuleName.internalInit(descriptor.getExtensions().get(7));
classLocalVariable.internalInit(descriptor.getExtensions().get(7));
packageModuleName.internalInit(descriptor.getExtensions().get(8));
packageLocalVariable.internalInit(descriptor.getExtensions().get(9));
org.jetbrains.kotlin.protobuf.ExtensionRegistry registry =
org.jetbrains.kotlin.protobuf.ExtensionRegistry.newInstance();
registry.add(org.jetbrains.kotlin.serialization.DebugExtOptionsProtoBuf.stringIdInTable);

View File

@@ -61,10 +61,11 @@
<pathelement location="${tools.jar}"/>
<fileset dir="${basedir}/lib" includes="**/*.jar"/>
<fileset dir="${dependencies}" includes="jline3.jar"/>
<fileset dir="${dependencies}" includes="jansi.jar"/>
<fileset dir="${dependencies}" includes="jline.jar"/>
<fileset dir="${dependencies}" includes="javaslang-2.0.6.jar"/>
<fileset dir="${dependencies}" includes="json-org.jar"/>
<fileset dir="${dependencies}" includes="kotlinx-coroutines-core.jar"/>
<fileset dir="${basedir}/ideaSDK/jps" includes="jps-model.jar"/>
</path>
@@ -386,23 +387,26 @@
<zipgroupfileset dir="${basedir}/lib" includes="*.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/annotations.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/asm-all.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/guava-19.0.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/guava-21.0.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/intellij-core.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/jdom.jar" excludes="META-INF/jb/** META-INF/LICENSE"/>
<zipfileset src="${basedir}/ideaSDK/core/jna.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/log4j.jar" excludes="META-INF/jb/** META-INF/LICENSE"/>
<zipfileset src="${basedir}/ideaSDK/core/picocontainer.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/snappy-in-java-0.5.1.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/streamex-0.6.2.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/trove4j.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/xpp3-1.1.4-min.jar"/>
<zipfileset src="${basedir}/ideaSDK/core/xstream-1.4.8.jar"/>
<zipfileset src="${idea.sdk}/lib/jna-platform.jar"/>
<zipfileset src="${idea.sdk}/lib/oromatcher.jar" excludes="META-INF/jb/** META-INF/LICENSE"/>
<zipfileset src="${idea.sdk}/jps/jps-model.jar"/>
<zipfileset src="${dependencies}/jline.jar"/>
<zipfileset src="${idea.sdk}/jps/jps-model.jar" excludes="META-INF/services/**"/>
<zipfileset src="${dependencies}/jline3.jar"/>
<zipfileset src="${dependencies}/jansi.jar"/>
<zipfileset src="${dependencies}/javaslang-2.0.6.jar"/>
<zipfileset src="${dependencies}/json-org.jar"/>
<zipfileset src="${protobuf.jar}"/>
<zipfileset src="${dependencies}/kotlinx-coroutines-core.jar"/>
<manifest>
<attribute name="Built-By" value="${manifest.impl.vendor}"/>
@@ -554,6 +558,8 @@
<pathelement path="build-common/test"/>
<pathelement path="compiler/incremental-compilation-impl/test"/>
</src>
<exclude name="**/*Generated.java"/>
<classpath>
<pathelement path="${bootstrap.runtime}"/>
<pathelement path="${bootstrap.reflect}"/>
@@ -653,9 +659,11 @@
<skip pattern="kotlin/Metadata"/>
<src>
<pathelement path="plugins/android-extensions/android-extensions-compiler/src"/>
<pathelement path="plugins/android-extensions/android-extensions-runtime/src"/>
</src>
<classpath>
<pathelement path="${idea.sdk}/core/intellij-core.jar"/>
<pathelement path="${idea.sdk}/plugins/android/lib/layoutlib.jar"/>
<pathelement path="${kotlin-home}/lib/kotlin-compiler.jar"/>
</classpath>
</javac2>
@@ -667,6 +675,28 @@
</jar>
</target>
<target name="android-extensions-runtime">
<cleandir dir="${output}/classes/android-extensions/android-extensions-runtime"/>
<javac2 destdir="${output}/classes/android-extensions/android-extensions-runtime" debug="true" debuglevel="lines,vars,source" includeAntRuntime="false">
<withKotlin modulename="kotlin-android-extensions-runtime">
<compilerarg value="-version"/>
</withKotlin>
<skip pattern="kotlin/Metadata"/>
<src>
<pathelement path="plugins/android-extensions/android-extensions-runtime/src"/>
</src>
<classpath>
<pathelement path="${idea.sdk}/plugins/android/lib/layoutlib.jar"/>
</classpath>
</javac2>
<jar destfile="${kotlin-home}/lib/android-extensions-runtime.jar">
<fileset dir="${output}/classes/android-extensions/android-extensions-runtime"/>
<zipfileset file="${kotlin-home}/build.txt" prefix="META-INF"/>
</jar>
</target>
<target name="allopen-compiler-plugin">
<cleandir dir="${output}/classes/allopen-compiler-plugin"/>
<javac2 destdir="${output}/classes/allopen-compiler-plugin" debug="true" debuglevel="lines,vars,source" includeAntRuntime="false">
@@ -953,7 +983,7 @@
depends="gradle-runtime,mock-runtime-for-test"/>
<target name="other-artifacts"
depends="android-extensions-compiler,allopen-compiler-plugin,noarg-compiler-plugin,sam-with-receiver-compiler-plugin,source-sections-compiler-plugin,annotation-processing,daemon-client,compiler-client-embeddable,kotlin-build-common-test" />
depends="android-extensions-compiler,android-extensions-runtime,allopen-compiler-plugin,noarg-compiler-plugin,sam-with-receiver-compiler-plugin,source-sections-compiler-plugin,annotation-processing,daemon-client,compiler-client-embeddable,kotlin-build-common-test" />
<target name="dist"
depends="clean,init,prepare-dist,preloader,runner,serialize-builtins,compiler-fork,compiler-sources,ant-tools,runtime,other-artifacts"

View File

@@ -3,9 +3,11 @@
buildscript {
repositories {
jcenter()
google()
}
dependencies {
classpath 'com.android.tools.build:gradle:2.2.3'
classpath 'com.android.tools.build:gradle:3.0.0-beta4'
// NOTE: Do not place your application dependencies here; they belong
// in the individual module build.gradle files
@@ -15,11 +17,12 @@ apply plugin: 'com.android.application'
repositories {
jcenter()
google()
}
android {
compileSdkVersion 19
buildToolsVersion "23.0.3"
buildToolsVersion "26.0.1"
defaultConfig {
applicationId "org.jetbrains.kotlin.android.tests"
@@ -64,7 +67,7 @@ android {
dexOptions {
dexInProcess false
javaMaxHeapSize "300m"
javaMaxHeapSize "600m"
//default is 4 and Total Memory = maxProcessCount * javaMaxHeapSize
maxProcessCount 1
additionalParameters "--debug"

View File

@@ -1,2 +1,4 @@
#don't try to download android specific tools within gradle: licence acceptance will be required
android.builder.sdkDownload=false
android.builder.sdkDownload=false
android.enableAapt2=false
android.enableD8=false

View File

@@ -41,19 +41,19 @@ public class SDKDownloader {
//NOTE: PLATFORM_TOOLS 23.1.0 requires only 64 bit build agents
private static final String PLATFORM_TOOLS = "23.0.1";
private static final String SDK_TOOLS = "25.1.1";
public static final String BUILD_TOOLS = "23.0.3";
public static final String BUILD_TOOLS = "26.0.1";
private static final int ANDROID_VERSION = 19;
public static final String GRADLE_VERSION = "2.14.1";
public static final String GRADLE_VERSION = "4.1";
public SDKDownloader(PathManager pathManager) {
this.pathManager = pathManager;
platformZipPath = pathManager.getRootForDownload() + "/platforms.zip";
platformZipPath = pathManager.getRootForDownload() + "/platform" + ANDROID_VERSION + ".zip";
armImage = pathManager.getRootForDownload() + "/arm-image.zip";
x86Image = pathManager.getRootForDownload() + "/x86-image.zip";
platformToolsZipPath = pathManager.getRootForDownload() + "/platform-tools.zip";
skdToolsZipPath = pathManager.getRootForDownload() + "/tools.zip";
buildToolsZipPath = pathManager.getRootForDownload() + "/build-tools.zip";
platformToolsZipPath = pathManager.getRootForDownload() + "/platform-tools" + PLATFORM_TOOLS + ".zip";
skdToolsZipPath = pathManager.getRootForDownload() + "/tools" + SDK_TOOLS + ".zip";
buildToolsZipPath = pathManager.getRootForDownload() + "/build-tools" + BUILD_TOOLS + ".zip";
gradleZipPath = pathManager.getRootForDownload() + "/gradle" + GRADLE_VERSION + ".zip";
}
@@ -127,7 +127,7 @@ public class SDKDownloader {
String buildToolsFolder = buildTools + BUILD_TOOLS + "/";
new File(buildToolsFolder).delete();
unzip(buildToolsZipPath, buildTools);
new File(buildTools + "/android-6.0").renameTo(new File(buildToolsFolder));
new File(buildTools + "/android-8.0.0").renameTo(new File(buildToolsFolder));
}
public void deleteAll() {

View File

@@ -33,6 +33,7 @@ public class GradleRunner {
listOfCommands = new ArrayList<>();
String cmdName = SystemInfo.isWindows ? "gradle.bat" : "gradle";
listOfCommands.add(pathManager.getGradleBinFolder() + "/" + cmdName);
listOfCommands.add("--no-daemon");
listOfCommands.add("--build-file");
listOfCommands.add(pathManager.getTmpFolder() + "/build.gradle");
}

View File

@@ -17,6 +17,8 @@
package org.jetbrains.kotlin.android.tests;
import com.google.common.collect.Lists;
import com.intellij.openapi.Disposable;
import com.intellij.openapi.util.Disposer;
import com.intellij.openapi.util.io.FileUtil;
import com.intellij.openapi.util.io.FileUtilRt;
import com.intellij.openapi.util.text.StringUtil;
@@ -28,6 +30,7 @@ import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment;
import org.jetbrains.kotlin.codegen.CodegenTestFiles;
import org.jetbrains.kotlin.codegen.GenerationUtils;
import org.jetbrains.kotlin.codegen.forTestCompile.ForTestCompileRuntime;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.config.CommonConfigurationKeys;
import org.jetbrains.kotlin.config.CompilerConfiguration;
import org.jetbrains.kotlin.config.JVMConfigurationKeys;
@@ -145,14 +148,16 @@ public class CodegenTestsOnAndroidGenerator extends KtUsefulTestCase {
public List<KtFile> files = new ArrayList<>();
private KotlinCoreEnvironment environment;
private Disposable disposable;
private FilesWriter(boolean isFullJdkAndRuntime, boolean inheritMultifileParts) {
this.isFullJdkAndRuntime = isFullJdkAndRuntime;
this.inheritMultifileParts = inheritMultifileParts;
this.environment = createEnvironment(isFullJdkAndRuntime);
this.disposable = new TestDisposable();
this.environment = createEnvironment(isFullJdkAndRuntime, disposable);
}
private KotlinCoreEnvironment createEnvironment(boolean isFullJdkAndRuntime) {
private KotlinCoreEnvironment createEnvironment(boolean isFullJdkAndRuntime, @NotNull Disposable disposable) {
ConfigurationKind configurationKind = isFullJdkAndRuntime ? ConfigurationKind.ALL : ConfigurationKind.NO_KOTLIN_REFLECT;
TestJdkKind testJdkKind = isFullJdkAndRuntime ? TestJdkKind.FULL_JDK : TestJdkKind.MOCK_JDK;
CompilerConfiguration configuration =
@@ -161,7 +166,7 @@ public class CodegenTestsOnAndroidGenerator extends KtUsefulTestCase {
if (inheritMultifileParts) {
configuration.put(JVMConfigurationKeys.INHERIT_MULTIFILE_PARTS, true);
}
return KotlinCoreEnvironment.createForTests(myTestRootDisposable, configuration, EnvironmentConfigFiles.JVM_CONFIG_FILES);
return KotlinCoreEnvironment.createForTests(disposable, configuration, EnvironmentConfigFiles.JVM_CONFIG_FILES);
}
public boolean shouldWriteFilesOnDisk() {
@@ -177,7 +182,11 @@ public class CodegenTestsOnAndroidGenerator extends KtUsefulTestCase {
public void writeFilesOnDisk() {
writeFiles(files);
files = new ArrayList<>();
environment = createEnvironment(isFullJdkAndRuntime);
if (disposable != null) {
Disposer.dispose(disposable);
disposable = new TestDisposable();
}
environment = createEnvironment(isFullJdkAndRuntime, disposable);
}
public void addFile(String name, String content) {
@@ -202,12 +211,19 @@ public class CodegenTestsOnAndroidGenerator extends KtUsefulTestCase {
? " (JVM.INHERIT_MULTIFILE_PARTS)"
: isFullJdkAndRuntime ? " (full jdk and runtime)" : "") + " into " + outputDir.getName() + "...");
OutputFileCollection outputFiles;
GenerationState state = null;
try {
outputFiles = GenerationUtils.compileFiles(filesToCompile, environment).getFactory();
state = GenerationUtils.compileFiles(filesToCompile, environment);
outputFiles = state.getFactory();
}
catch (Throwable e) {
throw new RuntimeException(e);
}
finally {
if (state != null) {
state.destroy();
}
}
if (!outputDir.exists()) {
outputDir.mkdirs();

View File

@@ -122,6 +122,7 @@ public class SpecialFiles {
// KT-8120
excludedFiles.add("closureOfInnerLocalClass.kt");
excludedFiles.add("closureWithSelfInstantiation.kt");
excludedFiles.add("quotedClassName.kt");
}
private SpecialFiles() {

View File

@@ -156,10 +156,9 @@ object CodegenUtil {
}
@JvmStatic
fun constructFakeFunctionCall(project: Project, referencedFunction: FunctionDescriptor): KtCallExpression {
val fakeFunctionCall = StringBuilder("callableReferenceFakeCall(")
fakeFunctionCall.append(referencedFunction.valueParameters.joinToString(", ") { "p${it.index}" })
fakeFunctionCall.append(")")
return KtPsiFactory(project, markGenerated = false).createExpression(fakeFunctionCall.toString()) as KtCallExpression
fun constructFakeFunctionCall(project: Project, arity: Int): KtCallExpression {
val fakeFunctionCall =
(1..arity).joinToString(prefix = "callableReferenceFakeCall(", separator = ", ", postfix = ")") { "p$it" }
return KtPsiFactory(project, markGenerated = false).createExpression(fakeFunctionCall) as KtCallExpression
}
}

View File

@@ -19,13 +19,22 @@ package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.descriptors.ReceiverParameterDescriptor
import org.jetbrains.kotlin.psi.KtSuperExpression
import org.jetbrains.kotlin.types.KotlinType
abstract class AccessorForPropertyBackingField(property: PropertyDescriptor,
type: KotlinType,
receiverType: KotlinType?,
dispatchReceiver: ReceiverParameterDescriptor?,
containingDeclaration: DeclarationDescriptor,
suffix: String
) : AccessorForPropertyDescriptor(property, type, receiverType, dispatchReceiver, containingDeclaration, null, suffix)
class AccessorForPropertyBackingField(
property: PropertyDescriptor,
containingDeclaration: DeclarationDescriptor,
delegateType: KotlinType?,
extensionReceiverParameter: ReceiverParameterDescriptor?,
dispatchReceiverParameter: ReceiverParameterDescriptor?,
nameSuffix: String,
val fieldAccessorKind: FieldAccessorKind
) : AccessorForPropertyDescriptor(
property,
delegateType ?: property.type,
extensionReceiverParameter?.type,
dispatchReceiverParameter,
containingDeclaration,
null,
nameSuffix
)

View File

@@ -1,28 +0,0 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.resolve.DescriptorUtils
class AccessorForPropertyBackingFieldFromLocal(property: PropertyDescriptor,
containingDeclaration: DeclarationDescriptor,
nameSuffix: String
) : AccessorForPropertyBackingField(property, property.type,
DescriptorUtils.getReceiverParameterType(property.extensionReceiverParameter),
property.dispatchReceiverParameter, containingDeclaration, nameSuffix)

View File

@@ -1,27 +0,0 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.descriptors.DeclarationDescriptor
import org.jetbrains.kotlin.descriptors.PropertyDescriptor
import org.jetbrains.kotlin.types.KotlinType
class AccessorForPropertyBackingFieldInClassCompanion(property: PropertyDescriptor,
containingDeclaration: DeclarationDescriptor,
delegationType: KotlinType?,
nameSuffix: String
) : AccessorForPropertyBackingField(property, delegationType ?: property.type, null, null, containingDeclaration, nameSuffix)

View File

@@ -16,6 +16,7 @@
package org.jetbrains.kotlin.codegen;
import kotlin.collections.CollectionsKt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.codegen.annotation.WrappedAnnotated;
@@ -25,6 +26,7 @@ import org.jetbrains.kotlin.descriptors.annotations.*;
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor;
import org.jetbrains.kotlin.load.java.JvmAnnotationNames;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.resolve.AnnotationChecker;
import org.jetbrains.kotlin.resolve.constants.*;
import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt;
@@ -291,32 +293,27 @@ public abstract class AnnotationCodegen {
@Nullable
private String genAnnotation(@NotNull AnnotationDescriptor annotationDescriptor) {
ClassifierDescriptor classifierDescriptor = getAnnotationClass(annotationDescriptor);
assert classifierDescriptor != null : "Annotation descriptor has no class: " + annotationDescriptor;
RetentionPolicy rp = getRetentionPolicy(classifierDescriptor);
ClassDescriptor classDescriptor = getAnnotationClass(annotationDescriptor);
assert classDescriptor != null : "Annotation descriptor has no class: " + annotationDescriptor;
RetentionPolicy rp = getRetentionPolicy(classDescriptor);
if (rp == RetentionPolicy.SOURCE && !typeMapper.getClassBuilderMode().generateSourceRetentionAnnotations) {
return null;
}
String descriptor = typeMapper.mapType(annotationDescriptor.getType()).getDescriptor();
innerClassConsumer.addInnerClassInfoFromAnnotation(classDescriptor);
if (classifierDescriptor instanceof ClassDescriptor) {
innerClassConsumer.addInnerClassInfoFromAnnotation(((ClassDescriptor) classifierDescriptor));
}
AnnotationVisitor annotationVisitor = visitAnnotation(descriptor, rp == RetentionPolicy.RUNTIME);
String asmTypeDescriptor = typeMapper.mapType(annotationDescriptor.getType()).getDescriptor();
AnnotationVisitor annotationVisitor = visitAnnotation(asmTypeDescriptor, rp == RetentionPolicy.RUNTIME);
genAnnotationArguments(annotationDescriptor, annotationVisitor);
annotationVisitor.visitEnd();
return descriptor;
return asmTypeDescriptor;
}
private void genAnnotationArguments(AnnotationDescriptor annotationDescriptor, AnnotationVisitor annotationVisitor) {
for (Map.Entry<ValueParameterDescriptor, ConstantValue<?>> entry : annotationDescriptor.getAllValueArguments().entrySet()) {
ValueParameterDescriptor descriptor = entry.getKey();
String name = descriptor.getName().asString();
genCompileTimeValue(name, entry.getValue(), annotationVisitor);
for (Map.Entry<Name, ConstantValue<?>> entry : annotationDescriptor.getAllValueArguments().entrySet()) {
genCompileTimeValue(entry.getKey().asString(), entry.getValue(), annotationVisitor);
}
}
@@ -475,16 +472,13 @@ public abstract class AnnotationCodegen {
}
AnnotationDescriptor retentionAnnotation = descriptor.getAnnotations().findAnnotation(new FqName(Retention.class.getName()));
if (retentionAnnotation != null) {
Collection<ConstantValue<?>> valueArguments = retentionAnnotation.getAllValueArguments().values();
if (!valueArguments.isEmpty()) {
ConstantValue<?> compileTimeConstant = valueArguments.iterator().next();
if (compileTimeConstant instanceof EnumValue) {
ClassDescriptor enumEntry = ((EnumValue) compileTimeConstant).getValue();
KotlinType classObjectType = DescriptorUtilsKt.getClassValueType(enumEntry);
if (classObjectType != null) {
if ("java/lang/annotation/RetentionPolicy".equals(typeMapper.mapType(classObjectType).getInternalName())) {
return RetentionPolicy.valueOf(enumEntry.getName().asString());
}
ConstantValue<?> compileTimeConstant = CollectionsKt.firstOrNull(retentionAnnotation.getAllValueArguments().values());
if (compileTimeConstant instanceof EnumValue) {
ClassDescriptor enumEntry = ((EnumValue) compileTimeConstant).getValue();
KotlinType classObjectType = DescriptorUtilsKt.getClassValueType(enumEntry);
if (classObjectType != null) {
if ("java/lang/annotation/RetentionPolicy".equals(typeMapper.mapType(classObjectType).getInternalName())) {
return RetentionPolicy.valueOf(enumEntry.getName().asString());
}
}
}

View File

@@ -38,10 +38,10 @@ import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.lexer.KtTokens;
import org.jetbrains.kotlin.load.java.JavaVisibilities;
import org.jetbrains.kotlin.load.java.JvmAnnotationNames;
import org.jetbrains.kotlin.name.ClassId;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.protobuf.MessageLite;
import org.jetbrains.kotlin.renderer.DescriptorRenderer;
import org.jetbrains.kotlin.resolve.DeprecationUtilKt;
import org.jetbrains.kotlin.resolve.DescriptorUtils;
import org.jetbrains.kotlin.resolve.annotations.AnnotationUtilKt;
import org.jetbrains.kotlin.resolve.inline.InlineUtil;
@@ -139,16 +139,16 @@ public class AsmUtil {
return primitiveTypeByBoxedType.get(boxedType);
}
public static boolean isBoxedTypeOf(@NotNull Type boxedType, @NotNull Type unboxedType) {
return unboxPrimitiveTypeOrNull(boxedType) == unboxedType;
}
public static boolean isIntPrimitive(Type type) {
return type == Type.INT_TYPE || type == Type.SHORT_TYPE || type == Type.BYTE_TYPE || type == Type.CHAR_TYPE;
}
public static boolean isNumberPrimitiveOrBoolean(Type type) {
return isNumberPrimitive(type) || type.getSort() == Type.BOOLEAN;
}
public static boolean isNumberPrimitive(Type type) {
return isIntPrimitive(type) || type == Type.FLOAT_TYPE || type == Type.DOUBLE_TYPE || type == Type.LONG_TYPE;
public static boolean isIntOrLongPrimitive(Type type) {
return isIntPrimitive(type) || type == Type.LONG_TYPE;
}
public static boolean isPrimitive(Type type) {
@@ -202,7 +202,7 @@ public class AsmUtil {
}
public static int getMethodAsmFlags(FunctionDescriptor functionDescriptor, OwnerKind kind, GenerationState state) {
int flags = getCommonCallableFlags(functionDescriptor);
int flags = getCommonCallableFlags(functionDescriptor, state);
for (AnnotationCodegen.JvmFlagAnnotation flagAnnotation : AnnotationCodegen.METHOD_FLAGS) {
if (flagAnnotation.hasAnnotation(functionDescriptor.getOriginal())) {
@@ -243,17 +243,11 @@ public class AsmUtil {
return flags;
}
public static int getCommonCallableFlags(FunctionDescriptor functionDescriptor) {
public static int getCommonCallableFlags(FunctionDescriptor functionDescriptor, @NotNull GenerationState state) {
int flags = getVisibilityAccessFlag(functionDescriptor);
flags |= getVarargsFlag(functionDescriptor);
flags |= getDeprecatedAccessFlag(functionDescriptor);
if (DeprecationUtilKt.isDeprecatedHidden(functionDescriptor, LanguageVersionSettingsImpl.DEFAULT)
|| functionDescriptor instanceof PropertyAccessorDescriptor
&& DeprecationUtilKt.isDeprecatedHidden(
((PropertyAccessorDescriptor) functionDescriptor).getCorrespondingProperty(),
LanguageVersionSettingsImpl.DEFAULT
)
) {
if (state.getDeprecationProvider().isDeprecatedHidden(functionDescriptor)) {
flags |= ACC_SYNTHETIC;
}
return flags;
@@ -353,7 +347,9 @@ public class AsmUtil {
DeclarationDescriptor containingDeclaration = memberDescriptor.getContainingDeclaration();
Visibility memberVisibility = memberDescriptor.getVisibility();
if (isEffectivelyInlineOnly(memberDescriptor)) return ACC_PRIVATE;
if (isEffectivelyInlineOnly(memberDescriptor)) {
return ACC_PRIVATE;
}
if (memberVisibility == Visibilities.LOCAL && memberDescriptor instanceof CallableMemberDescriptor) {
return ACC_PUBLIC;
@@ -657,8 +653,23 @@ public class AsmUtil {
// currently when resuming a suspend function we pass default values instead of real arguments (i.e. nulls for references)
if (descriptor.isSuspend()) return;
// Private method is not accessible from other classes, no assertions needed
if (getVisibilityAccessFlag(descriptor) == ACC_PRIVATE) return;
if (getVisibilityAccessFlag(descriptor) == ACC_PRIVATE) {
// Private method is not accessible from other classes, no assertions needed,
// unless we have a private operator function, in which we should generate a parameter assertion for an extension receiver.
// HACK: this provides "fail fast" behavior for operator functions.
// Such functions can be invoked in operator conventions desugaring,
// which is currently done on ad hoc basis in ExpressionCodegen.
if (state.isReceiverAssertionsDisabled()) return;
if (descriptor.isOperator()) {
ReceiverParameterDescriptor receiverParameter = descriptor.getExtensionReceiverParameter();
if (receiverParameter != null) {
genParamAssertion(v, state.getTypeMapper(), frameMap, receiverParameter, "$receiver");
}
}
return;
}
ReceiverParameterDescriptor receiverParameter = descriptor.getExtensionReceiverParameter();
if (receiverParameter != null) {
@@ -674,18 +685,19 @@ public class AsmUtil {
@NotNull InstructionAdapter v,
@NotNull KotlinTypeMapper typeMapper,
@NotNull FrameMap frameMap,
@NotNull CallableDescriptor parameter,
@NotNull ParameterDescriptor parameter,
@NotNull String name
) {
KotlinType type = parameter.getReturnType();
if (type == null || isNullableType(type)) return;
KotlinType type = parameter.getType();
if (isNullableType(type)) return;
int index = frameMap.getIndex(parameter);
Type asmType = typeMapper.mapType(type);
if (asmType.getSort() == Type.OBJECT || asmType.getSort() == Type.ARRAY) {
v.load(index, asmType);
v.visitLdcInsn(name);
v.invokestatic(IntrinsicMethods.INTRINSICS_CLASS_NAME, "checkParameterIsNotNull",
String checkMethod = "checkParameterIsNotNull";
v.invokestatic(IntrinsicMethods.INTRINSICS_CLASS_NAME, checkMethod,
"(Ljava/lang/Object;Ljava/lang/String;)V", false);
}
}
@@ -708,7 +720,7 @@ public class AsmUtil {
if (innerType.getSort() == Type.OBJECT || innerType.getSort() == Type.ARRAY) {
v.dup();
v.visitLdcInsn(runtimeAssertionInfo.getMessage());
v.invokestatic("kotlin/jvm/internal/Intrinsics", "checkExpressionValueIsNotNull",
v.invokestatic(IntrinsicMethods.INTRINSICS_CLASS_NAME, "checkExpressionValueIsNotNull",
"(Ljava/lang/Object;Ljava/lang/String;)V", false);
}
StackValue.coerce(innerType, type, v);
@@ -895,6 +907,11 @@ public class AsmUtil {
return Type.getObjectType(internalNameByFqNameWithoutInnerClasses(fqName));
}
@NotNull
public static Type asmTypeByClassId(@NotNull ClassId classId) {
return Type.getObjectType(classId.asString().replace('.', '$'));
}
@NotNull
public static String internalNameByFqNameWithoutInnerClasses(@NotNull FqName fqName) {
return JvmClassName.byFqNameWithoutInnerClasses(fqName).getInternalName();

View File

@@ -0,0 +1,308 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen
import com.intellij.psi.tree.IElementType
import org.jetbrains.kotlin.lexer.KtTokens
import org.jetbrains.org.objectweb.asm.Label
import org.jetbrains.org.objectweb.asm.Type
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter
abstract class NumberLikeCompare(
left: StackValue,
right: StackValue,
operandType: Type,
private val opToken: IElementType
) : BranchedValue(left, right, operandType, NumberCompare.getNumberCompareOpcode(opToken)) {
override fun patchOpcode(opcode: Int, v: InstructionAdapter): Int =
NumberCompare.patchOpcode(opcode, v, opToken, operandType)
}
abstract class SafeCallFusedWithPrimitiveEqualityBase(
opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue
) : NumberLikeCompare(left, right, operandType, opToken) {
private val trueIfEqual = opToken == KtTokens.EQEQ || opToken == KtTokens.EQEQEQ
protected abstract fun cleanupOnNullReceiver(v: InstructionAdapter)
override fun condJump(jumpLabel: Label, v: InstructionAdapter, jumpIfFalse: Boolean) {
val endLabel = Label()
arg1.put(operandType, v)
arg2!!.put(operandType, v)
v.visitJumpInsn(patchOpcode(if (jumpIfFalse) opcode else negatedOperations[opcode]!!, v), jumpLabel)
v.goTo(endLabel)
cleanupOnNullReceiver(v)
if (jumpIfFalse == trueIfEqual) {
v.goTo(jumpLabel)
}
v.mark(endLabel)
}
override fun putSelector(type: Type, v: InstructionAdapter) {
val falseLabel = Label()
val endLabel = Label()
arg1.put(operandType, v)
arg2!!.put(operandType, v)
v.visitJumpInsn(patchOpcode(opcode, v), falseLabel)
if (!trueIfEqual) {
val trueLabel = Label()
v.goTo(trueLabel)
cleanupOnNullReceiver(v)
v.mark(trueLabel)
}
v.iconst(1)
v.goTo(endLabel)
if (trueIfEqual) {
cleanupOnNullReceiver(v)
}
v.mark(falseLabel)
v.iconst(0)
v.mark(endLabel)
coerceTo(type, v)
}
}
class SafeCallToPrimitiveEquality(
opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue,
private val safeReceiverType: Type,
private val safeReceiverIsNull: Label
) : SafeCallFusedWithPrimitiveEqualityBase(opToken, operandType, left, right) {
override fun cleanupOnNullReceiver(v: InstructionAdapter) {
v.mark(safeReceiverIsNull)
AsmUtil.pop(v, safeReceiverType)
}
}
class PrimitiveToSafeCallEquality(
opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue,
private val safeReceiverType: Type,
private val safeReceiverIsNull: Label
) : SafeCallFusedWithPrimitiveEqualityBase(opToken, operandType, left, right) {
override fun cleanupOnNullReceiver(v: InstructionAdapter) {
v.mark(safeReceiverIsNull)
AsmUtil.pop(v, safeReceiverType)
AsmUtil.pop(v, arg1.type)
}
}
class BoxedToPrimitiveEquality private constructor(
leftBoxed: StackValue,
rightPrimitive: StackValue,
primitiveType: Type,
private val frameMap: FrameMap
) : NumberLikeCompare(leftBoxed, rightPrimitive, primitiveType, KtTokens.EQEQ) {
private val boxedType = arg1.type
override fun condJump(jumpLabel: Label, v: InstructionAdapter, jumpIfFalse: Boolean) {
if (arg2!!.canHaveSideEffects()) {
val tmp = frameMap.enterTemp(operandType)
doJump(
v, jumpLabel, jumpIfFalse,
{
arg1.put(boxedType, v)
arg2.put(operandType, v)
v.store(tmp, operandType)
},
{ v.load(tmp, operandType) }
)
frameMap.leaveTemp(operandType)
}
else {
doJump(
v, jumpLabel, jumpIfFalse,
{ arg1.put(boxedType, v) },
{ arg2.put(operandType, v) }
)
}
}
private inline fun doJump(
v: InstructionAdapter,
jumpLabel: Label,
jumpIfFalse: Boolean,
putArg1: () -> Unit,
putArg2: () -> Unit
) {
val notNullLabel = Label()
val endLabel = Label()
putArg1()
AsmUtil.dup(v, boxedType)
v.ifnonnull(notNullLabel)
AsmUtil.pop(v, boxedType)
if (jumpIfFalse) v.goTo(jumpLabel) else v.goTo(endLabel)
v.mark(notNullLabel)
coerce(boxedType, operandType, v)
putArg2()
v.visitJumpInsn(patchOpcode(if (jumpIfFalse) opcode else negatedOperations[opcode]!!, v), jumpLabel)
v.mark(endLabel)
}
companion object {
@JvmStatic
fun create(
opToken: IElementType,
left: StackValue,
leftType: Type,
right: StackValue,
rightType: Type,
frameMap: FrameMap
): BranchedValue =
if (!isApplicable(opToken, leftType, rightType))
throw IllegalArgumentException("Not applicable for $opToken, $leftType, $rightType")
else when (opToken) {
KtTokens.EQEQ -> BoxedToPrimitiveEquality(left, right, rightType, frameMap)
KtTokens.EXCLEQ -> Invert(BoxedToPrimitiveEquality(left, right, rightType, frameMap))
else -> throw AssertionError("Unexpected opToken: $opToken")
}
@JvmStatic
fun isApplicable(opToken: IElementType, leftType: Type, rightType: Type) =
(opToken == KtTokens.EQEQ || opToken == KtTokens.EXCLEQ) &&
AsmUtil.isIntOrLongPrimitive(rightType) &&
AsmUtil.isBoxedTypeOf(leftType, rightType)
}
}
abstract class PrimitiveToSomethingEquality
protected constructor(
leftPrimitive: StackValue,
right: StackValue,
primitiveType: Type
) : NumberLikeCompare(leftPrimitive, right, primitiveType, KtTokens.EQEQ) {
protected val primitiveType = leftPrimitive.type
protected val rightType = right.type
override fun condJump(jumpLabel: Label, v: InstructionAdapter, jumpIfFalse: Boolean) {
val notNullLabel = Label()
val endLabel = Label()
arg1.put(primitiveType, v)
arg2!!.put(rightType, v)
AsmUtil.dup(v, rightType)
jumpIfCanCompareTopWithPrimitive(v, notNullLabel)
AsmUtil.pop(v, rightType)
AsmUtil.pop(v, primitiveType)
if (jumpIfFalse) v.goTo(jumpLabel) else v.goTo(endLabel)
v.mark(notNullLabel)
coerceRightToPrimitive(v)
v.visitJumpInsn(patchOpcode(if (jumpIfFalse) opcode else negatedOperations[opcode]!!, v), jumpLabel)
v.mark(endLabel)
}
protected abstract fun jumpIfCanCompareTopWithPrimitive(v: InstructionAdapter, label: Label)
protected abstract fun coerceRightToPrimitive(v: InstructionAdapter)
}
class PrimitiveToBoxedEquality private constructor(
leftPrimitive: StackValue,
rightBoxed: StackValue,
primitiveType: Type
) : PrimitiveToSomethingEquality(leftPrimitive, rightBoxed, primitiveType) {
private val boxedType = rightBoxed.type
override fun jumpIfCanCompareTopWithPrimitive(v: InstructionAdapter, label: Label) {
v.ifnonnull(label)
}
override fun coerceRightToPrimitive(v: InstructionAdapter) {
coerce(boxedType, primitiveType, v)
}
companion object {
@JvmStatic
fun create(opToken: IElementType, left: StackValue, leftType: Type, right: StackValue, rightType: Type): BranchedValue =
if (!isApplicable(opToken, leftType, rightType))
throw IllegalArgumentException("Not applicable for $opToken, $leftType, $rightType")
else when (opToken) {
KtTokens.EQEQ -> PrimitiveToBoxedEquality(left, right, leftType)
KtTokens.EXCLEQ -> Invert(PrimitiveToBoxedEquality(left, right, leftType))
else -> throw AssertionError("Unexpected opToken: $opToken")
}
@JvmStatic
fun isApplicable(opToken: IElementType, leftType: Type, rightType: Type) =
(opToken == KtTokens.EQEQ || opToken == KtTokens.EXCLEQ) &&
AsmUtil.isIntOrLongPrimitive(leftType) &&
AsmUtil.isBoxedTypeOf(rightType, leftType)
}
}
class PrimitiveToObjectEquality private constructor(
leftPrimitive: StackValue,
rightObject: StackValue,
primitiveType: Type
) : PrimitiveToSomethingEquality(leftPrimitive, rightObject, primitiveType) {
private val boxedType = AsmUtil.boxType(primitiveType)
override fun jumpIfCanCompareTopWithPrimitive(v: InstructionAdapter, label: Label) {
v.instanceOf(boxedType)
v.ifne(label)
}
override fun coerceRightToPrimitive(v: InstructionAdapter) {
coerce(rightType, boxedType, v)
coerce(boxedType, primitiveType, v)
}
companion object {
@JvmStatic
fun create(opToken: IElementType, left: StackValue, leftType: Type, right: StackValue, rightType: Type): BranchedValue =
if (!isApplicable(opToken, leftType, rightType))
throw IllegalArgumentException("Not applicable for $opToken, $leftType, $rightType")
else when (opToken) {
KtTokens.EQEQ -> PrimitiveToObjectEquality(left, right, leftType)
KtTokens.EXCLEQ -> Invert(PrimitiveToObjectEquality(left, right, leftType))
else -> throw AssertionError("Unexpected opToken: $opToken")
}
@JvmStatic
fun isApplicable(opToken: IElementType, leftType: Type, rightType: Type) =
(opToken == KtTokens.EQEQ || opToken == KtTokens.EXCLEQ) &&
AsmUtil.isIntOrLongPrimitive(leftType) &&
rightType.sort == Type.OBJECT
}
}

View File

@@ -54,9 +54,7 @@ open class BranchedValue(
condJump(jumpLabel, v, jumpIfFalse)
}
protected open fun patchOpcode(opcode: Int, v: InstructionAdapter): Int {
return opcode
}
protected open fun patchOpcode(opcode: Int, v: InstructionAdapter): Int = opcode
companion object {
val negatedOperations = hashMapOf<Int, Int>()
@@ -120,13 +118,9 @@ open class BranchedValue(
negatedOperations.put(negatedOp, op)
}
fun booleanConstant(value: Boolean): BranchedValue {
return if (value) TRUE else FALSE
}
fun booleanConstant(value: Boolean): BranchedValue = if (value) TRUE else FALSE
fun createInvertValue(argument: StackValue): StackValue {
return Invert(condJump(argument))
}
fun createInvertValue(argument: StackValue): StackValue = Invert(condJump(argument))
fun condJump(condition: StackValue, label: Label, jumpIfFalse: Boolean, iv: InstructionAdapter) {
condJump(condition).condJump(label, iv, jumpIfFalse)
@@ -136,14 +130,11 @@ open class BranchedValue(
condJump(condition).loopJump(label, iv, jumpIfFalse)
}
fun condJump(condition: StackValue): CondJump {
return CondJump(if (condition is BranchedValue) {
condition
}
else {
BranchedValue(condition, null, Type.BOOLEAN_TYPE, IFEQ)
}, IFEQ)
}
fun condJump(condition: StackValue): CondJump =
CondJump(
condition as? BranchedValue ?: BranchedValue(condition, null, Type.BOOLEAN_TYPE, IFEQ),
IFEQ
)
fun cmp(opToken: IElementType, operandType: Type, left: StackValue, right: StackValue): StackValue =
if (operandType.sort == Type.OBJECT)
@@ -203,7 +194,7 @@ class CondJump(val condition: BranchedValue, op: Int) : BranchedValue(condition,
}
class NumberCompare(
val opToken: IElementType,
private val opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue
@@ -213,17 +204,15 @@ class NumberCompare(
patchOpcode(opcode, v, opToken, operandType)
companion object {
fun getNumberCompareOpcode(opToken: IElementType): Int {
return when (opToken) {
KtTokens.EQEQ, KtTokens.EQEQEQ -> IFNE
KtTokens.EXCLEQ, KtTokens.EXCLEQEQEQ -> IFEQ
KtTokens.GT -> IFLE
KtTokens.GTEQ -> IFLT
KtTokens.LT -> IFGE
KtTokens.LTEQ -> IFGT
else -> {
throw UnsupportedOperationException("Don't know how to generate this condJump: " + opToken)
}
fun getNumberCompareOpcode(opToken: IElementType): Int = when (opToken) {
KtTokens.EQEQ, KtTokens.EQEQEQ -> IFNE
KtTokens.EXCLEQ, KtTokens.EXCLEQEQEQ -> IFEQ
KtTokens.GT -> IFLE
KtTokens.GTEQ -> IFLT
KtTokens.LT -> IFGE
KtTokens.LTEQ -> IFGT
else -> {
throw UnsupportedOperationException("Don't know how to generate this condJump: " + opToken)
}
}
@@ -258,100 +247,11 @@ class ObjectCompare(
) : BranchedValue(left, right, operandType, ObjectCompare.getObjectCompareOpcode(opToken)) {
companion object {
fun getObjectCompareOpcode(opToken: IElementType): Int {
return when (opToken) {
KtTokens.EQEQEQ -> IF_ACMPNE
KtTokens.EXCLEQEQEQ -> IF_ACMPEQ
else -> throw UnsupportedOperationException("don't know how to generate this condjump")
}
fun getObjectCompareOpcode(opToken: IElementType): Int = when (opToken) {
KtTokens.EQEQEQ -> IF_ACMPNE
KtTokens.EXCLEQEQEQ -> IF_ACMPEQ
else -> throw UnsupportedOperationException("don't know how to generate this condjump")
}
}
}
abstract class SafeCallFusedWithPrimitiveEqualityBase(
val opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue
) : BranchedValue(left, right, operandType, NumberCompare.getNumberCompareOpcode(opToken)) {
private val trueIfEqual = opToken == KtTokens.EQEQ || opToken == KtTokens.EQEQEQ
protected abstract fun cleanupOnNullReceiver(v: InstructionAdapter)
override fun patchOpcode(opcode: Int, v: InstructionAdapter): Int =
NumberCompare.patchOpcode(opcode, v, opToken, operandType)
override fun condJump(jumpLabel: Label, v: InstructionAdapter, jumpIfFalse: Boolean) {
val endLabel = Label()
arg1.put(operandType, v)
arg2!!.put(operandType, v)
v.visitJumpInsn(patchOpcode(if (jumpIfFalse) opcode else negatedOperations[opcode]!!, v), jumpLabel)
v.goTo(endLabel)
cleanupOnNullReceiver(v)
if (jumpIfFalse == trueIfEqual) {
v.goTo(jumpLabel)
}
v.mark(endLabel)
}
override fun putSelector(type: Type, v: InstructionAdapter) {
val falseLabel = Label()
val endLabel = Label()
arg1.put(operandType, v)
arg2!!.put(operandType, v)
v.visitJumpInsn(patchOpcode(opcode, v), falseLabel)
if (!trueIfEqual) {
val trueLabel = Label()
v.goTo(trueLabel)
cleanupOnNullReceiver(v)
v.mark(trueLabel)
}
v.iconst(1)
v.goTo(endLabel)
if (trueIfEqual) {
cleanupOnNullReceiver(v)
}
v.mark(falseLabel)
v.iconst(0)
v.mark(endLabel)
coerceTo(type, v)
}
}
class SafeCallToPrimitiveEquality(
opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue,
val safeReceiverType: Type,
val safeReceiverIsNull: Label
) : SafeCallFusedWithPrimitiveEqualityBase(opToken, operandType, left, right) {
override fun cleanupOnNullReceiver(v: InstructionAdapter) {
v.mark(safeReceiverIsNull)
AsmUtil.pop(v, safeReceiverType)
}
}
class PrimitiveToSafeCallEquality(
opToken: IElementType,
operandType: Type,
left: StackValue,
right: StackValue,
val safeReceiverType: Type,
val safeReceiverIsNull: Label
) : SafeCallFusedWithPrimitiveEqualityBase(opToken, operandType, left, right) {
override fun cleanupOnNullReceiver(v: InstructionAdapter) {
v.mark(safeReceiverIsNull)
AsmUtil.pop(v, safeReceiverType)
AsmUtil.pop(v, arg1.type)
}
}

View File

@@ -28,7 +28,7 @@ import org.jetbrains.org.objectweb.asm.Type;
import java.util.List;
import static org.jetbrains.kotlin.codegen.StackValue.createDefaulValue;
import static org.jetbrains.kotlin.codegen.StackValue.createDefaultValue;
public class CallBasedArgumentGenerator extends ArgumentGenerator {
private final ExpressionCodegen codegen;
@@ -64,7 +64,7 @@ public class CallBasedArgumentGenerator extends ArgumentGenerator {
@Override
protected void generateDefault(int i, @NotNull DefaultValueArgument argument) {
callGenerator.putValueIfNeeded(valueParameterTypes.get(i), createDefaulValue(valueParameterTypes.get(i)), ValueKind.DEFAULT_PARAMETER, i);
callGenerator.putValueIfNeeded(valueParameterTypes.get(i), createDefaultValue(valueParameterTypes.get(i)), ValueKind.DEFAULT_PARAMETER, i);
}
@Override

View File

@@ -0,0 +1,168 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.codegen.intrinsics.JavaClassProperty;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
import org.jetbrains.org.objectweb.asm.Type;
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter;
public class CallReceiver extends StackValue {
private final StackValue dispatchReceiver;
private final StackValue extensionReceiver;
private final Type secondReceiverType;
private CallReceiver(
@NotNull StackValue dispatchReceiver,
@NotNull StackValue extensionReceiver,
@NotNull Type type,
@Nullable Type secondReceiverType
) {
super(type, dispatchReceiver.canHaveSideEffects() || extensionReceiver.canHaveSideEffects());
this.dispatchReceiver = dispatchReceiver;
this.extensionReceiver = extensionReceiver;
this.secondReceiverType = secondReceiverType;
}
public StackValue withoutReceiverArgument() {
return new CallReceiver(dispatchReceiver, none(), type, secondReceiverType);
}
public static StackValue generateCallReceiver(
@NotNull ResolvedCall<?> resolvedCall,
@NotNull ExpressionCodegen codegen,
@Nullable Callable callableMethod,
@Nullable ReceiverParameterDescriptor dispatchReceiverParameter,
@NotNull StackValue dispatchReceiver,
@Nullable ReceiverParameterDescriptor extensionReceiverParameter,
@NotNull StackValue extensionReceiver
) {
KotlinTypeMapper typeMapper = codegen.typeMapper;
GenerationState state = codegen.getState();
Type type;
Type secondReceiverType = null;
if (extensionReceiverParameter != null) {
type = calcExtensionReceiverType(resolvedCall, extensionReceiverParameter, typeMapper, callableMethod, state);
if (dispatchReceiverParameter != null) {
secondReceiverType = calcDispatchReceiverType(resolvedCall, dispatchReceiverParameter, typeMapper, callableMethod);
}
}
else if (dispatchReceiverParameter != null) {
type = calcDispatchReceiverType(resolvedCall, dispatchReceiverParameter, typeMapper, callableMethod);
}
else if (isLocalFunCall(callableMethod)) {
type = callableMethod.getGenerateCalleeType();
}
else {
type = Type.VOID_TYPE;
}
assert type != null : "Could not map receiver type for " + resolvedCall;
return new CallReceiver(dispatchReceiver, extensionReceiver, type, secondReceiverType);
}
private static Type calcDispatchReceiverType(
@NotNull ResolvedCall<?> resolvedCall,
@Nullable ReceiverParameterDescriptor dispatchReceiver,
@NotNull KotlinTypeMapper typeMapper,
@Nullable Callable callableMethod
) {
if (dispatchReceiver == null) return null;
CallableDescriptor descriptor = resolvedCall.getResultingDescriptor();
if (CodegenUtilKt.isJvmStaticInObjectOrClass(descriptor)) {
return Type.VOID_TYPE;
}
if (callableMethod != null) {
return callableMethod.getDispatchReceiverType();
}
// Extract the receiver from the resolved call, workarounding the fact that ResolvedCall#dispatchReceiver doesn't have
// all the needed information, for example there's no way to find out whether or not a smart cast was applied to the receiver.
DeclarationDescriptor container = descriptor.getContainingDeclaration();
if (container instanceof ClassDescriptor) {
return typeMapper.mapClass((ClassDescriptor) container);
}
return typeMapper.mapType(dispatchReceiver);
}
private static Type calcExtensionReceiverType(
@NotNull ResolvedCall<?> resolvedCall,
@Nullable ReceiverParameterDescriptor extensionReceiver,
@NotNull KotlinTypeMapper typeMapper,
@Nullable Callable callableMethod,
@NotNull GenerationState state
) {
if (extensionReceiver == null) return null;
CallableDescriptor descriptor = resolvedCall.getCandidateDescriptor();
if (descriptor instanceof PropertyDescriptor &&
// hackaround: boxing changes behaviour of T.javaClass intrinsic
state.getIntrinsics().getIntrinsic((PropertyDescriptor) descriptor) != JavaClassProperty.INSTANCE
) {
ReceiverParameterDescriptor receiverCandidate = descriptor.getExtensionReceiverParameter();
assert receiverCandidate != null;
return typeMapper.mapType(receiverCandidate.getType());
}
return callableMethod != null ? callableMethod.getExtensionReceiverType() : typeMapper.mapType(extensionReceiver.getType());
}
@Override
public void putSelector(@NotNull Type type, @NotNull InstructionAdapter v) {
StackValue currentExtensionReceiver = extensionReceiver;
boolean hasExtensionReceiver = extensionReceiver != none();
if (extensionReceiver instanceof SafeCall) {
currentExtensionReceiver.put(currentExtensionReceiver.type, v);
currentExtensionReceiver = StackValue.onStack(currentExtensionReceiver.type);
}
Type dispatchReceiverType = secondReceiverType != null ? secondReceiverType :
hasExtensionReceiver ? dispatchReceiver.type :
type;
dispatchReceiver.put(dispatchReceiverType, v);
currentExtensionReceiver
.moveToTopOfStack(hasExtensionReceiver ? type : currentExtensionReceiver.type, v, dispatchReceiverType.getSize());
}
@Override
public void dup(@NotNull InstructionAdapter v, boolean withReceiver) {
AsmUtil.dup(v, extensionReceiver.type, dispatchReceiver.type);
}
@NotNull
public StackValue getDispatchReceiver() {
return dispatchReceiver;
}
@NotNull
public StackValue getExtensionReceiver() {
return extensionReceiver;
}
}

View File

@@ -27,8 +27,11 @@ import org.jetbrains.kotlin.psi.synthetics.SyntheticClassOrObjectDescriptor;
import org.jetbrains.kotlin.psi.synthetics.SyntheticClassOrObjectDescriptorKt;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.DescriptorUtils;
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter;
import org.jetbrains.kotlin.resolve.scopes.MemberScope;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
@@ -101,6 +104,16 @@ public abstract class ClassBodyCodegen extends MemberCodegen<KtPureClassOrObject
genSyntheticClassOrObject((SyntheticClassOrObjectDescriptor) companionObjectDescriptor);
}
// Generate synthetic nested classes
Collection<DeclarationDescriptor> classifiers = descriptor
.getUnsubstitutedMemberScope()
.getContributedDescriptors(DescriptorKindFilter.CLASSIFIERS, MemberScope.Companion.getALL_NAME_FILTER());
for (DeclarationDescriptor memberDescriptor : classifiers) {
if (memberDescriptor instanceof SyntheticClassOrObjectDescriptor) {
genSyntheticClassOrObject((SyntheticClassOrObjectDescriptor) memberDescriptor);
}
}
if (generateNonClassMembers) {
generateBridges();
}
@@ -182,7 +195,7 @@ public abstract class ClassBodyCodegen extends MemberCodegen<KtPureClassOrObject
}
@NotNull
protected List<KtParameter> getPrimaryConstructorParameters() {
public List<KtParameter> getPrimaryConstructorParameters() {
if (myClass instanceof KtClass) {
return myClass.getPrimaryConstructorParameters();
}
@@ -192,6 +205,6 @@ public abstract class ClassBodyCodegen extends MemberCodegen<KtPureClassOrObject
@Nullable
@Override
protected ClassDescriptor classForInnerClassRecord() {
return DescriptorUtils.isTopLevelDeclaration(descriptor) ? null : descriptor;
return InnerClassConsumer.Companion.classForInnerClassRecord(descriptor, false);
}
}

View File

@@ -19,16 +19,19 @@ package org.jetbrains.kotlin.codegen;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.PsiFile;
import kotlin.collections.CollectionsKt;
import kotlin.io.FilesKt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.annotations.TestOnly;
import org.jetbrains.kotlin.backend.common.output.OutputFile;
import org.jetbrains.kotlin.backend.common.output.OutputFileCollection;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.load.kotlin.ModuleMapping;
import org.jetbrains.kotlin.load.kotlin.PackagePartClassUtils;
import org.jetbrains.kotlin.load.kotlin.PackageParts;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.psi.KtFile;
import org.jetbrains.kotlin.resolve.CompilerDeserializationConfiguration;
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOrigin;
import org.jetbrains.kotlin.serialization.jvm.JvmPackageTable;
import org.jetbrains.org.objectweb.asm.Type;
@@ -143,8 +146,26 @@ public class ClassFileFactory implements OutputFileCollection {
StringBuilder answer = new StringBuilder();
for (OutputFile file : asList()) {
answer.append("@").append(file.getRelativePath()).append('\n');
answer.append(file.asText());
File relativePath = new File(file.getRelativePath());
answer.append("@").append(relativePath).append('\n');
switch (FilesKt.getExtension(relativePath)) {
case "class":
answer.append(file.asText());
break;
case "kotlin_module": {
ModuleMapping mapping = ModuleMapping.Companion.create(
file.asByteArray(), relativePath.getPath(), CompilerDeserializationConfiguration.Default.INSTANCE
);
for (Map.Entry<String, PackageParts> entry : mapping.getPackageFqName2Parts().entrySet()) {
FqName packageFqName = new FqName(entry.getKey());
PackageParts packageParts = entry.getValue();
answer.append("<package ").append(packageFqName).append(": ").append(packageParts.getParts()).append(">\n");
}
break;
}
default:
throw new UnsupportedOperationException("Unknown OutputFile: " + file);
}
}
return answer.toString();
@@ -176,9 +197,9 @@ public class ClassFileFactory implements OutputFileCollection {
private PackagePartRegistry buildNewPackagePartRegistry(@NotNull FqName packageFqName) {
String packageFqNameAsString = packageFqName.asString();
return (partShortName, facadeShortName) -> {
return (partInternalName, facadeInternalName) -> {
PackageParts packageParts = partsGroupedByPackage.computeIfAbsent(packageFqNameAsString, PackageParts::new);
packageParts.addPart(partShortName, facadeShortName);
packageParts.addPart(partInternalName, facadeInternalName);
};
}

View File

@@ -24,6 +24,7 @@ import kotlin.collections.CollectionsKt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.codegen.binding.CalculatedClosure;
import org.jetbrains.kotlin.codegen.binding.CodegenBinding;
import org.jetbrains.kotlin.codegen.context.ClosureContext;
import org.jetbrains.kotlin.codegen.context.EnclosedValueDescriptor;
import org.jetbrains.kotlin.codegen.coroutines.CoroutineCodegenUtilKt;
@@ -33,6 +34,7 @@ import org.jetbrains.kotlin.codegen.signature.JvmSignatureWriter;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor;
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl;
import org.jetbrains.kotlin.incremental.components.NoLookupLocation;
import org.jetbrains.kotlin.load.java.JvmAbi;
@@ -201,7 +203,7 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
erasedInterfaceFunction = getErasedInvokeFunction(funDescriptor);
}
else {
erasedInterfaceFunction = samType.getAbstractMethod().getOriginal();
erasedInterfaceFunction = samType.getOriginalAbstractMethod();
}
generateBridge(
@@ -229,9 +231,10 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
@Override
protected void generateKotlinMetadataAnnotation() {
FunctionDescriptor frontendFunDescriptor = CodegenUtilKt.unwrapFrontendVersion(funDescriptor);
FunctionDescriptor freeLambdaDescriptor = createFreeLambdaDescriptor(frontendFunDescriptor);
Method method = v.getSerializationBindings().get(METHOD_FOR_FUNCTION, frontendFunDescriptor);
assert method != null : "No method for " + frontendFunDescriptor;
FunctionDescriptor freeLambdaDescriptor = FakeDescriptorsForReferencesKt.createFreeFakeLambdaDescriptor(frontendFunDescriptor);
v.getSerializationBindings().put(METHOD_FOR_FUNCTION, freeLambdaDescriptor, method);
DescriptorSerializer serializer =
@@ -245,30 +248,6 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
});
}
/**
* Given a function descriptor, creates another function descriptor with type parameters copied from outer context(s).
* This is needed because once we're serializing this to a proto, there's no place to store information about external type parameters.
*/
@NotNull
public static FunctionDescriptor createFreeLambdaDescriptor(@NotNull FunctionDescriptor descriptor) {
FunctionDescriptor.CopyBuilder<? extends FunctionDescriptor> builder = descriptor.newCopyBuilder();
List<TypeParameterDescriptor> typeParameters = new ArrayList<>(0);
builder.setTypeParameters(typeParameters);
DeclarationDescriptor container = descriptor.getContainingDeclaration();
while (container != null) {
if (container instanceof ClassDescriptor) {
typeParameters.addAll(((ClassDescriptor) container).getDeclaredTypeParameters());
}
else if (container instanceof CallableDescriptor && !(container instanceof ConstructorDescriptor)) {
typeParameters.addAll(((CallableDescriptor) container).getTypeParameters());
}
container = container.getContainingDeclaration();
}
return typeParameters.isEmpty() ? descriptor : builder.build();
}
@Override
protected void done() {
writeOuterClassAndEnclosingMethod();
@@ -381,13 +360,30 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
@NotNull GenerationState state
) {
DeclarationDescriptor container = descriptor.getContainingDeclaration();
if (container instanceof ClassDescriptor) {
// TODO: getDefaultType() here is wrong and won't work for arrays
putJavaLangClassInstance(iv, state.getTypeMapper().mapType(((ClassDescriptor) container).getDefaultType()));
wrapJavaClassIntoKClass(iv);
}
else if (container instanceof PackageFragmentDescriptor) {
iv.aconst(state.getTypeMapper().mapOwner(descriptor));
}
else if (descriptor instanceof VariableDescriptorWithAccessors) {
iv.aconst(state.getBindingContext().get(
CodegenBinding.DELEGATED_PROPERTY_METADATA_OWNER, ((VariableDescriptorWithAccessors) descriptor)
));
}
else {
iv.aconst(null);
return;
}
boolean isContainerPackage =
descriptor instanceof LocalVariableDescriptor
? DescriptorUtils.getParentOfType(descriptor, ClassDescriptor.class) == null
: container instanceof PackageFragmentDescriptor;
if (isContainerPackage) {
// Note that this name is not used in reflection. There should be the name of the referenced declaration's module instead,
// but there's no nice API to obtain that name here yet
// TODO: write the referenced declaration's module name and use it in reflection
@@ -396,7 +392,7 @@ public class ClosureCodegen extends MemberCodegen<KtElement> {
Type.getMethodDescriptor(K_DECLARATION_CONTAINER_TYPE, getType(Class.class), getType(String.class)), false);
}
else {
iv.aconst(null);
wrapJavaClassIntoKClass(iv);
}
}

View File

@@ -1,27 +0,0 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.fileClasses.JvmFileClassInfo
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil
import org.jetbrains.kotlin.fileClasses.JvmFileClassesProvider
import org.jetbrains.kotlin.psi.KtFile
class CodegenFileClassesProvider : JvmFileClassesProvider {
override fun getFileClassInfo(file: KtFile): JvmFileClassInfo =
JvmFileClassUtil.getFileClassInfoNoResolve(file)
}

View File

@@ -22,7 +22,7 @@ import java.util.*
class DefaultCallArgs(val size: Int) {
val bits: BitSet = BitSet(size)
private val bits: BitSet = BitSet(size)
fun mark(index: Int) {
assert (index < size) {
@@ -39,7 +39,7 @@ class DefaultCallArgs(val size: Int) {
val masks = ArrayList<Int>(1)
var mask = 0
for (i in 0..size - 1) {
for (i in 0 until size) {
if (i != 0 && i % Integer.SIZE == 0) {
masks.add(mask)
mask = 0

View File

@@ -26,7 +26,6 @@ import org.jetbrains.kotlin.psi.KtPureElement
import org.jetbrains.kotlin.resolve.descriptorUtil.hasDefaultValue
import org.jetbrains.kotlin.resolve.jvm.AsmTypes
import org.jetbrains.kotlin.resolve.jvm.annotations.findJvmOverloadsAnnotation
import org.jetbrains.kotlin.resolve.jvm.diagnostics.OtherOrigin
import org.jetbrains.kotlin.resolve.jvm.diagnostics.OtherOriginFromPure
import org.jetbrains.org.objectweb.asm.Label
import org.jetbrains.org.objectweb.asm.Opcodes
@@ -129,7 +128,7 @@ class DefaultParameterValueSubstitutor(val state: GenerationState) {
) {
val typeMapper = state.typeMapper
val isStatic = AsmUtil.isStaticMethod(contextKind, functionDescriptor)
val baseMethodFlags = AsmUtil.getCommonCallableFlags(functionDescriptor) and Opcodes.ACC_VARARGS.inv()
val baseMethodFlags = AsmUtil.getCommonCallableFlags(functionDescriptor, state) and Opcodes.ACC_VARARGS.inv()
val remainingParameters = getRemainingParameters(functionDescriptor.original, substituteCount)
val flags =
baseMethodFlags or

View File

@@ -39,18 +39,18 @@ import org.jetbrains.kotlin.codegen.coroutines.CoroutineCodegenForLambda;
import org.jetbrains.kotlin.codegen.coroutines.CoroutineCodegenUtilKt;
import org.jetbrains.kotlin.codegen.coroutines.ResolvedCallWithRealDescriptor;
import org.jetbrains.kotlin.codegen.extensions.ExpressionCodegenExtension;
import org.jetbrains.kotlin.codegen.range.forLoop.ForLoopGenerator;
import org.jetbrains.kotlin.codegen.inline.*;
import org.jetbrains.kotlin.codegen.intrinsics.*;
import org.jetbrains.kotlin.codegen.pseudoInsns.PseudoInsnsKt;
import org.jetbrains.kotlin.codegen.range.RangeValue;
import org.jetbrains.kotlin.codegen.range.RangeValuesKt;
import org.jetbrains.kotlin.codegen.range.forLoop.ForLoopGenerator;
import org.jetbrains.kotlin.codegen.signature.BothSignatureWriter;
import org.jetbrains.kotlin.codegen.signature.JvmSignatureWriter;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.codegen.when.SwitchCodegen;
import org.jetbrains.kotlin.codegen.when.SwitchCodegenUtil;
import org.jetbrains.kotlin.codegen.when.SwitchCodegenProvider;
import org.jetbrains.kotlin.config.ApiVersion;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor;
@@ -61,14 +61,12 @@ import org.jetbrains.kotlin.diagnostics.Errors;
import org.jetbrains.kotlin.lexer.KtTokens;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.load.java.sam.SamConstructorDescriptor;
import org.jetbrains.kotlin.load.kotlin.MethodSignatureMappingKt;
import org.jetbrains.kotlin.load.kotlin.TypeSignatureMappingKt;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.psiUtil.PsiUtilsKt;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.BindingContextUtils;
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils;
import org.jetbrains.kotlin.resolve.DescriptorUtils;
import org.jetbrains.kotlin.resolve.*;
import org.jetbrains.kotlin.resolve.calls.callResolverUtil.CallResolverUtilKt;
import org.jetbrains.kotlin.resolve.calls.callUtil.CallUtilKt;
import org.jetbrains.kotlin.resolve.calls.model.*;
@@ -106,6 +104,7 @@ import java.util.*;
import static org.jetbrains.kotlin.builtins.KotlinBuiltIns.isInt;
import static org.jetbrains.kotlin.codegen.AsmUtil.*;
import static org.jetbrains.kotlin.codegen.CodegenUtilKt.extractReificationArgument;
import static org.jetbrains.kotlin.codegen.CodegenUtilKt.isPossiblyUninitializedSingleton;
import static org.jetbrains.kotlin.codegen.CodegenUtilKt.unwrapInitialSignatureDescriptor;
import static org.jetbrains.kotlin.codegen.JvmCodegenUtil.*;
import static org.jetbrains.kotlin.codegen.binding.CodegenBinding.*;
@@ -134,6 +133,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
private final MemberCodegen<?> parentCodegen;
private final TailRecursionCodegen tailRecursionCodegen;
public final CallGenerator defaultCallGenerator = new CallGenerator.DefaultCallGenerator(this);
private final SwitchCodegenProvider switchCodegenProvider;
private final Stack<BlockStackElement> blockStackElements = new Stack<>();
@@ -165,6 +165,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
this.parentCodegen = parentCodegen;
this.tailRecursionCodegen = new TailRecursionCodegen(context, this, this.v, state);
this.switchCodegenProvider = new SwitchCodegenProvider(this);
}
@Nullable
@@ -436,11 +437,6 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return CodegenUtilKt.asmType(expression, typeMapper, bindingContext);
}
@Nullable
private KotlinType expressionJetType(@Nullable KtExpression expression) {
return CodegenUtilKt.kotlinType(expression, bindingContext);
}
@Override
public StackValue visitParenthesizedExpression(@NotNull KtParenthesizedExpression expression, StackValue receiver) {
return genQualified(receiver, expression.getExpression());
@@ -750,11 +746,21 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@Override
public StackValue visitConstantExpression(@NotNull KtConstantExpression expression, StackValue receiver) {
ConstantValue<?> compileTimeValue = getPrimitiveOrStringCompileTimeConstant(expression, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> compileTimeValue = getPrimitiveOrStringCompileTimeConstant(expression);
assert compileTimeValue != null;
return StackValue.constant(compileTimeValue.getValue(), expressionType(expression));
}
@Nullable
public ConstantValue<?> getCompileTimeConstant(@NotNull KtExpression expression) {
return getCompileTimeConstant(expression, bindingContext, state.getShouldInlineConstVals());
}
@Nullable
public ConstantValue<?> getPrimitiveOrStringCompileTimeConstant(@NotNull KtExpression expression) {
return getPrimitiveOrStringCompileTimeConstant(expression, bindingContext, state.getShouldInlineConstVals());
}
@Nullable
public static ConstantValue<?> getPrimitiveOrStringCompileTimeConstant(
@NotNull KtExpression expression,
@@ -831,24 +837,29 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
public StackValue visitStringTemplateExpression(@NotNull KtStringTemplateExpression expression, StackValue receiver) {
List<StringTemplateEntry> entries = preprocessStringTemplate(expression);
if (entries.size() == 1) {
Type type = expressionType(expression);
if (entries.size() == 0) {
return StackValue.constant("", type);
}
else if (entries.size() == 1) {
StringTemplateEntry entry = entries.get(0);
if (entry instanceof StringTemplateEntry.Expression) {
KtExpression expr = ((StringTemplateEntry.Expression) entry).expression;
return genToString(gen(expr), expressionType(expr));
return genToString(gen(expr), type);
}
else {
Type type = expressionType(expression);
return StackValue.constant(((StringTemplateEntry.Constant) entry).value, type);
}
}
return StackValue.operation(JAVA_STRING_TYPE, v -> {
genStringBuilderConstructor(v);
invokeAppendForEntries(v, entries);
v.invokevirtual("java/lang/StringBuilder", "toString", "()Ljava/lang/String;", false);
return Unit.INSTANCE;
});
else {
return StackValue.operation(type, v -> {
genStringBuilderConstructor(v);
invokeAppendForEntries(v, entries);
v.invokevirtual("java/lang/StringBuilder", "toString", "()Ljava/lang/String;", false);
return Unit.INSTANCE;
});
}
}
private void invokeAppendForEntries(InstructionAdapter v, List<StringTemplateEntry> entries) {
@@ -905,8 +916,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
KtExpression entryExpression = entry.getExpression();
if (entryExpression == null) throw new AssertionError("No expression in " + entry);
ConstantValue<?> compileTimeConstant =
getPrimitiveOrStringCompileTimeConstant(entryExpression, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(entryExpression);
if (compileTimeConstant != null && isConstantValueInlinableInStringTemplate(compileTimeConstant)) {
constantValue.append(String.valueOf(compileTimeConstant.getValue()));
@@ -1062,7 +1072,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
List<ResolvedValueArgument> valueArguments = new ArrayList<>(params);
List<ValueParameterDescriptor> valueParameters = new ArrayList<>(params);
List<Type> mappedTypes = new ArrayList<>(params);
for (ValueParameterDescriptor parameter : superValueParameters) {
for (ValueParameterDescriptor parameter : superCall.getValueArguments().keySet()) {
ResolvedValueArgument argument = superCall.getValueArguments().get(parameter);
if (!(argument instanceof DefaultValueArgument)) {
valueArguments.add(argument);
@@ -1276,8 +1286,19 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
KotlinType varType = isDelegatedLocalVariable(variableDescriptor)
? JvmCodegenUtil.getPropertyDelegateType((VariableDescriptorWithAccessors) variableDescriptor, bindingContext)
: variableDescriptor.getType();
//noinspection ConstantConditions
return asmType(varType);
if (variableDescriptor instanceof ValueParameterDescriptor &&
MethodSignatureMappingKt.forceSingleValueParameterBoxing(
(CallableDescriptor) variableDescriptor.getContainingDeclaration()
)
) {
//noinspection ConstantConditions
return asmType(TypeUtils.makeNullable(varType));
}
else {
//noinspection ConstantConditions
return asmType(varType);
}
}
private void putDescriptorIntoFrameMap(@NotNull KtElement statement) {
@@ -1608,11 +1629,12 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
// If it does not end with return we should return something
// because if we don't there can be VerifyError (specific cases with Nothing-typed expressions)
if (!endsWithReturn(expr)) {
markLineNumber(expr, true);
if (isLambdaVoidBody(expr, typeForExpression)) {
markLineNumber((KtFunctionLiteral) expr.getParent(), true);
}
else {
markLineNumber(expr, true);
}
if (typeForExpression.getSort() == Type.VOID) {
StackValue.none().put(returnType, v);
@@ -1684,7 +1706,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
Collection<ExpressionCodegenExtension> codegenExtensions = ExpressionCodegenExtension.Companion.getInstances(state.getProject());
if (!codegenExtensions.isEmpty() && resolvedCall != null) {
ExpressionCodegenExtension.Context context = new ExpressionCodegenExtension.Context(typeMapper, v);
ExpressionCodegenExtension.Context context = new ExpressionCodegenExtension.Context(this, typeMapper, v);
KotlinType returnType = propertyDescriptor.getReturnType();
for (ExpressionCodegenExtension extension : codegenExtensions) {
if (returnType != null) {
@@ -1701,7 +1723,8 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
receiver = StackValue.receiverWithoutReceiverArgument(receiver);
}
return intermediateValueForProperty(propertyDescriptor, directToField, directToField, superCallTarget, false, receiver, resolvedCall);
return intermediateValueForProperty(propertyDescriptor, directToField, directToField, superCallTarget, false, receiver,
resolvedCall, false);
}
if (descriptor instanceof TypeAliasDescriptor) {
@@ -1715,6 +1738,9 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
if (descriptor instanceof ClassDescriptor) {
ClassDescriptor classDescriptor = (ClassDescriptor) descriptor;
if (isPossiblyUninitializedSingleton(classDescriptor) && isInsideSingleton(classDescriptor)) {
return generateThisOrOuterFromContext(classDescriptor, false, false);
}
if (isObject(classDescriptor)) {
return StackValue.singleton(classDescriptor, typeMapper);
}
@@ -1776,31 +1802,15 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return lookupCapturedValueInConstructorParameters(descriptor);
}
return lookupValuaAndLocalVariableMetadata(descriptor, StackValue.LOCAL_0, state, false, context, this);
}
@Nullable
static StackValue lookupValuaAndLocalVariableMetadata(
@NotNull DeclarationDescriptor descriptor,
@NotNull StackValue prefix,
@NotNull GenerationState state,
boolean ignoreNoOuter,
@NotNull CodegenContext context,
@Nullable ExpressionCodegen codegen
) {
StackValue value = context.lookupInContext(descriptor, prefix, state, ignoreNoOuter);
if(!isDelegatedLocalVariable(descriptor) || value == null) {
return value;
StackValue value = context.lookupInContext(descriptor, StackValue.LOCAL_0, state, false);
if (isDelegatedLocalVariable(descriptor) && value != null) {
VariableDescriptor metadata = getDelegatedLocalVariableMetadata((VariableDescriptor) descriptor, bindingContext);
StackValue metadataValue = context.lookupInContext(metadata, StackValue.LOCAL_0, state, false);
assert metadataValue != null : "Metadata stack value should be non-null for local delegated property: " + descriptor;
return delegatedVariableValue(value, metadataValue, (VariableDescriptorWithAccessors) descriptor, typeMapper);
}
VariableDescriptor metadata = getDelegatedLocalVariableMetadata((VariableDescriptor) descriptor, state.getBindingContext());
StackValue metadataValue = context.lookupInContext(metadata, prefix, state, ignoreNoOuter);
assert metadataValue != null : "Metadata stack value should be non-null for local delegated property";
//required for ImplementationBodyCodegen.lookupConstructorExpressionsInClosureIfPresent
if (codegen == null) return null;
return codegen.delegatedVariableValue(value, metadataValue, (VariableDescriptorWithAccessors) descriptor,
state.getTypeMapper());
return value;
}
@Nullable
@@ -1811,7 +1821,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
int parameterOffsetInConstructor = context.closure.getCapturedParameterOffsetInConstructor(descriptor);
// when captured parameter is singleton
// see compiler/testData/codegen/box/objects/objectInLocalAnonymousObject.kt (fun local() captured in A)
if (parameterOffsetInConstructor == -1) return adjustVariableValue(parentResult , descriptor);
if (parameterOffsetInConstructor == -1) return adjustVariableValue(parentResult, descriptor);
assert parentResult instanceof StackValue.Field || parentResult instanceof StackValue.FieldForSharedVar
: "Part of closure should be either Field or FieldForSharedVar";
@@ -1830,10 +1840,10 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
Type sharedVarType = typeMapper.getSharedVarType(descriptor);
Type varType = getVariableTypeNoSharing(variableDescriptor);
if (sharedVarType != null) {
return StackValue.shared(index, varType);
return StackValue.shared(index, varType, variableDescriptor);
}
else {
return adjustVariableValue(StackValue.local(index, varType), variableDescriptor);
return adjustVariableValue(StackValue.local(index, varType, variableDescriptor), variableDescriptor);
}
}
else {
@@ -1864,7 +1874,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@Nullable ClassDescriptor superCallTarget,
@NotNull StackValue receiver
) {
return intermediateValueForProperty(propertyDescriptor, forceField, false, superCallTarget, false, receiver, null);
return intermediateValueForProperty(propertyDescriptor, forceField, false, superCallTarget, false, receiver, null, false);
}
private CodegenContext getBackingFieldContext(
@@ -1872,12 +1882,24 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@NotNull DeclarationDescriptor containingDeclaration
) {
switch (accessorKind) {
case NORMAL: return context.getParentContext();
case NORMAL:
if (containingDeclaration instanceof ClassDescriptor) {
CodegenContext parentWithDescriptor = context.findParentContextWithDescriptor(containingDeclaration);
if (parentWithDescriptor != null) {
return parentWithDescriptor;
}
}
return context.getParentContext();
// For companion object property, backing field lives in object containing class
// Otherwise, it lives in its containing declaration
case IN_CLASS_COMPANION: return context.findParentContextWithDescriptor(containingDeclaration.getContainingDeclaration());
case FIELD_FROM_LOCAL: return context.findParentContextWithDescriptor(containingDeclaration);
default: throw new IllegalStateException();
case IN_CLASS_COMPANION:
return context.findParentContextWithDescriptor(containingDeclaration.getContainingDeclaration());
case FIELD_FROM_LOCAL:
return context.findParentContextWithDescriptor(containingDeclaration);
case LATEINIT_INTRINSIC:
return context.findParentContextWithDescriptor(containingDeclaration);
default:
throw new IllegalStateException("Unknown field accessor kind: " + accessorKind);
}
}
@@ -1888,22 +1910,35 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@Nullable ClassDescriptor superCallTarget,
boolean skipAccessorsForPrivateFieldInOuterClass,
@NotNull StackValue receiver,
@Nullable ResolvedCall resolvedCall
@Nullable ResolvedCall resolvedCall,
boolean skipLateinitAssertion
) {
if (propertyDescriptor instanceof SyntheticJavaPropertyDescriptor) {
return intermediateValueForSyntheticExtensionProperty((SyntheticJavaPropertyDescriptor) propertyDescriptor, receiver);
}
if (propertyDescriptor instanceof PropertyImportedFromObject) {
propertyDescriptor = ((PropertyImportedFromObject) propertyDescriptor).getCallableFromObject();
}
DeclarationDescriptor containingDeclaration = propertyDescriptor.getContainingDeclaration();
FieldAccessorKind fieldAccessorKind = FieldAccessorKind.NORMAL;
boolean isBackingFieldInClassCompanion = JvmAbi.isPropertyWithBackingFieldInOuterClass(propertyDescriptor);
if (isBackingFieldInClassCompanion && (forceField || propertyDescriptor.isConst() && Visibilities.isPrivate(propertyDescriptor.getVisibility()))) {
FieldAccessorKind fieldAccessorKind;
if (skipLateinitAssertion) {
fieldAccessorKind = FieldAccessorKind.LATEINIT_INTRINSIC;
}
else if (isBackingFieldInClassCompanion &&
(forceField || propertyDescriptor.isConst() && Visibilities.isPrivate(propertyDescriptor.getVisibility()))) {
fieldAccessorKind = FieldAccessorKind.IN_CLASS_COMPANION;
}
else if (syntheticBackingField && context.getFirstCrossInlineOrNonInlineContext().getParentContext().getContextDescriptor() != containingDeclaration) {
else if ((syntheticBackingField &&
context.getFirstCrossInlineOrNonInlineContext().getParentContext().getContextDescriptor() != containingDeclaration)) {
fieldAccessorKind = FieldAccessorKind.FIELD_FROM_LOCAL;
}
else {
fieldAccessorKind = FieldAccessorKind.NORMAL;
}
boolean isStaticBackingField = DescriptorUtils.isStaticDeclaration(propertyDescriptor) ||
AsmUtil.isInstancePropertyWithStaticBackingField(propertyDescriptor);
boolean isSuper = superCallTarget != null;
@@ -1916,15 +1951,26 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
CallableMethod callableSetter = null;
CodegenContext backingFieldContext = getBackingFieldContext(fieldAccessorKind, containingDeclaration);
DeclarationDescriptor ownerDescriptor = containingDeclaration;
boolean isPrivateProperty =
fieldAccessorKind != FieldAccessorKind.NORMAL &&
(AsmUtil.getVisibilityForBackingField(propertyDescriptor, isDelegatedProperty) & ACC_PRIVATE) != 0;
DeclarationDescriptor ownerDescriptor;
boolean skipPropertyAccessors;
PropertyDescriptor originalPropertyDescriptor = DescriptorUtils.unwrapFakeOverride(propertyDescriptor);
if (fieldAccessorKind != FieldAccessorKind.NORMAL) {
int flags = AsmUtil.getVisibilityForBackingField(propertyDescriptor, isDelegatedProperty);
if (fieldAccessorKind == FieldAccessorKind.LATEINIT_INTRINSIC) {
skipPropertyAccessors = !isPrivateProperty || context.getClassOrPackageParentContext() == backingFieldContext;
if (!skipPropertyAccessors) {
propertyDescriptor = (AccessorForPropertyBackingField)
backingFieldContext.getAccessor(propertyDescriptor, fieldAccessorKind, delegateType, superCallTarget);
}
ownerDescriptor = propertyDescriptor;
}
else if (fieldAccessorKind == FieldAccessorKind.IN_CLASS_COMPANION || fieldAccessorKind == FieldAccessorKind.FIELD_FROM_LOCAL) {
boolean isInlinedConst = propertyDescriptor.isConst() && state.getShouldInlineConstVals();
skipPropertyAccessors = isInlinedConst || (flags & ACC_PRIVATE) == 0 || skipAccessorsForPrivateFieldInOuterClass;
skipPropertyAccessors = isInlinedConst || !isPrivateProperty || skipAccessorsForPrivateFieldInOuterClass;
if (!skipPropertyAccessors) {
//noinspection ConstantConditions
@@ -1935,12 +1981,13 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
"Unexpected accessor descriptor: " + propertyDescriptor;
ownerDescriptor = propertyDescriptor;
}
else {
ownerDescriptor = containingDeclaration;
}
}
else {
if (!isBackingFieldInClassCompanion) {
ownerDescriptor = propertyDescriptor;
}
skipPropertyAccessors = forceField;
ownerDescriptor = isBackingFieldInClassCompanion ? containingDeclaration : propertyDescriptor;
}
if (!skipPropertyAccessors) {
@@ -1984,10 +2031,11 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
fieldName = KotlinTypeMapper.mapDefaultFieldName(propertyDescriptor, isDelegatedProperty);
}
return StackValue.property(propertyDescriptor, backingFieldOwner,
typeMapper.mapType(
isDelegatedProperty && forceField ? delegateType : propertyDescriptor.getOriginal().getType()),
isStaticBackingField, fieldName, callableGetter, callableSetter, receiver, this, resolvedCall);
return StackValue.property(
propertyDescriptor, backingFieldOwner,
typeMapper.mapType(isDelegatedProperty && forceField ? delegateType : propertyDescriptor.getOriginal().getType()),
isStaticBackingField, fieldName, callableGetter, callableSetter, receiver, this, resolvedCall, skipLateinitAssertion
);
}
@NotNull
@@ -2001,7 +2049,8 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
FunctionDescriptor setMethod = propertyDescriptor.getSetMethod();
CallableMethod callableSetter =
setMethod != null ? typeMapper.mapToCallableMethod(context.accessibleDescriptor(setMethod, null), false) : null;
return StackValue.property(propertyDescriptor, null, type, false, null, callableGetter, callableSetter, receiver, this, null);
return StackValue.property(propertyDescriptor, null, type, false, null, callableGetter, callableSetter, receiver, this,
null, false);
}
@Override
@@ -2120,7 +2169,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
Collection<ExpressionCodegenExtension> codegenExtensions = ExpressionCodegenExtension.Companion.getInstances(state.getProject());
if (!codegenExtensions.isEmpty()) {
ExpressionCodegenExtension.Context context = new ExpressionCodegenExtension.Context(typeMapper, v);
ExpressionCodegenExtension.Context context = new ExpressionCodegenExtension.Context(this, typeMapper, v);
for (ExpressionCodegenExtension extension : codegenExtensions) {
StackValue stackValue = extension.applyFunction(receiver, resolvedCall, context);
if (stackValue != null) return stackValue;
@@ -2205,7 +2254,9 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
) {
boolean isSuspendCall = CoroutineCodegenUtilKt.isSuspendNoInlineCall(resolvedCall);
boolean isConstructor = resolvedCall.getResultingDescriptor() instanceof ConstructorDescriptor;
putReceiverAndInlineMarkerIfNeeded(callableMethod, resolvedCall, receiver, isSuspendCall, isConstructor);
if (!(callableMethod instanceof IntrinsicWithSpecialReceiver)) {
putReceiverAndInlineMarkerIfNeeded(callableMethod, resolvedCall, receiver, isSuspendCall, isConstructor);
}
callGenerator.processAndPutHiddenParameters(false);
@@ -2292,12 +2343,12 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
// But the problem is that we should leave the receiver itself on the stack, so we store it in a temporary variable.
if (isSuspendCall && isSafeCallOrOnStack) {
boolean bothReceivers =
receiver instanceof StackValue.CallReceiver
&& ((StackValue.CallReceiver) receiver).getDispatchReceiver().type.getSort() != Type.VOID
&& ((StackValue.CallReceiver) receiver).getExtensionReceiver().type.getSort() != Type.VOID;
receiver instanceof CallReceiver
&& ((CallReceiver) receiver).getDispatchReceiver().type.getSort() != Type.VOID
&& ((CallReceiver) receiver).getExtensionReceiver().type.getSort() != Type.VOID;
Type firstReceiverType =
bothReceivers
? ((StackValue.CallReceiver) receiver).getDispatchReceiver().type
? ((CallReceiver) receiver).getDispatchReceiver().type
: receiver.type;
Type secondReceiverType = bothReceivers ? receiver.type : null;
@@ -2335,15 +2386,21 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
) {
if (callElement == null) return defaultCallGenerator;
boolean isIntrinsic = descriptor instanceof CallableMemberDescriptor &&
state.getIntrinsics().getIntrinsic((CallableMemberDescriptor) descriptor) != null;
boolean isInline = (InlineUtil.isInline(descriptor) && !isIntrinsic) || InlineUtil.isArrayConstructorWithLambda(descriptor);
// We should inline callable containing reified type parameters even if inline is disabled
// because they may contain something to reify and straight call will probably fail at runtime
boolean isInline = (!state.isInlineDisabled() || InlineUtil.containsReifiedTypeParameters(descriptor)) &&
(InlineUtil.isInline(descriptor) || InlineUtil.isArrayConstructorWithLambda(descriptor));
if (!isInline) return defaultCallGenerator;
boolean shouldInline = isInline && (!state.isInlineDisabled() || InlineUtil.containsReifiedTypeParameters(descriptor));
if (!shouldInline) return defaultCallGenerator;
FunctionDescriptor original =
unwrapInitialSignatureDescriptor(DescriptorUtils.unwrapFakeOverride((FunctionDescriptor) descriptor.getOriginal()));
CoroutineCodegenUtilKt.getOriginalSuspendFunctionView(
unwrapInitialSignatureDescriptor(DescriptorUtils.unwrapFakeOverride((FunctionDescriptor) descriptor.getOriginal())),
bindingContext
);
if (isDefaultCompilation) {
return new InlineCodegenForDefaultBody(original, this, state, new PsiSourceCompilerForInline(this, callElement));
}
@@ -2430,6 +2487,9 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
if (contextDescriptor instanceof FunctionDescriptor && receiverDescriptor == contextDescriptor.getContainingDeclaration()) {
return StackValue.LOCAL_0;
}
else if (isPossiblyUninitializedSingleton(receiverDescriptor) && isInsideSingleton(receiverDescriptor)) {
return generateThisOrOuterFromContext(receiverDescriptor, false, false);
}
else {
return StackValue.singleton(receiverDescriptor, typeMapper);
}
@@ -2447,7 +2507,14 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return generateExtensionReceiver(((ExtensionReceiver) receiverValue).getDeclarationDescriptor());
}
else if (receiverValue instanceof ExpressionReceiver) {
return gen(((ExpressionReceiver) receiverValue).getExpression());
ExpressionReceiver expressionReceiver = (ExpressionReceiver) receiverValue;
StackValue stackValue = gen(expressionReceiver.getExpression());
if (!state.isReceiverAssertionsDisabled()) {
RuntimeAssertionInfo runtimeAssertionInfo =
bindingContext.get(JvmBindingContextSlices.RECEIVER_RUNTIME_ASSERTION_INFO, expressionReceiver);
stackValue = genNotNullAssertions(state, stackValue, runtimeAssertionInfo);
}
return stackValue;
}
else {
throw new UnsupportedOperationException("Unsupported receiver value: " + receiverValue);
@@ -2507,22 +2574,47 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return generateThisOrOuter(calleeContainingClass, isSuper, false);
}
@NotNull
public StackValue generateThisOrOuter(@NotNull ClassDescriptor calleeContainingClass, boolean isSuper, boolean forceOuter) {
boolean isSingleton = calleeContainingClass.getKind().isSingleton();
if (isSingleton) {
if (calleeContainingClass.equals(context.getThisDescriptor()) &&
!CodegenUtilKt.isJvmStaticInObjectOrClass(context.getFunctionDescriptor())) {
return StackValue.local(0, typeMapper.mapType(calleeContainingClass));
}
else if (isEnumEntry(calleeContainingClass)) {
return StackValue.enumEntry(calleeContainingClass, typeMapper);
}
else {
return StackValue.singleton(calleeContainingClass, typeMapper);
private boolean isInsideSingleton(@NotNull ClassDescriptor singletonClassDescriptor) {
assert singletonClassDescriptor.getKind().isSingleton() :
"Singleton expected: " + singletonClassDescriptor;
DeclarationDescriptor descriptor = context.getContextDescriptor();
while (descriptor != null) {
if (descriptor == singletonClassDescriptor) return true;
if (descriptor instanceof ClassDescriptor &&
!(((ClassDescriptor) descriptor).isInner() || DescriptorUtils.isAnonymousObject(descriptor))) {
return false;
}
descriptor = descriptor.getContainingDeclaration();
}
return false;
}
@NotNull
public StackValue generateThisOrOuter(@NotNull ClassDescriptor calleeContainingClass, boolean isSuper, boolean forceOuter) {
if (!calleeContainingClass.getKind().isSingleton()) {
return generateThisOrOuterFromContext(calleeContainingClass, isSuper, forceOuter);
}
if (calleeContainingClass.equals(context.getThisDescriptor()) &&
!CodegenUtilKt.isJvmStaticInObjectOrClass(context.getFunctionDescriptor())) {
return StackValue.local(0, typeMapper.mapType(calleeContainingClass));
}
else if (CodegenUtilKt.isPossiblyUninitializedSingleton(calleeContainingClass) && isInsideSingleton(calleeContainingClass)) {
return generateThisOrOuterFromContext(calleeContainingClass, isSuper, forceOuter);
}
else if (isEnumEntry(calleeContainingClass)) {
return StackValue.enumEntry(calleeContainingClass, typeMapper);
}
else {
return StackValue.singleton(calleeContainingClass, typeMapper);
}
}
private StackValue generateThisOrOuterFromContext(@NotNull ClassDescriptor calleeContainingClass, boolean isSuper, boolean forceOuter) {
CodegenContext cur = context;
Type type = asmType(calleeContainingClass.getDefaultType());
StackValue result = StackValue.local(0, type);
@@ -2683,35 +2775,45 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
public StackValue visitCallableReferenceExpression(@NotNull KtCallableReferenceExpression expression, StackValue data) {
ResolvedCall<?> resolvedCall = CallUtilKt.getResolvedCallWithAssert(expression.getCallableReference(), bindingContext);
KotlinType receiverExpressionType = expressionJetType(expression.getReceiverExpression());
Type receiverAsmType = receiverExpressionType != null ? asmType(receiverExpressionType) : null;
StackValue receiverValue =
receiverExpressionType != null ? StackValue.coercion(gen(expression.getReceiverExpression()), receiverAsmType) : null;
StackValue receiver = generateCallableReferenceReceiver(resolvedCall);
FunctionDescriptor functionDescriptor = bindingContext.get(FUNCTION, expression);
if (functionDescriptor != null) {
FunctionReferenceGenerationStrategy strategy =
new FunctionReferenceGenerationStrategy(state, functionDescriptor, resolvedCall, receiverAsmType, null, false);
FunctionReferenceGenerationStrategy strategy = new FunctionReferenceGenerationStrategy(
state, functionDescriptor, resolvedCall, receiver != null ? receiver.type : null, null, false
);
return genClosure(
expression, functionDescriptor, strategy, null,
(FunctionDescriptor) resolvedCall.getResultingDescriptor(), receiverValue
(FunctionDescriptor) resolvedCall.getResultingDescriptor(), receiver
);
}
VariableDescriptor variableDescriptor = getVariableDescriptorNotNull(expression);
return generatePropertyReference(
expression, variableDescriptor, (VariableDescriptor) resolvedCall.getResultingDescriptor(),
receiverAsmType, receiverValue
expression, getVariableDescriptorNotNull(expression),
(VariableDescriptor) resolvedCall.getResultingDescriptor(), receiver
);
}
@Nullable
private StackValue generateCallableReferenceReceiver(@NotNull ResolvedCall<?> resolvedCall) {
CallableDescriptor descriptor = resolvedCall.getResultingDescriptor();
if (descriptor.getExtensionReceiverParameter() == null && descriptor.getDispatchReceiverParameter() == null) return null;
ReceiverValue dispatchReceiver = resolvedCall.getDispatchReceiver();
ReceiverValue extensionReceiver = resolvedCall.getExtensionReceiver();
assert dispatchReceiver == null || extensionReceiver == null : "Cannot generate reference with both receivers: " + descriptor;
ReceiverValue receiver = dispatchReceiver != null ? dispatchReceiver : extensionReceiver;
if (receiver == null || receiver instanceof TransientReceiver) return null;
return StackValue.coercion(generateReceiverValue(receiver, false), asmType(receiver.getType()));
}
@NotNull
private StackValue generatePropertyReference(
@NotNull KtElement element,
@NotNull VariableDescriptor variableDescriptor,
@NotNull VariableDescriptor target,
@Nullable Type receiverAsmType,
@Nullable StackValue receiverValue
) {
ClassDescriptor classDescriptor = CodegenBinding.anonymousClassForCallable(bindingContext, variableDescriptor);
@@ -2722,17 +2824,14 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
element.getContainingFile()
);
Type receiverAsmType = receiverValue != null ? receiverValue.type : null;
PropertyReferenceCodegen codegen = new PropertyReferenceCodegen(
state, parentCodegen, context.intoAnonymousClass(classDescriptor, this, OwnerKind.IMPLEMENTATION),
element, classBuilder, variableDescriptor, target, receiverAsmType
);
codegen.generate();
return codegen.putInstanceOnStack(receiverValue == null ? null : () -> {
assert receiverAsmType != null : "Receiver type should not be null when receiver value is not null: " + receiverValue;
receiverValue.put(receiverAsmType, v);
return Unit.INSTANCE;
});
return codegen.putInstanceOnStack(receiverValue);
}
@NotNull
@@ -2833,7 +2932,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
}
else if (opToken == KtTokens.EQEQ || opToken == KtTokens.EXCLEQ ||
opToken == KtTokens.EQEQEQ || opToken == KtTokens.EXCLEQEQEQ) {
return generateEquals(expression.getLeft(), expression.getRight(), opToken);
return generateEquals(expression.getLeft(), expression.getRight(), opToken, null);
}
else if (opToken == KtTokens.LT || opToken == KtTokens.LTEQ ||
opToken == KtTokens.GT || opToken == KtTokens.GTEQ) {
@@ -2847,7 +2946,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
expression.getRight(), reference);
}
else {
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expression, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expression);
if (compileTimeConstant != null) {
return StackValue.constant(compileTimeConstant.getValue(), expressionType(expression));
}
@@ -2878,33 +2977,81 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return StackValue.or(gen(expression.getLeft()), gen(expression.getRight()));
}
private StackValue generateEquals(@Nullable KtExpression left, @Nullable KtExpression right, @NotNull IElementType opToken) {
private StackValue genLazyUnlessProvided(@Nullable StackValue pregenerated, @NotNull KtExpression expr, @NotNull Type type) {
return pregenerated != null ? StackValue.coercion(pregenerated, type) : genLazy(expr, type);
}
private StackValue genUnlessProvided(@Nullable StackValue pregenerated, @NotNull KtExpression expr, @NotNull Type type) {
if (pregenerated != null) {
pregenerated.put(type, v);
}
else {
gen(expr, type);
}
return StackValue.onStack(type);
}
private StackValue generateEquals(
@Nullable KtExpression left,
@Nullable KtExpression right,
@NotNull IElementType opToken,
@Nullable StackValue pregeneratedLeft
) {
Type leftType = expressionType(left);
Type rightType = expressionType(right);
if (KtPsiUtil.isNullConstant(left)) {
return genCmpWithNull(right, opToken);
return genCmpWithNull(right, opToken, null);
}
if (KtPsiUtil.isNullConstant(right)) {
return genCmpWithNull(left, opToken);
return genCmpWithNull(left, opToken, pregeneratedLeft);
}
if (isIntZero(left, leftType) && isIntPrimitive(rightType)) {
return genCmpWithZero(right, opToken);
return genCmpWithZero(right, opToken, null);
}
if (isIntZero(right, rightType) && isIntPrimitive(leftType)) {
return genCmpWithZero(left, opToken);
return genCmpWithZero(left, opToken, pregeneratedLeft);
}
if (left instanceof KtSafeQualifiedExpression && isPrimitive(rightType)) {
if (pregeneratedLeft == null && left instanceof KtSafeQualifiedExpression &&
isSelectorPureNonNullType((KtSafeQualifiedExpression) left) && isPrimitive(rightType)) {
return genCmpSafeCallToPrimitive((KtSafeQualifiedExpression) left, right, rightType, opToken);
}
if (isPrimitive(leftType) && right instanceof KtSafeQualifiedExpression) {
return genCmpPrimitiveToSafeCall(left, leftType, (KtSafeQualifiedExpression) right, opToken);
if (isPrimitive(leftType) && right instanceof KtSafeQualifiedExpression &&
isSelectorPureNonNullType(((KtSafeQualifiedExpression) right))) {
return genCmpPrimitiveToSafeCall(left, leftType, (KtSafeQualifiedExpression) right, opToken, pregeneratedLeft);
}
if (BoxedToPrimitiveEquality.isApplicable(opToken, leftType, rightType)) {
return BoxedToPrimitiveEquality.create(
opToken,
genLazyUnlessProvided(pregeneratedLeft, left, leftType), leftType,
genLazy(right, rightType), rightType,
myFrameMap
);
}
if (PrimitiveToBoxedEquality.isApplicable(opToken, leftType, rightType)) {
return PrimitiveToBoxedEquality.create(
opToken,
genLazyUnlessProvided(pregeneratedLeft, left, leftType), leftType,
genLazy(right, rightType), rightType
);
}
if (PrimitiveToObjectEquality.isApplicable(opToken, leftType, rightType)) {
return PrimitiveToObjectEquality.create(
opToken,
genLazyUnlessProvided(pregeneratedLeft, left, leftType), leftType,
genLazy(right, rightType), rightType
);
}
if (isPrimitive(leftType) != isPrimitive(rightType)) {
leftType = boxType(leftType);
rightType = boxType(rightType);
@@ -2913,23 +3060,38 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
if (opToken == KtTokens.EQEQEQ || opToken == KtTokens.EXCLEQEQEQ) {
// TODO: always casting to the type of the left operand in case of primitives looks wrong
Type operandType = isPrimitive(leftType) ? leftType : OBJECT_TYPE;
return StackValue.cmp(opToken, operandType, genLazy(left, leftType), genLazy(right, rightType));
return StackValue.cmp(
opToken,
operandType,
genLazyUnlessProvided(pregeneratedLeft, left, leftType),
genLazy(right, rightType)
);
}
return genEqualsForExpressionsPreferIEEE754Arithmetic(left, right, opToken, leftType, rightType, null);
return genEqualsForExpressionsPreferIEEE754Arithmetic(left, right, opToken, leftType, rightType, pregeneratedLeft);
}
private boolean isSelectorPureNonNullType(@NotNull KtSafeQualifiedExpression safeExpression) {
KtExpression expression = safeExpression.getSelectorExpression();
if (expression == null) return false;
ResolvedCall<?> resolvedCall = CallUtilKt.getResolvedCall(expression, bindingContext);
if (resolvedCall == null) return false;
KotlinType returnType = resolvedCall.getResultingDescriptor().getReturnType();
return returnType != null && !TypeUtils.isNullableType(returnType);
}
private StackValue genCmpPrimitiveToSafeCall(
@NotNull KtExpression left,
@NotNull Type leftType,
@NotNull KtSafeQualifiedExpression right,
@NotNull IElementType opToken
@NotNull IElementType opToken,
@Nullable StackValue pregeneratedLeft
) {
Label rightIsNull = new Label();
return new PrimitiveToSafeCallEquality(
opToken,
leftType,
genLazy(left, leftType),
genLazyUnlessProvided(pregeneratedLeft, left, leftType),
generateSafeQualifiedExpression(right, rightIsNull),
expressionType(right.getReceiverExpression()),
rightIsNull
@@ -2990,7 +3152,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
return genEqualsForExpressionsOnStack(
opToken,
pregeneratedLeft != null ? StackValue.coercion(pregeneratedLeft, leftType) : genLazy(left, leftType),
genLazyUnlessProvided(pregeneratedLeft, left, leftType),
genLazy(right, rightType)
);
}
@@ -3006,12 +3168,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
) {
Type leftType = left754Type.isNullable ? AsmUtil.boxType(left754Type.type) : left754Type.type;
if (pregeneratedLeft != null) {
StackValue.coercion(pregeneratedLeft, leftType).put(leftType, v);
}
else {
gen(left, leftType);
}
genUnlessProvided(pregeneratedLeft, left, leftType);
Type rightType = right754Type.isNullable ? AsmUtil.boxType(right754Type.type) : right754Type.type;
gen(right, rightType);
@@ -3116,16 +3273,22 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
}
private boolean isIntZero(KtExpression expr, Type exprType) {
ConstantValue<?> exprValue = getPrimitiveOrStringCompileTimeConstant(expr, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> exprValue = getPrimitiveOrStringCompileTimeConstant(expr);
return isIntPrimitive(exprType) && exprValue != null && Integer.valueOf(0).equals(exprValue.getValue());
}
private StackValue genCmpWithZero(KtExpression exp, IElementType opToken) {
return StackValue.compareIntWithZero(gen(exp), (KtTokens.EQEQ == opToken || KtTokens.EQEQEQ == opToken) ? IFNE : IFEQ);
private StackValue genCmpWithZero(KtExpression exp, IElementType opToken, @Nullable StackValue pregeneratedExpr) {
return StackValue.compareIntWithZero(
pregeneratedExpr != null ? pregeneratedExpr : gen(exp),
(KtTokens.EQEQ == opToken || KtTokens.EQEQEQ == opToken) ? IFNE : IFEQ
);
}
private StackValue genCmpWithNull(KtExpression exp, IElementType opToken) {
return StackValue.compareWithNull(gen(exp), (KtTokens.EQEQ == opToken || KtTokens.EQEQEQ == opToken) ? IFNONNULL : IFNULL);
private StackValue genCmpWithNull(KtExpression exp, IElementType opToken, @Nullable StackValue pregeneratedExpr) {
return StackValue.compareWithNull(
pregeneratedExpr != null ? pregeneratedExpr : gen(exp),
(KtTokens.EQEQ == opToken || KtTokens.EQEQEQ == opToken) ? IFNONNULL : IFNULL
);
}
private StackValue generateElvis(@NotNull KtBinaryExpression expression) {
@@ -3245,7 +3408,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
public void invokeAppend(InstructionAdapter v, KtExpression expr) {
expr = KtPsiUtil.safeDeparenthesize(expr);
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expr, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expr);
if (compileTimeConstant == null) {
if (expr instanceof KtBinaryExpression) {
@@ -3295,7 +3458,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@Override
public StackValue visitPrefixExpression(@NotNull KtPrefixExpression expression, @NotNull StackValue receiver) {
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expression, bindingContext, state.getShouldInlineConstVals());
ConstantValue<?> compileTimeConstant = getPrimitiveOrStringCompileTimeConstant(expression);
if (compileTimeConstant != null) {
return StackValue.constant(compileTimeConstant.getValue(), expressionType(expression));
}
@@ -3413,6 +3576,9 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
else if (delegateExpression != null) {
initializeLocalVariable(property, gen(delegateExpression));
}
else if (property.hasModifier(KtTokens.LATEINIT_KEYWORD)) {
initializeLocalVariable(property, null);
}
return StackValue.none();
}
@@ -3444,10 +3610,6 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
initializeDestructuringDeclarationVariables(multiDeclaration, initializerAsReceiver, local, asProperty);
if (initializerAsmType.getSort() == Type.OBJECT || initializerAsmType.getSort() == Type.ARRAY) {
v.aconst(null);
v.store(tempVarIndex, initializerAsmType);
}
myFrameMap.leaveTemp(initializerAsmType);
return StackValue.none();
@@ -3479,13 +3641,8 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
if (asProperty && variableDescriptor instanceof PropertyDescriptor) {
StackValue.Property propertyValue = intermediateValueForProperty(
(PropertyDescriptor) variableDescriptor,
true,
false,
null,
true,
StackValue.LOCAL_0,
null);
(PropertyDescriptor) variableDescriptor, true, false, null, true, StackValue.LOCAL_0, null, false
);
propertyValue.store(invokeFunction(call, resolvedCall, receiverStackValue), v);
}
@@ -3496,7 +3653,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
}
@NotNull
private StackValue getVariableMetadataValue(VariableDescriptor variableDescriptor) {
private StackValue getVariableMetadataValue(@NotNull VariableDescriptorWithAccessors variableDescriptor) {
StackValue value = findLocalOrCapturedValue(getDelegatedLocalVariableMetadata(variableDescriptor, bindingContext));
assert value != null : "Can't find stack value for local delegated variable metadata: " + variableDescriptor;
return value;
@@ -3513,7 +3670,7 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
private void initializeLocalVariable(
@NotNull KtVariableDeclaration variableDeclaration,
@NotNull StackValue initializer
@Nullable StackValue initializer
) {
LocalVariableDescriptor variableDescriptor = (LocalVariableDescriptor) getVariableDescriptorNotNull(variableDeclaration);
@@ -3533,6 +3690,14 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
StackValue storeTo = sharedVarType == null ? StackValue.local(index, varType) : StackValue.shared(index, varType);
storeTo.putReceiver(v, false);
if (variableDescriptor.isLateInit()) {
assert initializer == null : "Initializer should be null for lateinit var " + variableDescriptor + ": " + initializer;
v.aconst(null);
storeTo.storeSelector(storeTo.type, v);
return;
}
assert initializer != null : "Initializer should be not null for " + variableDescriptor;
initializer.put(initializer.type, v);
markLineNumber(variableDeclaration, false);
@@ -3542,14 +3707,13 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
StackValue metadataValue = getVariableMetadataValue(variableDescriptor);
initializePropertyMetadata((KtProperty) variableDeclaration, variableDescriptor, metadataValue);
ResolvedCall<FunctionDescriptor> provideDelegateResolvedCall = bindingContext.get(PROVIDE_DELEGATE_RESOLVED_CALL, variableDescriptor);
if (provideDelegateResolvedCall != null) {
resultType = generateProvideDelegateCallForLocalVariable(initializer, metadataValue, provideDelegateResolvedCall);
ResolvedCall<FunctionDescriptor> provideDelegateCall = bindingContext.get(PROVIDE_DELEGATE_RESOLVED_CALL, variableDescriptor);
if (provideDelegateCall != null) {
resultType = generateProvideDelegateCallForLocalVariable(initializer, metadataValue, provideDelegateCall);
}
}
storeTo.storeSelector(resultType, v);
}
@NotNull
@@ -3596,10 +3760,16 @@ public class ExpressionCodegen extends KtVisitor<StackValue, StackValue> impleme
@NotNull LocalVariableDescriptor variableDescriptor,
@NotNull StackValue metadataVar
) {
// TODO: do not generate anonymous classes for local delegated properties in inline functions
// We can use the $$delegatedProperties array as in non-inline functions and upon inlining, detect elements at what indices
// of that array are used in the inline function body, load the corresponding initializing bytecode from <clinit> of the
// container class (where the PropertyReferenceNImpl instance is created), copy and adapt it at the call site
//noinspection ConstantConditions
StackValue value = generatePropertyReference(variable.getDelegate(), variableDescriptor, variableDescriptor, null, null);
value.put(K_PROPERTY0_TYPE, v);
metadataVar.storeSelector(K_PROPERTY0_TYPE, v);
StackValue value = context.getFunctionDescriptor().isInline()
? generatePropertyReference(variable.getDelegate(), variableDescriptor, variableDescriptor, null)
: PropertyCodegen.getDelegatedPropertyMetadata(variableDescriptor, bindingContext);
value.put(K_PROPERTY_TYPE, v);
metadataVar.storeSelector(K_PROPERTY_TYPE, v);
}
@NotNull
@@ -3988,22 +4158,7 @@ The "returned" value of try expression with no finally is either the last expres
private StackValue generateExpressionMatch(StackValue expressionToMatch, KtExpression subjectExpression, KtExpression patternExpression) {
if (expressionToMatch != null) {
Type subjectType = expressionToMatch.type;
markStartLineNumber(patternExpression);
KotlinType condJetType = bindingContext.getType(patternExpression);
Type condType;
if (isNumberPrimitiveOrBoolean(subjectType)) {
assert condJetType != null;
condType = asmType(condJetType);
if (!isNumberPrimitiveOrBoolean(condType)) {
subjectType = boxType(subjectType);
}
}
else {
condType = OBJECT_TYPE;
}
return genEqualsForExpressionsPreferIEEE754Arithmetic(subjectExpression, patternExpression, KtTokens.EQEQ, subjectType, condType, expressionToMatch);
return generateEquals(subjectExpression, patternExpression, KtTokens.EQEQ, expressionToMatch);
}
else {
return gen(patternExpression);
@@ -4076,12 +4231,12 @@ The "returned" value of try expression with no finally is either the last expres
Type resultType = isStatement ? Type.VOID_TYPE : expressionType(expression);
return StackValue.operation(resultType, v -> {
SwitchCodegen switchCodegen = SwitchCodegenUtil.buildAppropriateSwitchCodegenIfPossible(
expression, isStatement, CodegenUtil.isExhaustive(bindingContext, expression, isStatement), this
SwitchCodegen switchCodegen = switchCodegenProvider.buildAppropriateSwitchCodegenIfPossible(
expression, isStatement, CodegenUtil.isExhaustive(bindingContext, expression, isStatement)
);
if (switchCodegen != null) {
switchCodegen.generate();
return Unit.INSTANCE;
return null;
}
int subjectLocal = expr != null ? myFrameMap.enterTemp(subjectType) : -1;

View File

@@ -34,7 +34,7 @@ public class FieldInfo {
}
if (isNonCompanionObject(classDescriptor) || CompanionObjectMapping.INSTANCE.isMappedIntrinsicCompanionObject(classDescriptor)) {
return createSingletonViaInstance(classDescriptor, typeMapper);
return createSingletonViaInstance(classDescriptor, typeMapper, JvmAbi.INSTANCE_FIELD);
}
ClassDescriptor ownerDescriptor = DescriptorUtils.getParentOfType(classDescriptor, ClassDescriptor.class);
@@ -46,10 +46,11 @@ public class FieldInfo {
@NotNull
public static FieldInfo createSingletonViaInstance(
@NotNull ClassDescriptor classDescriptor,
@NotNull KotlinTypeMapper typeMapper
@NotNull KotlinTypeMapper typeMapper,
@NotNull String name
) {
Type type = typeMapper.mapType(classDescriptor);
return new FieldInfo(type, type, JvmAbi.INSTANCE_FIELD, true);
return new FieldInfo(type, type, name, true);
}
@NotNull

View File

@@ -204,53 +204,6 @@ public class FunctionCodegen {
return;
}
boolean isOpenSuspendInClass =
functionDescriptor.isSuspend() &&
functionDescriptor.getModality() != Modality.ABSTRACT && isOverridable(functionDescriptor) &&
!isInterface(functionDescriptor.getContainingDeclaration()) &&
origin.getOriginKind() != JvmDeclarationOriginKind.CLASS_MEMBER_DELEGATION_TO_DEFAULT_IMPL;
if (isOpenSuspendInClass) {
MethodVisitor mv =
v.newMethod(origin,
flags,
asmMethod.getName(),
asmMethod.getDescriptor(),
jvmSignature.getGenericsSignature(),
getThrownExceptions(functionDescriptor, typeMapper)
);
mv.visitCode();
mv.visitVarInsn(Opcodes.ALOAD, 0);
int index = 1;
for (Type type : asmMethod.getArgumentTypes()) {
mv.visitVarInsn(type.getOpcode(Opcodes.ILOAD), index);
index += type.getSize();
}
asmMethod = CoroutineCodegenUtilKt.getImplForOpenMethod(asmMethod, v.getThisName());
// remove generic signature as it's unnecessary for synthetic methods
jvmSignature =
new JvmMethodGenericSignature(
asmMethod,
jvmSignature.getValueParameters(),
null
);
mv.visitMethodInsn(
Opcodes.INVOKESTATIC,
v.getThisName(), asmMethod.getName(), asmMethod.getDescriptor(),
false
);
mv.visitInsn(Opcodes.ARETURN);
mv.visitEnd();
flags |= Opcodes.ACC_STATIC | Opcodes.ACC_SYNTHETIC;
flags &= ~getVisibilityAccessFlag(functionDescriptor);
flags |= AsmUtil.NO_FLAG_PACKAGE_PRIVATE;
}
MethodVisitor mv =
strategy.wrapMethodVisitor(
v.newMethod(origin,
@@ -286,6 +239,79 @@ public class FunctionCodegen {
parentBodyCodegen.addAdditionalTask(new JvmStaticInCompanionObjectGenerator(functionDescriptor, origin, state, parentBodyCodegen));
}
boolean isOpenSuspendInClass =
functionDescriptor.isSuspend() &&
functionDescriptor.getModality() != Modality.ABSTRACT && isOverridable(functionDescriptor) &&
!isInterface(functionDescriptor.getContainingDeclaration()) &&
origin.getOriginKind() != JvmDeclarationOriginKind.CLASS_MEMBER_DELEGATION_TO_DEFAULT_IMPL;
if (isOpenSuspendInClass) {
mv.visitCode();
mv.visitVarInsn(Opcodes.ALOAD, 0);
int index = 1;
for (Type type : asmMethod.getArgumentTypes()) {
mv.visitVarInsn(type.getOpcode(Opcodes.ILOAD), index);
index += type.getSize();
}
Method asmMethodForOpenSuspendImpl = CoroutineCodegenUtilKt.getImplForOpenMethod(asmMethod, v.getThisName());
// remove generic signature as it's unnecessary for synthetic methods
JvmMethodSignature jvmSignatureForOpenSuspendImpl =
new JvmMethodGenericSignature(
asmMethodForOpenSuspendImpl,
jvmSignature.getValueParameters(),
null
);
mv.visitMethodInsn(
Opcodes.INVOKESTATIC,
v.getThisName(), asmMethodForOpenSuspendImpl.getName(), asmMethodForOpenSuspendImpl.getDescriptor(),
false
);
mv.visitInsn(Opcodes.ARETURN);
mv.visitEnd();
int flagsForOpenSuspendImpl = flags;
flagsForOpenSuspendImpl |= Opcodes.ACC_STATIC | Opcodes.ACC_SYNTHETIC;
flagsForOpenSuspendImpl &= ~getVisibilityAccessFlag(functionDescriptor);
flagsForOpenSuspendImpl |= AsmUtil.NO_FLAG_PACKAGE_PRIVATE;
MethodVisitor mvForOpenSuspendImpl = strategy.wrapMethodVisitor(
v.newMethod(origin,
flagsForOpenSuspendImpl,
asmMethodForOpenSuspendImpl.getName(),
asmMethodForOpenSuspendImpl.getDescriptor(),
null,
getThrownExceptions(functionDescriptor, typeMapper)
),
flagsForOpenSuspendImpl, asmMethodForOpenSuspendImpl.getName(),
asmMethodForOpenSuspendImpl.getDescriptor()
);
generateMethodBody(
origin, functionDescriptor, methodContext, strategy, mvForOpenSuspendImpl, jvmSignatureForOpenSuspendImpl,
staticInCompanionObject
);
}
else {
generateMethodBody(
origin, functionDescriptor, methodContext, strategy, mv, jvmSignature, staticInCompanionObject
);
}
}
private void generateMethodBody(
@NotNull JvmDeclarationOrigin origin,
@NotNull FunctionDescriptor functionDescriptor,
@NotNull MethodContext methodContext,
@NotNull FunctionGenerationStrategy strategy,
@NotNull MethodVisitor mv,
@NotNull JvmMethodSignature jvmSignature,
boolean staticInCompanionObject
) {
OwnerKind contextKind = methodContext.getContextKind();
if (!state.getClassBuilderMode().generateBodies || isAbstractMethod(functionDescriptor, contextKind, state)) {
generateLocalVariableTable(
mv,
@@ -595,8 +621,31 @@ public class FunctionCodegen {
@NotNull KotlinTypeMapper typeMapper,
int shiftForDestructuringVariables
) {
generateLocalVariablesForParameters(mv, jvmMethodSignature, thisType, methodBegin, methodEnd,
functionDescriptor.getValueParameters(),
if (functionDescriptor.isSuspend()) {
FunctionDescriptor unwrapped = CoroutineCodegenUtilKt.unwrapInitialDescriptorForSuspendFunction(
functionDescriptor
);
if (unwrapped != functionDescriptor) {
generateLocalVariableTable(
mv,
new JvmMethodSignature(
jvmMethodSignature.getAsmMethod(),
jvmMethodSignature.getValueParameters().subList(
0,
jvmMethodSignature.getValueParameters().size() - 1
)
),
unwrapped,
thisType, methodBegin, methodEnd, ownerKind, typeMapper, shiftForDestructuringVariables
);
return;
}
}
generateLocalVariablesForParameters(mv,
jvmMethodSignature,
thisType, methodBegin, methodEnd, functionDescriptor.getValueParameters(),
AsmUtil.isStaticMethod(ownerKind, functionDescriptor), typeMapper, shiftForDestructuringVariables
);
}
@@ -786,7 +835,9 @@ public class FunctionCodegen {
}
}
private static String renderByteCodeIfAvailable(MethodVisitor mv) {
@SuppressWarnings("WeakerAccess") // Useful in debug
@Nullable
public static String renderByteCodeIfAvailable(@NotNull MethodVisitor mv) {
String bytecode = null;
if (mv instanceof TransformationMethodVisitor) {

View File

@@ -24,10 +24,7 @@ import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.calls.model.DelegatingResolvedCall;
import org.jetbrains.kotlin.resolve.calls.model.ExpressionValueArgument;
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
import org.jetbrains.kotlin.resolve.calls.model.ResolvedValueArgument;
import org.jetbrains.kotlin.resolve.calls.model.*;
import org.jetbrains.kotlin.resolve.calls.util.CallMaker;
import org.jetbrains.kotlin.resolve.jvm.jvmSignature.JvmMethodSignature;
import org.jetbrains.kotlin.resolve.scopes.receivers.ExpressionReceiver;
@@ -40,8 +37,24 @@ import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import static org.jetbrains.kotlin.resolve.DescriptorUtils.isObject;
/*
* Notice the difference between two function descriptors in this class.
* - [referencedFunction] is the function declaration which is referenced by the "::" expression. This is a real function present in code.
* - [functionDescriptor] is a synthetically created function which has the same signature as the "invoke" of the generated callable
* reference subclass. Its parameters include dispatch/extension receiver parameters of the referenced function, and those value
* parameters of the referenced function which are required by the expected function type where the callable reference is passed to.
* In simple cases, these value parameters are all of the referenced function's value parameters. But in cases when the referenced
* function has parameters with default values, or a vararg parameter, functionDescriptor can take fewer parameters than
* referencedFunction if the expected function type takes fewer parameters as well. For example:
*
* fun foo(a: A, b: B = ..., c: C = ..., vararg d: D) {}
*
* fun bar(f: (A, B) -> Unit) {}
*
* // referencedFunction: foo(A, B, C, vararg D)
* // functionDescriptor: invoke(A, B)
* bar(::foo)
*/
public class FunctionReferenceGenerationStrategy extends FunctionGenerationStrategy.CodegenBased {
private final ResolvedCall<?> resolvedCall;
private final FunctionDescriptor referencedFunction;
@@ -80,20 +93,21 @@ public class FunctionReferenceGenerationStrategy extends FunctionGenerationStrat
every argument boils down to calling LOAD with the corresponding index
*/
KtCallExpression fakeExpression = CodegenUtil.constructFakeFunctionCall(state.getProject(), referencedFunction);
int receivers = CallableReferenceUtilKt.computeExpectedNumberOfReceivers(referencedFunction, receiverType != null);
KtCallExpression fakeExpression =
CodegenUtil.constructFakeFunctionCall(state.getProject(), functionDescriptor.getValueParameters().size() - receivers);
List<? extends ValueArgument> fakeArguments = fakeExpression.getValueArguments();
ReceiverValue dispatchReceiver = computeAndSaveReceiver(signature, codegen, referencedFunction.getDispatchReceiverParameter());
ReceiverValue extensionReceiver = computeAndSaveReceiver(signature, codegen, referencedFunction.getExtensionReceiverParameter());
computeAndSaveArguments(fakeArguments, codegen);
computeAndSaveArguments(fakeArguments, codegen, receivers);
ResolvedCall<CallableDescriptor> fakeResolvedCall = new DelegatingResolvedCall<CallableDescriptor>(resolvedCall) {
private final Map<ValueParameterDescriptor, ResolvedValueArgument> argumentMap;
private final Map<ValueParameterDescriptor, ResolvedValueArgument> argumentMap = new LinkedHashMap<>();
{
argumentMap = new LinkedHashMap<>(fakeArguments.size());
int index = 0;
List<ValueParameterDescriptor> parameters = functionDescriptor.getValueParameters();
List<ValueParameterDescriptor> parameters = referencedFunction.getValueParameters();
for (ValueArgument argument : fakeArguments) {
argumentMap.put(parameters.get(index), new ExpressionValueArgument(argument));
index++;
@@ -146,20 +160,14 @@ public class FunctionReferenceGenerationStrategy extends FunctionGenerationStrat
v.areturn(returnType);
}
private void computeAndSaveArguments(@NotNull List<? extends ValueArgument> fakeArguments, @NotNull ExpressionCodegen codegen) {
int receivers = (referencedFunction.getDispatchReceiverParameter() != null ? 1 : 0) +
(referencedFunction.getExtensionReceiverParameter() != null ? 1 : 0) -
(receiverType != null ? 1 : 0);
if (receivers < 0 && referencedFunction instanceof ConstructorDescriptor && isObject(referencedFunction.getContainingDeclaration().getContainingDeclaration())) {
//reference to object nested class
//TODO: seems problem should be fixed on frontend side (note that object instance are captured by generated class)
receivers = 0;
}
List<ValueParameterDescriptor> parameters = CollectionsKt.drop(functionDescriptor.getValueParameters(), receivers);
for (int i = 0; i < parameters.size(); i++) {
ValueParameterDescriptor parameter = parameters.get(i);
private void computeAndSaveArguments(
@NotNull List<? extends ValueArgument> fakeArguments, @NotNull ExpressionCodegen codegen, int receivers
) {
List<ValueParameterDescriptor> valueParameters = CollectionsKt.drop(functionDescriptor.getValueParameters(), receivers);
assert valueParameters.size() == fakeArguments.size()
: functionDescriptor + ": " + valueParameters.size() + " != " + fakeArguments.size();
for (int i = 0; i < valueParameters.size(); i++) {
ValueParameterDescriptor parameter = valueParameters.get(i);
ValueArgument fakeArgument = fakeArguments.get(i);
Type type = state.getTypeMapper().mapType(parameter);

View File

@@ -35,10 +35,10 @@ import org.jetbrains.kotlin.codegen.signature.BothSignatureWriter;
import org.jetbrains.kotlin.codegen.signature.JvmSignatureWriter;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.config.LanguageFeature;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.incremental.components.NoLookupLocation;
import org.jetbrains.kotlin.lexer.KtTokens;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.load.java.descriptors.JavaClassDescriptor;
import org.jetbrains.kotlin.load.kotlin.TypeMappingMode;
import org.jetbrains.kotlin.name.ClassId;
@@ -64,10 +64,7 @@ import org.jetbrains.kotlin.resolve.scopes.receivers.ExtensionReceiver;
import org.jetbrains.kotlin.resolve.scopes.receivers.ImplicitReceiver;
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue;
import org.jetbrains.kotlin.types.KotlinType;
import org.jetbrains.org.objectweb.asm.FieldVisitor;
import org.jetbrains.org.objectweb.asm.Label;
import org.jetbrains.org.objectweb.asm.MethodVisitor;
import org.jetbrains.org.objectweb.asm.Type;
import org.jetbrains.org.objectweb.asm.*;
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter;
import org.jetbrains.org.objectweb.asm.commons.Method;
@@ -79,6 +76,7 @@ import static org.jetbrains.kotlin.codegen.CodegenUtilKt.isNonGenericToArray;
import static org.jetbrains.kotlin.codegen.JvmCodegenUtil.*;
import static org.jetbrains.kotlin.codegen.binding.CodegenBinding.enumEntryNeedSubclass;
import static org.jetbrains.kotlin.codegen.inline.InlineCodegenUtils2Kt.initDefaultSourceMappingIfNeeded;
import static org.jetbrains.kotlin.load.java.JvmAbi.*;
import static org.jetbrains.kotlin.resolve.BindingContextUtils.getDelegationConstructorCall;
import static org.jetbrains.kotlin.resolve.BindingContextUtils.getNotNull;
import static org.jetbrains.kotlin.resolve.DescriptorToSourceUtils.descriptorToDeclaration;
@@ -356,6 +354,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
protected void generateSyntheticPartsAfterBody() {
generateFieldForSingleton();
initializeObjects();
generateCompanionObjectBackingFieldCopies();
generateTraitMethods();
@@ -813,21 +813,21 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
}
private void generateFieldForSingleton() {
if (isCompanionObjectInInterfaceNotIntrinsic(descriptor)) {
StackValue.Field field = StackValue.createSingletonViaInstance(descriptor, typeMapper, HIDDEN_INSTANCE_FIELD);
//hidden instance in interface companion
v.newField(JvmDeclarationOriginKt.OtherOrigin(descriptor),
ACC_SYNTHETIC | ACC_STATIC | ACC_FINAL, field.name, field.type.getDescriptor(), null, null);
}
if (isEnumEntry(descriptor) || isCompanionObject(descriptor)) return;
if (isNonCompanionObject(descriptor)) {
StackValue.Field field = StackValue.singletonViaInstance(descriptor, typeMapper);
StackValue.Field field = StackValue.createSingletonViaInstance(descriptor, typeMapper, INSTANCE_FIELD);
v.newField(JvmDeclarationOriginKt.OtherOriginFromPure(myClass),
ACC_PUBLIC | ACC_STATIC | ACC_FINAL,
field.name, field.type.getDescriptor(), null, null);
if (!state.getClassBuilderMode().generateBodies) return;
// Invoke the object constructor but ignore the result because INSTANCE will be initialized in the first line of <init>
InstructionAdapter v = createOrGetClInitCodegen().v;
markLineNumberForElement(element.getPsiOrParent(), v);
v.anew(classAsmType);
v.invokespecial(classAsmType.getInternalName(), "<init>", "()V", false);
return;
}
@@ -838,9 +838,75 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
@Nullable KtObjectDeclaration companionObject = CollectionsKt.firstOrNull(myClass.getCompanionObjects());
int properFieldVisibilityFlag = getVisibilityAccessFlag(companionObjectDescriptor);
boolean fieldShouldBeDeprecated =
state.getLanguageVersionSettings().supportsFeature(LanguageFeature.DeprecatedFieldForInvisibleCompanionObject) &&
(properFieldVisibilityFlag & (ACC_PRIVATE | ACC_PROTECTED)) != 0;
// TODO generate field with proper visibility in language version 1.3
int fieldAccessFlags = ACC_PUBLIC | ACC_STATIC | ACC_FINAL;
if (fieldShouldBeDeprecated) {
fieldAccessFlags |= ACC_DEPRECATED;
}
StackValue.Field field = StackValue.singleton(companionObjectDescriptor, typeMapper);
v.newField(JvmDeclarationOriginKt.OtherOrigin(companionObject == null ? myClass.getPsiOrParent() : companionObject),
ACC_PUBLIC | ACC_STATIC | ACC_FINAL, field.name, field.type.getDescriptor(), null, null);
FieldVisitor fv = v.newField(JvmDeclarationOriginKt.OtherOrigin(companionObject == null ? myClass.getPsiOrParent() : companionObject),
fieldAccessFlags, field.name, field.type.getDescriptor(), null, null);
if (fieldShouldBeDeprecated) {
AnnotationCodegen.forField(fv, this, typeMapper).visitAnnotation("Ljava/lang/Deprecated;", true).visitEnd();
}
}
private void initializeObjects() {
if (!DescriptorUtils.isObject(descriptor)) return;
if (!state.getClassBuilderMode().generateBodies) return;
boolean isNonCompanionObject = isNonCompanionObject(descriptor);
boolean isInterfaceCompanion = isCompanionObjectInInterfaceNotIntrinsic(descriptor);
boolean isMappedIntrinsicCompanionObject = isMappedIntrinsicCompanionObject(descriptor);
if (isNonCompanionObject || isInterfaceCompanion || isMappedIntrinsicCompanionObject) {
ExpressionCodegen clInitCodegen = createOrGetClInitCodegen();
InstructionAdapter v = clInitCodegen.v;
markLineNumberForElement(element.getPsiOrParent(), v);
v.anew(classAsmType);
v.dup();
v.invokespecial(classAsmType.getInternalName(), "<init>", "()V", false);
//local0 emulates this in object constructor
int local0Index = clInitCodegen.getFrameMap().enterTemp(classAsmType);
assert local0Index == 0 : "Local variable with index 0 in clInit should be used only for singleton instance keeping";
StackValue.Local local0 = StackValue.local(0, classAsmType);
local0.store(StackValue.onStack(classAsmType), clInitCodegen.v);
StackValue.Field singleton =
StackValue.createSingletonViaInstance(
descriptor, typeMapper, isInterfaceCompanion ? HIDDEN_INSTANCE_FIELD : INSTANCE_FIELD
);
singleton.store(local0, clInitCodegen.v);
generateInitializers(clInitCodegen);
if (isInterfaceCompanion) {
//initialize singleton instance in outer by hidden instance
StackValue.singleton(descriptor, typeMapper).store(
singleton, getParentCodegen().createOrGetClInitCodegen().v, true
);
}
}
else if (isCompanionObjectWithBackingFieldsInOuter(descriptor)) {
ImplementationBodyCodegen parentCodegen = (ImplementationBodyCodegen) getParentCodegen();
ExpressionCodegen parentClInitCodegen = parentCodegen.createOrGetClInitCodegen();
InstructionAdapter parentVisitor = parentClInitCodegen.v;
FunctionDescriptor constructor = (FunctionDescriptor) parentCodegen.context.accessibleDescriptor(
CollectionsKt.single(descriptor.getConstructors()), /* superCallExpression = */ null
);
parentCodegen.generateMethodCallTo(constructor, null, parentVisitor);
StackValue instance = StackValue.onStack(parentCodegen.typeMapper.mapClass(descriptor));
StackValue.singleton(descriptor, parentCodegen.typeMapper).store(instance, parentVisitor, true);
generateInitializers(parentClInitCodegen);
}
else {
assert false : "Unknown object type: " + descriptor;
}
}
private void generateCompanionObjectBackingFieldCopies() {
@@ -890,17 +956,6 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
field.store(property, codegen.v);
}
private void generateCompanionObjectInitializer(@NotNull ClassDescriptor companionObject) {
ExpressionCodegen codegen = createOrGetClInitCodegen();
FunctionDescriptor constructor = (FunctionDescriptor) context.accessibleDescriptor(
CollectionsKt.single(companionObject.getConstructors()), /* superCallExpression = */ null
);
generateMethodCallTo(constructor, null, codegen.v);
StackValue instance = StackValue.onStack(typeMapper.mapClass(companionObject));
StackValue.singleton(companionObject, typeMapper).store(instance, codegen.v, true);
}
private void generatePrimaryConstructor(DelegationFieldsInfo delegationFieldsInfo) {
if (isInterface(descriptor) || isAnnotationClass(descriptor)) return;
@@ -968,10 +1023,6 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
generateDelegatorToConstructorCall(iv, codegen, constructorDescriptor,
getDelegationConstructorCall(bindingContext, constructorDescriptor));
if (isNonCompanionObject(descriptor)) {
StackValue.singletonViaInstance(descriptor, typeMapper).store(StackValue.LOCAL_0, iv);
}
for (KtSuperTypeListEntry specifier : myClass.getSuperTypeListEntries()) {
if (specifier instanceof KtDelegatedSuperTypeEntry) {
genCallToDelegatorByExpressionSpecifier(iv, codegen, (KtDelegatedSuperTypeEntry) specifier, fieldsInfo);
@@ -993,18 +1044,10 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
curParam++;
}
if (isCompanionObject(descriptor)) {
ImplementationBodyCodegen parentCodegen = (ImplementationBodyCodegen) getParentCodegen();
parentCodegen.generateCompanionObjectInitializer(descriptor);
}
if (JvmAbi.isCompanionObjectWithBackingFieldsInOuter(descriptor)) {
generateInitializers(((ImplementationBodyCodegen) getParentCodegen())::createOrGetClInitCodegen);
}
else {
//object initialization was moved to initializeObjects()
if (!isObject(descriptor)) {
generateInitializers(codegen);
}
iv.visitInsn(RETURN);
}
@@ -1149,7 +1192,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
if (asmType == null) continue;
result.addField((KtDelegatedSuperTypeEntry) specifier, asmType, JvmAbi.DELEGATE_SUPER_FIELD_PREFIX + n);
result.addField((KtDelegatedSuperTypeEntry) specifier, asmType, DELEGATE_SUPER_FIELD_PREFIX + n);
}
n++;
}
@@ -1237,9 +1280,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
}
}
private void lookupInContext(@NotNull DeclarationDescriptor toLookup) {
ExpressionCodegen.lookupValuaAndLocalVariableMetadata(toLookup, StackValue.LOCAL_0, state, true, context, null);
context.lookupInContext(toLookup, StackValue.LOCAL_0, state, true);
}
@Override
@@ -1395,7 +1437,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
}
else {
argumentGenerator =
generateSuperCallImplicitArguments(iv, codegen, constructorDescriptor, delegateConstructor, delegateConstructorCallable,
generateSuperCallImplicitArguments(iv, codegen, constructorDescriptor, delegateConstructor, delegationConstructorCall,
delegateConstructorCallable,
delegatingParameters,
parameters);
}
@@ -1414,6 +1457,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
@NotNull ExpressionCodegen codegen,
@NotNull ConstructorDescriptor constructorDescriptor,
@NotNull ConstructorDescriptor superConstructor,
@NotNull ResolvedCall<ConstructorDescriptor> superConstructorCall,
@NotNull CallableMethod superCallable,
@NotNull List<JvmMethodParameterSignature> superParameters,
@NotNull List<JvmMethodParameterSignature> parameters
@@ -1456,7 +1500,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
if (isAnonymousObject(descriptor)) {
List<JvmMethodParameterSignature> superValues = superParameters.subList(superIndex, superParameters.size());
return new ObjectSuperCallArgumentGenerator(superValues, iv, offset);
return new ObjectSuperCallArgumentGenerator(superValues, iv, offset, superConstructorCall);
}
else {
return new CallBasedArgumentGenerator(codegen, codegen.defaultCallGenerator, superConstructor.getValueParameters(),
@@ -1497,49 +1541,6 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
delegatingCallable.getValueParameterTypes());
}
private static class ObjectSuperCallArgumentGenerator extends ArgumentGenerator {
private final List<JvmMethodParameterSignature> parameters;
private final InstructionAdapter iv;
private int offset;
public ObjectSuperCallArgumentGenerator(
@NotNull List<JvmMethodParameterSignature> superParameters,
@NotNull InstructionAdapter iv,
int firstValueParamOffset
) {
this.parameters = superParameters;
this.iv = iv;
this.offset = firstValueParamOffset;
}
@Override
public void generateExpression(int i, @NotNull ExpressionValueArgument argument) {
generateSuperCallArgument(i);
}
@Override
public void generateDefault(int i, @NotNull DefaultValueArgument argument) {
Type type = parameters.get(i).getAsmType();
pushDefaultValueOnStack(type, iv);
}
@Override
public void generateVararg(int i, @NotNull VarargValueArgument argument) {
generateSuperCallArgument(i);
}
private void generateSuperCallArgument(int i) {
Type type = parameters.get(i).getAsmType();
iv.load(offset, type);
offset += type.getSize();
}
@Override
protected void reorderArgumentsIfNeeded(@NotNull List<ArgumentAndDeclIndex> args) {
}
}
private void generateEnumEntries() {
if (descriptor.getKind() != ClassKind.ENUM_CLASS) return;

View File

@@ -23,9 +23,9 @@ import org.jetbrains.kotlin.diagnostics.DiagnosticSink
import org.jetbrains.kotlin.diagnostics.Errors
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall
class InlineCycleReporter(val diagnostics: DiagnosticSink) {
class InlineCycleReporter(private val diagnostics: DiagnosticSink) {
val processingFunctions = linkedMapOf<PsiElement, CallableDescriptor>()
private val processingFunctions = linkedMapOf<PsiElement, CallableDescriptor>()
fun enterIntoInlining(call: ResolvedCall<*>?): Boolean {
//null call for default method inlining

View File

@@ -17,7 +17,35 @@
package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.descriptors.ClassDescriptor
import org.jetbrains.kotlin.descriptors.ClassKind
import org.jetbrains.kotlin.descriptors.Modality
import org.jetbrains.kotlin.descriptors.SourceElement
import org.jetbrains.kotlin.descriptors.impl.ClassDescriptorImpl
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.DescriptorUtils
import org.jetbrains.kotlin.resolve.scopes.MemberScope
import java.util.*
interface InnerClassConsumer {
fun addInnerClassInfoFromAnnotation(classDescriptor: ClassDescriptor)
companion object {
fun classForInnerClassRecord(descriptor: ClassDescriptor, defaultImpls: Boolean): ClassDescriptor? {
if (defaultImpls) {
if (DescriptorUtils.isLocal(descriptor)) return null
val classDescriptorImpl = ClassDescriptorImpl(
descriptor, Name.identifier(JvmAbi.DEFAULT_IMPLS_CLASS_NAME),
Modality.FINAL, ClassKind.CLASS, Collections.emptyList(), SourceElement.NO_SOURCE,
/* isExternal = */ false)
classDescriptorImpl.initialize(MemberScope.Empty, emptySet(), null)
return classDescriptorImpl
}
else {
return if (DescriptorUtils.isTopLevelDeclaration(descriptor)) null else descriptor
}
}
}
}

View File

@@ -22,20 +22,14 @@ import org.jetbrains.kotlin.backend.common.bridges.firstSuperMethodFromKotlin
import org.jetbrains.kotlin.codegen.context.ClassContext
import org.jetbrains.kotlin.codegen.state.GenerationState
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.impl.ClassDescriptorImpl
import org.jetbrains.kotlin.load.java.JvmAbi
import org.jetbrains.kotlin.load.java.descriptors.JavaMethodDescriptor
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.psi.KtPureClassOrObject
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils
import org.jetbrains.kotlin.resolve.DescriptorUtils
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOrigin
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOriginKind
import org.jetbrains.kotlin.resolve.jvm.jvmSignature.JvmMethodSignature
import org.jetbrains.kotlin.resolve.scopes.MemberScope
import org.jetbrains.org.objectweb.asm.MethodVisitor
import org.jetbrains.org.objectweb.asm.Opcodes.*
import java.util.*
class InterfaceImplBodyCodegen(
aClass: KtPureClassOrObject,
@@ -47,12 +41,14 @@ class InterfaceImplBodyCodegen(
private var isAnythingGenerated: Boolean = false
get() = (v as InterfaceImplClassBuilder).isAnythingGenerated
private val defaultImplType = typeMapper.mapDefaultImpls(descriptor)
override fun generateDeclaration() {
val codegenFlags = ACC_PUBLIC or ACC_FINAL or ACC_SUPER
val flags = if (state.classBuilderMode == ClassBuilderMode.LIGHT_CLASSES) codegenFlags or ACC_STATIC else codegenFlags
v.defineClass(
myClass.psiOrParent, state.classFileVersion, flags,
typeMapper.mapDefaultImpls(descriptor).internalName,
defaultImplType.internalName,
null, "java/lang/Object", ArrayUtil.EMPTY_STRING_ARRAY
)
v.visitSource(myClass.containingKtFile.name, null)
@@ -60,14 +56,7 @@ class InterfaceImplBodyCodegen(
override fun classForInnerClassRecord(): ClassDescriptor? {
if (!isAnythingGenerated) return null
if (DescriptorUtils.isLocal(descriptor)) return null
val classDescriptorImpl = ClassDescriptorImpl(
descriptor, Name.identifier(JvmAbi.DEFAULT_IMPLS_CLASS_NAME),
Modality.FINAL, ClassKind.CLASS, Collections.emptyList(), SourceElement.NO_SOURCE,
/* isExternal = */ false)
classDescriptorImpl.initialize(MemberScope.Empty, emptySet(), null)
return classDescriptorImpl
return InnerClassConsumer.classForInnerClassRecord(descriptor, true)
}
override fun generateSyntheticPartsAfterBody() {
@@ -161,7 +150,7 @@ class InterfaceImplBodyCodegen(
override fun done() {
super.done()
if (!isAnythingGenerated) {
state.factory.removeClasses(setOf(typeMapper.mapDefaultImpls(descriptor).internalName))
state.factory.removeClasses(setOf(defaultImplType.internalName))
}
}
@@ -190,4 +179,8 @@ class InterfaceImplBodyCodegen(
return super.newMethod(origin, access, name, desc, signature, exceptions)
}
}
override fun generateSyntheticPartsBeforeBody() {
generatePropertyMetadataArrayFieldIfNeeded(defaultImplType)
}
}

View File

@@ -22,6 +22,7 @@ import org.jetbrains.kotlin.codegen.coroutines.getOrCreateJvmSuspendFunctionView
import org.jetbrains.kotlin.coroutines.isSuspendLambda
import org.jetbrains.kotlin.descriptors.*
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor
import org.jetbrains.kotlin.descriptors.impl.MutableClassDescriptor
import org.jetbrains.kotlin.descriptors.impl.MutablePackageFragmentDescriptor
@@ -29,7 +30,6 @@ import org.jetbrains.kotlin.name.FqName
import org.jetbrains.kotlin.name.Name
import org.jetbrains.kotlin.resolve.descriptorUtil.builtIns
import org.jetbrains.kotlin.types.KotlinType
import org.jetbrains.kotlin.types.expressions.ExpressionTypingUtils
class JvmRuntimeTypes(module: ModuleDescriptor) {
private val kotlinJvmInternalPackage = MutablePackageFragmentDescriptor(module, FqName("kotlin.jvm.internal"))
@@ -77,7 +77,7 @@ class JvmRuntimeTypes(module: ModuleDescriptor) {
descriptor.builtIns,
Annotations.EMPTY,
actualFunctionDescriptor.extensionReceiverParameter?.type,
ExpressionTypingUtils.getValueParametersTypes(actualFunctionDescriptor.valueParameters),
actualFunctionDescriptor.valueParameters.map { it.type },
null,
actualFunctionDescriptor.returnType!!
)
@@ -94,14 +94,20 @@ class JvmRuntimeTypes(module: ModuleDescriptor) {
return listOf(lambda.defaultType, functionType)
}
fun getSupertypesForFunctionReference(descriptor: FunctionDescriptor, isBound: Boolean): Collection<KotlinType> {
fun getSupertypesForFunctionReference(
referencedFunction: FunctionDescriptor,
anonymousFunctionDescriptor: AnonymousFunctionDescriptor,
isBound: Boolean
): Collection<KotlinType> {
val receivers = computeExpectedNumberOfReceivers(referencedFunction, isBound)
val functionType = createFunctionType(
descriptor.builtIns,
referencedFunction.builtIns,
Annotations.EMPTY,
if (isBound) null else descriptor.extensionReceiverParameter?.type ?: descriptor.dispatchReceiverParameter?.type,
ExpressionTypingUtils.getValueParametersTypes(descriptor.valueParameters),
if (isBound) null else referencedFunction.extensionReceiverParameter?.type ?: referencedFunction.dispatchReceiverParameter?.type,
anonymousFunctionDescriptor.valueParameters.drop(receivers).map { it.type },
null,
descriptor.returnType!!
referencedFunction.returnType!!
)
return listOf(functionReference.defaultType, functionType)

View File

@@ -25,9 +25,9 @@ import org.jetbrains.kotlin.resolve.jvm.diagnostics.Synthetic
import org.jetbrains.kotlin.resolve.jvm.jvmSignature.JvmMethodSignature
class JvmStaticInCompanionObjectGenerator(
val descriptor: FunctionDescriptor,
val declarationOrigin: JvmDeclarationOrigin,
val state: GenerationState,
private val descriptor: FunctionDescriptor,
private val declarationOrigin: JvmDeclarationOrigin,
private val state: GenerationState,
parentBodyCodegen: ImplementationBodyCodegen
) : Function2<ImplementationBodyCodegen, ClassBuilder, Unit> {
private val typeMapper = state.typeMapper
@@ -94,8 +94,7 @@ class JvmStaticInCompanionObjectGenerator(
CallableMemberDescriptor.Kind.SYNTHESIZED,
false
)
val staticFunctionDescriptor = copies[descriptor]!!
return staticFunctionDescriptor
return copies[descriptor]!!
}
}
}

View File

@@ -16,11 +16,12 @@
package org.jetbrains.kotlin.codegen;
import com.google.common.collect.Sets;
import com.intellij.util.containers.MultiMap;
import kotlin.collections.SetsKt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.fileClasses.JvmFileClassInfo;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.progress.ProgressIndicatorAndCompilationCanceledStatus;
import org.jetbrains.kotlin.psi.KtFile;
@@ -55,7 +56,7 @@ public class KotlinCodegenFacade {
for (KtFile file : files) {
if (file == null) throw new IllegalArgumentException("A null file given for compilation");
JvmFileClassInfo fileClassInfo = state.getFileClassesProvider().getFileClassInfo(file);
JvmFileClassInfo fileClassInfo = JvmFileClassUtil.getFileClassInfoNoResolve(file);
if (fileClassInfo.getWithJvmMultifileClass()) {
filesInMultifileClasses.putValue(fileClassInfo.getFacadeClassFqName(), file);
@@ -66,13 +67,13 @@ public class KotlinCodegenFacade {
}
Set<FqName> obsoleteMultifileClasses = new HashSet<>(state.getObsoleteMultifileClasses());
for (FqName multifileClassFqName : Sets.union(filesInMultifileClasses.keySet(), obsoleteMultifileClasses)) {
for (FqName multifileClassFqName : SetsKt.plus(filesInMultifileClasses.keySet(), obsoleteMultifileClasses)) {
doCheckCancelled(state);
generateMultifileClass(state, multifileClassFqName, filesInMultifileClasses.get(multifileClassFqName), errorHandler);
}
Set<FqName> packagesWithObsoleteParts = new HashSet<>(state.getPackagesWithObsoleteParts());
for (FqName packageFqName : Sets.union(packagesWithObsoleteParts, filesInPackages.keySet())) {
for (FqName packageFqName : SetsKt.plus(packagesWithObsoleteParts, filesInPackages.keySet())) {
doCheckCancelled(state);
generatePackage(state, packageFqName, filesInPackages.get(packageFqName), errorHandler);
}

View File

@@ -24,6 +24,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.backend.common.CodegenUtil;
import org.jetbrains.kotlin.codegen.annotation.AnnotatedSimple;
import org.jetbrains.kotlin.codegen.binding.CodegenBinding;
import org.jetbrains.kotlin.codegen.context.*;
import org.jetbrains.kotlin.codegen.inline.DefaultSourceMapper;
import org.jetbrains.kotlin.codegen.inline.NameGenerator;
@@ -36,8 +37,7 @@ import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.annotations.AnnotationUseSiteTarget;
import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.descriptors.impl.SimpleFunctionDescriptorImpl;
import org.jetbrains.kotlin.fileClasses.FileClasses;
import org.jetbrains.kotlin.fileClasses.JvmFileClassesProvider;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.load.java.JavaVisibilities;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.load.java.JvmAnnotationNames;
@@ -47,7 +47,6 @@ import org.jetbrains.kotlin.name.SpecialNames;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.synthetics.SyntheticClassOrObjectDescriptor;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.BindingContextUtils;
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils;
import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall;
import org.jetbrains.kotlin.resolve.constants.ConstantValue;
@@ -69,7 +68,10 @@ import org.jetbrains.org.objectweb.asm.Type;
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter;
import org.jetbrains.org.objectweb.asm.commons.Method;
import java.util.*;
import java.util.Collection;
import java.util.Collections;
import java.util.LinkedHashSet;
import java.util.List;
import static org.jetbrains.kotlin.codegen.AsmUtil.*;
import static org.jetbrains.kotlin.codegen.JvmCodegenUtil.isJvm8InterfaceWithDefaultsMember;
@@ -95,7 +97,6 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
public final KotlinTypeMapper typeMapper;
public final BindingContext bindingContext;
private final JvmFileClassesProvider fileClassesProvider;
private final MemberCodegen<?> parentCodegen;
private final ReifiedTypeParametersUsages reifiedTypeParametersUsages = new ReifiedTypeParametersUsages();
private final Collection<ClassDescriptor> innerClasses = new LinkedHashSet<>();
@@ -115,7 +116,6 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
this.state = state;
this.typeMapper = state.getTypeMapper();
this.bindingContext = state.getBindingContext();
this.fileClassesProvider = state.getFileClassesProvider();
this.element = element;
this.context = context;
this.v = builder;
@@ -339,12 +339,7 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
parentCodegen.innerClasses.add(classDescriptor);
}
for (MemberCodegen<?> codegen = this; codegen != null; codegen = codegen.getParentCodegen()) {
ClassDescriptor outerClass = codegen.classForInnerClassRecord();
if (outerClass != null) {
innerClasses.add(outerClass);
}
}
addParentsToInnerClassesIfNeeded(innerClasses);
}
for (ClassDescriptor innerClass : innerClasses) {
@@ -352,6 +347,18 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
}
}
protected void addParentsToInnerClassesIfNeeded(@NotNull Collection<ClassDescriptor> innerClasses) {
ClassDescriptor outerClass = classForInnerClassRecord();
if (outerClass != null) {
innerClasses.add(outerClass);
}
MemberCodegen<?> parentCodegen = getParentCodegen();
if (parentCodegen != null) {
parentCodegen.addParentsToInnerClassesIfNeeded(innerClasses);
}
}
// It's necessary for proper recovering of classId by plain string JVM descriptor when loading annotations
// See FileBasedKotlinClass.convertAnnotationVisitor
@Override
@@ -423,7 +430,7 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
return implementationOwnerType;
}
else {
return FileClasses.getFileClassType(fileClassesProvider, element.getContainingKtFile());
return Type.getObjectType(JvmFileClassUtil.getFileClassInternalName(element.getContainingKtFile()));
}
}
@@ -451,7 +458,7 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
@NotNull
public NameGenerator getInlineNameGenerator() {
if (inlineNameGenerator == null) {
String prefix = getInlineName(context, typeMapper, fileClassesProvider);
String prefix = getInlineName(context, typeMapper);
inlineNameGenerator = new NameGenerator(prefix);
}
return inlineNameGenerator;
@@ -506,7 +513,8 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
public void beforeMethodBody(@NotNull MethodVisitor mv) {
}
private void initializeProperty(@NotNull ExpressionCodegen codegen, @NotNull KtProperty property) {
// Requires public access, because it is used by serialization plugin to generate initializer in synthetic constructor
public void initializeProperty(@NotNull ExpressionCodegen codegen, @NotNull KtProperty property) {
PropertyDescriptor propertyDescriptor = (PropertyDescriptor) bindingContext.get(VARIABLE, property);
assert propertyDescriptor != null;
@@ -514,7 +522,8 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
assert initializer != null : "shouldInitializeProperty must return false if initializer is null";
StackValue.Property propValue = codegen.intermediateValueForProperty(
propertyDescriptor, true, false, null, true, StackValue.LOCAL_0, null);
propertyDescriptor, true, false, null, true, StackValue.LOCAL_0, null, false
);
ResolvedCall<FunctionDescriptor> provideDelegateResolvedCall = bindingContext.get(PROVIDE_DELEGATE_RESOLVED_CALL, propertyDescriptor);
if (provideDelegateResolvedCall == null) {
@@ -524,17 +533,15 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
StackValue provideDelegateReceiver = codegen.gen(initializer);
int indexOfDelegatedProperty = PropertyCodegen.indexOfDelegatedProperty(property);
StackValue delegateValue = PropertyCodegen.invokeDelegatedPropertyConventionMethodWithReceiver(
codegen, typeMapper, provideDelegateResolvedCall, indexOfDelegatedProperty, 1,
provideDelegateReceiver, propertyDescriptor
StackValue delegateValue = PropertyCodegen.invokeDelegatedPropertyConventionMethod(
codegen, provideDelegateResolvedCall, provideDelegateReceiver, propertyDescriptor
);
propValue.store(delegateValue, codegen.v);
}
protected boolean shouldInitializeProperty(@NotNull KtProperty property) {
// Public accessible for serialization plugin to check whether call to initializeProperty(..) is legal.
public boolean shouldInitializeProperty(@NotNull KtProperty property) {
if (!property.hasDelegateExpressionOrInitializer()) return false;
PropertyDescriptor propertyDescriptor = (PropertyDescriptor) bindingContext.get(VARIABLE, property);
@@ -608,16 +615,8 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
}
protected void generatePropertyMetadataArrayFieldIfNeeded(@NotNull Type thisAsmType) {
List<KtProperty> delegatedProperties = new ArrayList<>();
for (KtDeclaration declaration : ((KtDeclarationContainer) element).getDeclarations()) {
if (declaration instanceof KtProperty) {
KtProperty property = (KtProperty) declaration;
if (property.hasDelegate()) {
delegatedProperties.add(property);
}
}
}
if (delegatedProperties.isEmpty()) return;
List<VariableDescriptorWithAccessors> delegatedProperties = bindingContext.get(CodegenBinding.DELEGATED_PROPERTIES, thisAsmType);
if (delegatedProperties == null || delegatedProperties.isEmpty()) return;
v.newField(NO_ORIGIN, ACC_STATIC | ACC_FINAL | ACC_SYNTHETIC, JvmAbi.DELEGATED_PROPERTIES_ARRAY_NAME,
"[" + K_PROPERTY_TYPE, null, null);
@@ -629,8 +628,7 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
iv.newarray(K_PROPERTY_TYPE);
for (int i = 0, size = delegatedProperties.size(); i < size; i++) {
PropertyDescriptor property =
(PropertyDescriptor) BindingContextUtils.getNotNull(bindingContext, VARIABLE, delegatedProperties.get(i));
VariableDescriptorWithAccessors property = delegatedProperties.get(i);
iv.dup();
iv.iconst(i);
@@ -640,10 +638,12 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
Type implType = property.isVar() ? MUTABLE_PROPERTY_REFERENCE_IMPL[receiverCount] : PROPERTY_REFERENCE_IMPL[receiverCount];
iv.anew(implType);
iv.dup();
// TODO: generate the container once and save to a local field instead (KT-10495)
ClosureCodegen.generateCallableReferenceDeclarationContainer(iv, property, state);
iv.aconst(property.getName().asString());
PropertyReferenceCodegen.generateCallableReferenceSignature(iv, property, state);
iv.invokespecial(
implType.getInternalName(), "<init>",
Type.getMethodDescriptor(Type.VOID_TYPE, K_DECLARATION_CONTAINER_TYPE, JAVA_STRING_TYPE, JAVA_STRING_TYPE), false
@@ -736,6 +736,7 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
class PropertyAccessorStrategy extends FunctionGenerationStrategy.CodegenBased {
private final PropertyAccessorDescriptor callableDescriptor;
private PropertyAccessorStrategy(@NotNull PropertyAccessorDescriptor callableDescriptor) {
super(MemberCodegen.this.state);
this.callableDescriptor = callableDescriptor;
@@ -743,7 +744,9 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
@Override
public void doGenerateBody(@NotNull ExpressionCodegen codegen, @NotNull JvmMethodSignature signature) {
boolean syntheticBackingField = accessor instanceof AccessorForPropertyBackingFieldFromLocal;
FieldAccessorKind fieldAccessorKind = accessor instanceof AccessorForPropertyBackingField
? ((AccessorForPropertyBackingField) accessor).getFieldAccessorKind() : null;
boolean syntheticBackingField = fieldAccessorKind == FieldAccessorKind.FIELD_FROM_LOCAL;
boolean forceFieldForCompanionProperty = JvmAbi.isPropertyWithBackingFieldInOuterClass(original) &&
!isCompanionObject(accessor.getContainingDeclaration());
boolean forceField = forceFieldForCompanionProperty ||
@@ -751,7 +754,8 @@ public abstract class MemberCodegen<T extends KtPureElement/* TODO: & KtDeclarat
original.getVisibility() == JavaVisibilities.PROTECTED_STATIC_VISIBILITY;
StackValue property = codegen.intermediateValueForProperty(
original, forceField, syntheticBackingField, accessor.getSuperCallTarget(),
forceFieldForCompanionProperty, StackValue.none(), null
forceFieldForCompanionProperty, StackValue.none(), null,
fieldAccessorKind == FieldAccessorKind.LATEINIT_INTRINSIC
);
InstructionAdapter iv = codegen.v;

View File

@@ -77,9 +77,6 @@ class MultifileClassCodegenImpl(
.getContributedDescriptors(DescriptorKindFilter.CALLABLES, MemberScope.ALL_NAME_FILTER)
.filterIsInstance<DeserializedCallableMemberDescriptor>()
private fun KtFile.getFileClassFqName() =
state.fileClassesProvider.getFileClassInfo(this).fileClassFqName
private val shouldGeneratePartHierarchy =
state.inheritMultifileParts
@@ -87,7 +84,7 @@ class MultifileClassCodegenImpl(
val partInternalNamesSet = hashSetOf<String>()
for (file in files) {
if (file.hasDeclarationsForPartClass()) {
partInternalNamesSet.add(file.getFileClassFqName().toInternalName())
partInternalNamesSet.add(JvmFileClassUtil.getFileClassInternalName(file))
}
}
compiledPackageFragment?.let {
@@ -205,17 +202,14 @@ class MultifileClassCodegenImpl(
val packageFragment = this.packageFragment
?: throw AssertionError("File part $file of $facadeFqName: no package fragment")
val partClassFqName = file.getFileClassFqName()
val partInitializerClassFqName = FqName(partClassFqName.asString() + "__Init")
val partType = partClassFqName.toAsmType()
val partInitializerType = partInitializerClassFqName.toAsmType()
val partContext = state.rootContext.intoMultifileClassPart(packageFragment, facadeClassType, partType, partInitializerType, file)
val partType = Type.getObjectType(JvmFileClassUtil.getFileClassInternalName(file))
val partContext = state.rootContext.intoMultifileClassPart(packageFragment, facadeClassType, partType, file)
generateNonPartClassDeclarations(file, partContext)
if (!state.generateDeclaredClassFilter.shouldGeneratePackagePart(file) || !file.hasDeclarationsForPartClass()) return
packagePartRegistry.addPart(partType.internalName.substringAfterLast('/'), facadeClassType.internalName.substringAfterLast('/'))
packagePartRegistry.addPart(partType.internalName, facadeClassType.internalName)
val builder = state.factory.newVisitor(MultifileClassPart(file, packageFragment), partType, file)
@@ -323,7 +317,7 @@ class MultifileClassCodegenImpl(
private fun writeKotlinMultifileFacadeAnnotationIfNeeded() {
if (!state.classBuilderMode.generateMetadata) return
if (files.any { it.isScript }) return
if (files.any { it.isScript() }) return
val extraFlags = if (shouldGeneratePartHierarchy) JvmAnnotationNames.METADATA_MULTIFILE_PARTS_INHERIT_FLAG else 0
@@ -375,12 +369,6 @@ class MultifileClassCodegenImpl(
private fun KtFile.hasDeclarationsForPartClass() =
declarations.any { it is KtProperty || it is KtFunction }
private fun FqName.toInternalName() =
AsmUtil.internalNameByFqNameWithoutInnerClasses(this)
private fun FqName.toAsmType() =
AsmUtil.asmTypeByFqNameWithoutInnerClasses(this)
private fun getCompiledPackageFragment(
facadeFqName: FqName, state: GenerationState
): IncrementalPackageFragmentProvider.IncrementalMultifileClassPackageFragment? {
@@ -396,5 +384,4 @@ class MultifileClassCodegenImpl(
return incrementalPackageFragment?.getPackageFragmentForMultifileClass(facadeFqName)
}
}
}
}

View File

@@ -175,8 +175,11 @@ class MultifileClassPartCodegen(
}
}
val serializer = DescriptorSerializer.createTopLevel(JvmSerializerExtension(v.serializationBindings, state))
val packageProto = serializer.packagePartProto(packageFragment.fqName, members).build()
val extension = JvmSerializerExtension(v.serializationBindings, state)
val serializer = DescriptorSerializer.createTopLevel(extension)
val builder = serializer.packagePartProto(packageFragment.fqName, members)
extension.serializeJvmPackage(builder, partType)
val packageProto = builder.build()
val extraFlags = if (shouldGeneratePartHierarchy) JvmAnnotationNames.METADATA_MULTIFILE_PARTS_INHERIT_FLAG else 0

View File

@@ -0,0 +1,77 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.codegen
import org.jetbrains.kotlin.codegen.AsmUtil.pushDefaultValueOnStack
import org.jetbrains.kotlin.descriptors.CallableDescriptor
import org.jetbrains.kotlin.descriptors.ConstructorDescriptor
import org.jetbrains.kotlin.resolve.calls.model.*
import org.jetbrains.kotlin.resolve.jvm.jvmSignature.JvmMethodParameterSignature
import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter
internal class ObjectSuperCallArgumentGenerator(
private val parameters: List<JvmMethodParameterSignature>,
private val iv: InstructionAdapter,
offset: Int,
superConstructorCall: ResolvedCall<ConstructorDescriptor>
) : ArgumentGenerator() {
private val offsets = IntArray(parameters.size) { -1 }
init {
var currentOffset = offset
superConstructorCall.valueArguments.forEach {
(descriptor, argument) ->
if (argument !is DefaultValueArgument) {
val index = descriptor.index
offsets[index] = currentOffset
currentOffset += parameters[index].asmType.size
}
}
}
override fun generate(
valueArgumentsByIndex: List<ResolvedValueArgument>,
actualArgs: List<ResolvedValueArgument>,
calleeDescriptor: CallableDescriptor?
): DefaultCallArgs = super.generate(valueArgumentsByIndex, valueArgumentsByIndex, calleeDescriptor)
public override fun generateExpression(i: Int, argument: ExpressionValueArgument) {
generateSuperCallArgument(i)
}
public override fun generateDefault(i: Int, argument: DefaultValueArgument) {
val type = parameters[i].asmType
pushDefaultValueOnStack(type, iv)
}
public override fun generateVararg(i: Int, argument: VarargValueArgument) {
generateSuperCallArgument(i)
}
private fun generateSuperCallArgument(i: Int) {
val type = parameters[i].asmType
if (offsets[i] == -1) {
throw AssertionError("Unknown parameter value at index $i with type $type")
}
iv.load(offsets[i], type)
}
override fun reorderArgumentsIfNeeded(args: List<ArgumentAndDeclIndex>) {
}
}

View File

@@ -20,7 +20,6 @@ import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.progress.ProcessCanceledException;
import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.util.SmartList;
import kotlin.text.StringsKt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.codegen.context.PackageContext;
@@ -28,10 +27,11 @@ import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.descriptors.PackageFragmentDescriptor;
import org.jetbrains.kotlin.diagnostics.DiagnosticUtils;
import org.jetbrains.kotlin.fileClasses.JvmFileClassInfo;
import org.jetbrains.kotlin.lexer.KtTokens;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.progress.ProgressIndicatorAndCompilationCanceledStatus;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.psiUtil.PsiUtilsKt;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.jvm.diagnostics.JvmDeclarationOriginKt;
import org.jetbrains.org.objectweb.asm.Type;
@@ -88,11 +88,8 @@ public class PackageCodegenImpl implements PackageCodegen {
}
private void generateFile(@NotNull KtFile file) {
JvmFileClassInfo fileClassInfo = state.getFileClassesProvider().getFileClassInfo(file);
if (fileClassInfo.getWithJvmMultifileClass()) {
return;
}
JvmFileClassInfo fileClassInfo = JvmFileClassUtil.getFileClassInfoNoResolve(file);
if (fileClassInfo.getWithJvmMultifileClass()) return;
Type fileClassType = AsmUtil.asmTypeByFqNameWithoutInnerClasses(fileClassInfo.getFileClassFqName());
PackageContext packagePartContext = state.getRootContext().intoPackagePart(packageFragment, fileClassType, file);
@@ -102,7 +99,7 @@ public class PackageCodegenImpl implements PackageCodegen {
List<KtClassOrObject> classOrObjects = new ArrayList<>();
for (KtDeclaration declaration : file.getDeclarations()) {
if (declaration.hasModifier(KtTokens.HEADER_KEYWORD)) continue;
if (PsiUtilsKt.hasExpectModifier(declaration)) continue;
if (declaration instanceof KtProperty || declaration instanceof KtNamedFunction || declaration instanceof KtTypeAlias) {
generatePackagePart = true;
@@ -125,8 +122,7 @@ public class PackageCodegenImpl implements PackageCodegen {
if (!generatePackagePart || !state.getGenerateDeclaredClassFilter().shouldGeneratePackagePart(file)) return;
String name = fileClassType.getInternalName();
packagePartRegistry.addPart(StringsKt.substringAfterLast(name, '/', name), null);
packagePartRegistry.addPart(fileClassType.getInternalName(), null);
ClassBuilder builder = state.getFactory().newVisitor(JvmDeclarationOriginKt.PackagePart(file, packageFragment), fileClassType, file);

View File

@@ -30,9 +30,9 @@ import org.jetbrains.kotlin.descriptors.VariableDescriptor;
import org.jetbrains.kotlin.descriptors.annotations.Annotated;
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor;
import org.jetbrains.kotlin.descriptors.annotations.AnnotationsImpl;
import org.jetbrains.kotlin.lexer.KtTokens;
import org.jetbrains.kotlin.load.kotlin.header.KotlinClassHeader;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.psiUtil.PsiUtilsKt;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.serialization.DescriptorSerializer;
import org.jetbrains.kotlin.serialization.ProtoBuf;
@@ -89,7 +89,7 @@ public class PackagePartCodegen extends MemberCodegen<KtFile> {
@Override
protected void generateBody() {
for (KtDeclaration declaration : element.getDeclarations()) {
if (declaration.hasModifier(KtTokens.HEADER_KEYWORD)) continue;
if (PsiUtilsKt.hasExpectModifier(declaration)) continue;
if (declaration instanceof KtNamedFunction || declaration instanceof KtProperty || declaration instanceof KtTypeAlias) {
genSimpleMember(declaration);
@@ -119,9 +119,11 @@ public class PackagePartCodegen extends MemberCodegen<KtFile> {
}
}
DescriptorSerializer serializer =
DescriptorSerializer.createTopLevel(new JvmSerializerExtension(v.getSerializationBindings(), state));
ProtoBuf.Package packageProto = serializer.packagePartProto(element.getPackageFqName(), members).build();
JvmSerializerExtension extension = new JvmSerializerExtension(v.getSerializationBindings(), state);
DescriptorSerializer serializer = DescriptorSerializer.createTopLevel(extension);
ProtoBuf.Package.Builder builder = serializer.packagePartProto(element.getPackageFqName(), members);
extension.serializeJvmPackage(builder, packagePartType);
ProtoBuf.Package packageProto = builder.build();
WriteAnnotationUtilKt.writeKotlinMetadata(v, state, KotlinClassHeader.Kind.FILE_FACADE, 0, av -> {
writeAnnotationData(av, serializer, packageProto);

View File

@@ -17,5 +17,5 @@
package org.jetbrains.kotlin.codegen
interface PackagePartRegistry {
fun addPart(partShortName: String, facadeShortName: String?)
fun addPart(partInternalName: String, facadeInternalName: String?)
}

View File

@@ -21,7 +21,10 @@ import com.intellij.psi.PsiElement;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.codegen.annotation.AnnotatedWithFakeAnnotations;
import org.jetbrains.kotlin.codegen.context.*;
import org.jetbrains.kotlin.codegen.context.CodegenContextUtil;
import org.jetbrains.kotlin.codegen.context.FieldOwnerContext;
import org.jetbrains.kotlin.codegen.context.MultifileClassFacadeContext;
import org.jetbrains.kotlin.codegen.context.MultifileClassPartContext;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.descriptors.*;
@@ -32,7 +35,6 @@ import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtilKt;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.psiUtil.PsiUtilsKt;
import org.jetbrains.kotlin.resolve.BindingContext;
import org.jetbrains.kotlin.resolve.DescriptorFactory;
import org.jetbrains.kotlin.resolve.DescriptorToSourceUtils;
@@ -60,6 +62,8 @@ import static org.jetbrains.kotlin.codegen.AsmUtil.getDeprecatedAccessFlag;
import static org.jetbrains.kotlin.codegen.AsmUtil.getVisibilityForBackingField;
import static org.jetbrains.kotlin.codegen.JvmCodegenUtil.isConstOrHasJvmFieldAnnotation;
import static org.jetbrains.kotlin.codegen.JvmCodegenUtil.isJvmInterface;
import static org.jetbrains.kotlin.codegen.binding.CodegenBinding.DELEGATED_PROPERTIES;
import static org.jetbrains.kotlin.codegen.binding.CodegenBinding.DELEGATED_PROPERTY_METADATA_OWNER;
import static org.jetbrains.kotlin.codegen.serialization.JvmSerializationBindings.FIELD_FOR_PROPERTY;
import static org.jetbrains.kotlin.codegen.serialization.JvmSerializationBindings.SYNTHETIC_METHOD_FOR_PROPERTY;
import static org.jetbrains.kotlin.resolve.DescriptorUtils.isCompanionObject;
@@ -478,7 +482,7 @@ public class PropertyCodegen {
FunctionGenerationStrategy strategy;
if (accessor == null || !accessor.hasBody()) {
if (p instanceof KtProperty && ((KtProperty) p).hasDelegate()) {
strategy = new DelegatedPropertyAccessorStrategy(state, accessorDescriptor, indexOfDelegatedProperty((KtProperty) p));
strategy = new DelegatedPropertyAccessorStrategy(state, accessorDescriptor);
}
else {
strategy = new DefaultPropertyAccessorStrategy(state, accessorDescriptor);
@@ -491,39 +495,9 @@ public class PropertyCodegen {
functionCodegen.generateMethod(JvmDeclarationOriginKt.OtherOrigin(accessor != null ? accessor : p, accessorDescriptor), accessorDescriptor, strategy);
}
public static int indexOfDelegatedProperty(@NotNull KtProperty property) {
PsiElement parent = property.getParent();
KtDeclarationContainer container;
if (parent instanceof KtClassBody) {
container = ((KtClassOrObject) parent.getParent());
}
else if (parent instanceof KtFile) {
container = (KtFile) parent;
}
else if (KtPsiUtil.isScriptDeclaration(property)) {
container = KtPsiUtil.getScript(property);
assert container != null : "Script declaration for property '" + property.getText() + "' should be not null!";
}
else {
throw new UnsupportedOperationException("Unknown delegated property container: " + parent);
}
int index = 0;
for (KtDeclaration declaration : container.getDeclarations()) {
if (declaration instanceof KtProperty && ((KtProperty) declaration).hasDelegate()) {
if (declaration == property) {
return index;
}
index++;
}
}
throw new IllegalStateException("Delegated property not found in its parent: " + PsiUtilsKt.getElementTextWithContext(property));
}
private static class DefaultPropertyAccessorStrategy extends FunctionGenerationStrategy.CodegenBased {
private final PropertyAccessorDescriptor propertyAccessorDescriptor;
public DefaultPropertyAccessorStrategy(@NotNull GenerationState state, @NotNull PropertyAccessorDescriptor descriptor) {
super(state);
propertyAccessorDescriptor = descriptor;
@@ -561,75 +535,45 @@ public class PropertyCodegen {
}
public static StackValue invokeDelegatedPropertyConventionMethod(
@NotNull PropertyDescriptor propertyDescriptor,
@NotNull ExpressionCodegen codegen,
@NotNull KotlinTypeMapper typeMapper,
@NotNull ResolvedCall<FunctionDescriptor> resolvedCall,
int indexInPropertyMetadataArray,
int propertyMetadataArgumentIndex
) {
StackValue.Property receiver = codegen.intermediateValueForProperty(propertyDescriptor, true, null, StackValue.LOCAL_0);
return invokeDelegatedPropertyConventionMethodWithReceiver(
codegen, typeMapper, resolvedCall, indexInPropertyMetadataArray, propertyMetadataArgumentIndex,
receiver, propertyDescriptor
);
}
public static StackValue invokeDelegatedPropertyConventionMethodWithReceiver(
@NotNull ExpressionCodegen codegen,
@NotNull KotlinTypeMapper typeMapper,
@NotNull ResolvedCall<FunctionDescriptor> resolvedCall,
int indexInPropertyMetadataArray,
int propertyMetadataArgumentIndex,
@Nullable StackValue receiver,
@NotNull PropertyDescriptor propertyDescriptor
) {
Type owner = JvmAbi.isPropertyWithBackingFieldInOuterClass(propertyDescriptor) ?
codegen.getState().getTypeMapper().mapOwner(propertyDescriptor) :
getDelegatedPropertyMetadataOwner(codegen, typeMapper);
codegen.tempVariables.put(
resolvedCall.getCall().getValueArguments().get(propertyMetadataArgumentIndex).asElement(),
new StackValue(K_PROPERTY_TYPE) {
@Override
public void putSelector(@NotNull Type type, @NotNull InstructionAdapter v) {
Field array = StackValue.field(
Type.getType("[" + K_PROPERTY_TYPE), owner, JvmAbi.DELEGATED_PROPERTIES_ARRAY_NAME, true, StackValue.none()
);
StackValue.arrayElement(
K_PROPERTY_TYPE, array, StackValue.constant(indexInPropertyMetadataArray, Type.INT_TYPE)
).put(type, v);
}
}
resolvedCall.getCall().getValueArguments().get(1).asElement(),
getDelegatedPropertyMetadata(propertyDescriptor, codegen.getBindingContext())
);
return codegen.invokeFunction(resolvedCall, receiver);
}
private static Type getDelegatedPropertyMetadataOwner(@NotNull ExpressionCodegen codegen, @NotNull KotlinTypeMapper typeMapper) {
CodegenContext<? extends ClassOrPackageFragmentDescriptor> ownerContext = codegen.getContext().getClassOrPackageParentContext();
if (ownerContext instanceof ClassContext) {
return typeMapper.mapClass(((ClassContext) ownerContext).getContextDescriptor());
}
else if (ownerContext instanceof PackageContext) {
return ((PackageContext) ownerContext).getPackagePartType();
}
else if (ownerContext instanceof MultifileClassContextBase) {
return ((MultifileClassContextBase) ownerContext).getFilePartType();
}
else {
throw new UnsupportedOperationException("Unknown context: " + ownerContext);
@NotNull
public static StackValue getDelegatedPropertyMetadata(
@NotNull VariableDescriptorWithAccessors descriptor,
@NotNull BindingContext bindingContext
) {
Type owner = bindingContext.get(DELEGATED_PROPERTY_METADATA_OWNER, descriptor);
assert owner != null : "Delegated property owner not found: " + descriptor;
List<VariableDescriptorWithAccessors> allDelegatedProperties = bindingContext.get(DELEGATED_PROPERTIES, owner);
int index = allDelegatedProperties == null ? -1 : allDelegatedProperties.indexOf(descriptor);
if (index < 0) {
throw new AssertionError("Delegated property not found in " + owner + ": " + descriptor);
}
StackValue.Field array = StackValue.field(
Type.getType("[" + K_PROPERTY_TYPE), owner, JvmAbi.DELEGATED_PROPERTIES_ARRAY_NAME, true, StackValue.none()
);
return StackValue.arrayElement(K_PROPERTY_TYPE, array, StackValue.constant(index, Type.INT_TYPE));
}
private static class DelegatedPropertyAccessorStrategy extends FunctionGenerationStrategy.CodegenBased {
private final int index;
private final PropertyAccessorDescriptor propertyAccessorDescriptor;
public DelegatedPropertyAccessorStrategy(@NotNull GenerationState state, @NotNull PropertyAccessorDescriptor descriptor, int index) {
public DelegatedPropertyAccessorStrategy(@NotNull GenerationState state, @NotNull PropertyAccessorDescriptor descriptor) {
super(state);
this.index = index;
propertyAccessorDescriptor = descriptor;
this.propertyAccessorDescriptor = descriptor;
}
@Override
@@ -641,8 +585,9 @@ public class PropertyCodegen {
bindingContext.get(BindingContext.DELEGATED_PROPERTY_RESOLVED_CALL, propertyAccessorDescriptor);
assert resolvedCall != null : "Resolve call should be recorded for delegate call " + signature.toString();
StackValue lastValue = invokeDelegatedPropertyConventionMethod(propertyAccessorDescriptor.getCorrespondingProperty(),
codegen, state.getTypeMapper(), resolvedCall, index, 1);
PropertyDescriptor propertyDescriptor = propertyAccessorDescriptor.getCorrespondingProperty();
StackValue.Property receiver = codegen.intermediateValueForProperty(propertyDescriptor, true, null, StackValue.LOCAL_0);
StackValue lastValue = invokeDelegatedPropertyConventionMethod(codegen, resolvedCall, receiver, propertyDescriptor);
Type asmType = signature.getReturnType();
lastValue.put(asmType, v);
v.areturn(asmType);

View File

@@ -62,7 +62,7 @@ class PropertyReferenceCodegen(
private val isLocalDelegatedProperty = target is LocalVariableDescriptor
val getFunction =
private val getFunction =
if (isLocalDelegatedProperty)
(localVariableDescriptorForReference as VariableDescriptorWithAccessors).getter!!
else
@@ -116,10 +116,11 @@ class PropertyReferenceCodegen(
generateCallableReferenceSignature(this, target, state)
}
generateMethod("property reference getOwner", ACC_PUBLIC, method("getOwner", K_DECLARATION_CONTAINER_TYPE)) {
ClosureCodegen.generateCallableReferenceDeclarationContainer(this, target, state)
}
if (!isLocalDelegatedProperty) {
generateMethod("property reference getOwner", ACC_PUBLIC, method("getOwner", K_DECLARATION_CONTAINER_TYPE)) {
ClosureCodegen.generateCallableReferenceDeclarationContainer(this, target, state)
}
generateAccessors()
}
}
@@ -164,7 +165,7 @@ class PropertyReferenceCodegen(
writeSyntheticClassMetadata(v, state)
}
fun putInstanceOnStack(receiverValue: (() -> Unit)?): StackValue {
fun putInstanceOnStack(receiverValue: StackValue?): StackValue {
return StackValue.operation(wrapperMethod.returnType) { iv ->
if (JvmCodegenUtil.isConst(closure)) {
assert(receiverValue == null) { "No receiver expected for unbound property reference: $classDescriptor" }
@@ -174,7 +175,7 @@ class PropertyReferenceCodegen(
assert(receiverValue != null) { "Receiver expected for bound property reference: $classDescriptor" }
iv.anew(asmType)
iv.dup()
receiverValue!!()
receiverValue!!.put(receiverValue.type, iv)
iv.invokespecial(asmType.internalName, "<init>", constructor.descriptor, false)
}
}
@@ -194,6 +195,17 @@ class PropertyReferenceCodegen(
@JvmStatic
fun generateCallableReferenceSignature(iv: InstructionAdapter, callable: CallableDescriptor, state: GenerationState) {
if (callable is LocalVariableDescriptor) {
val asmType = state.bindingContext.get(CodegenBinding.DELEGATED_PROPERTY_METADATA_OWNER, callable)
val allDelegatedProperties = state.bindingContext.get(CodegenBinding.DELEGATED_PROPERTIES, asmType)
val index = allDelegatedProperties?.indexOf(callable) ?: -1
if (index < 0) {
throw AssertionError("Local delegated property is not found in $asmType: $callable")
}
iv.aconst("<v#$index>") // v = "variable"
return
}
val accessor = when (callable) {
is FunctionDescriptor -> callable
is VariableDescriptorWithAccessors ->
@@ -238,13 +250,13 @@ class PropertyReferenceCodegen(
class PropertyReferenceGenerationStrategy(
val isGetter: Boolean,
val originalFunctionDesc: FunctionDescriptor,
private val originalFunctionDesc: FunctionDescriptor,
val target: VariableDescriptor,
val asmType: Type,
val receiverType: Type?,
val expression: KtElement,
state: GenerationState,
val isInliningStrategy: Boolean
private val isInliningStrategy: Boolean
) :
FunctionGenerationStrategy.CodegenBased(state) {
override fun doGenerateBody(codegen: ExpressionCodegen, signature: JvmMethodSignature) {

View File

@@ -50,12 +50,12 @@ public class SamType {
@NotNull
public KotlinType getKotlinFunctionType() {
//noinspection ConstantConditions
return getJavaClassDescriptor().getFunctionTypeForSamInterface();
return getJavaClassDescriptor().getDefaultFunctionTypeForSamInterface();
}
@NotNull
public SimpleFunctionDescriptor getAbstractMethod() {
return (SimpleFunctionDescriptor) SingleAbstractMethodUtils.getAbstractMembers(type).get(0);
public SimpleFunctionDescriptor getOriginalAbstractMethod() {
return (SimpleFunctionDescriptor) SingleAbstractMethodUtils.getAbstractMembers(getJavaClassDescriptor()).get(0);
}
@Override

View File

@@ -88,7 +88,7 @@ public class SamWrapperCodegen {
/* isExternal = */ false
);
// e.g. compare(T, T)
SimpleFunctionDescriptor erasedInterfaceFunction = samType.getAbstractMethod().getOriginal().copy(
SimpleFunctionDescriptor erasedInterfaceFunction = samType.getOriginalAbstractMethod().copy(
classDescriptor,
Modality.FINAL,
Visibilities.PUBLIC,
@@ -167,7 +167,7 @@ public class SamWrapperCodegen {
// generate sam bridges
// TODO: erasedInterfaceFunction is actually not an interface function, but function in generated class
SimpleFunctionDescriptor originalInterfaceErased = samType.getAbstractMethod().getOriginal();
SimpleFunctionDescriptor originalInterfaceErased = samType.getOriginalAbstractMethod();
SimpleFunctionDescriptorImpl descriptorForBridges = SimpleFunctionDescriptorImpl
.create(erasedInterfaceFunction.getContainingDeclaration(), erasedInterfaceFunction.getAnnotations(), originalInterfaceErased.getName(),
CallableMemberDescriptor.Kind.DECLARATION, erasedInterfaceFunction.getSource());

View File

@@ -19,7 +19,6 @@ package org.jetbrains.kotlin.codegen;
import com.intellij.psi.tree.IElementType;
import kotlin.Unit;
import kotlin.collections.ArraysKt;
import kotlin.collections.CollectionsKt;
import kotlin.jvm.functions.Function1;
import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull;
@@ -27,12 +26,12 @@ import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.builtins.KotlinBuiltIns;
import org.jetbrains.kotlin.builtins.PrimitiveType;
import org.jetbrains.kotlin.codegen.intrinsics.IntrinsicMethods;
import org.jetbrains.kotlin.codegen.intrinsics.JavaClassProperty;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.pseudoInsns.PseudoInsnsKt;
import org.jetbrains.kotlin.codegen.state.KotlinTypeMapper;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.impl.SyntheticFieldDescriptor;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.psi.KtExpression;
import org.jetbrains.kotlin.psi.ValueArgument;
import org.jetbrains.kotlin.resolve.BindingContext;
@@ -149,6 +148,11 @@ public abstract class StackValue {
return new Local(index, type);
}
@NotNull
public static Local local(int index, @NotNull Type type, @NotNull VariableDescriptor descriptor) {
return new Local(index, type, descriptor.isLateInit(), descriptor.getName());
}
@NotNull
public static Delegate delegate(
@NotNull Type type,
@@ -165,6 +169,11 @@ public abstract class StackValue {
return new Shared(index, type);
}
@NotNull
public static StackValue shared(int index, @NotNull Type type, @NotNull VariableDescriptor descriptor) {
return new Shared(index, type, descriptor.isLateInit(), descriptor.getName());
}
@NotNull
public static StackValue onStack(@NotNull Type type) {
return type == Type.VOID_TYPE ? none() : new OnStack(type);
@@ -181,7 +190,7 @@ public abstract class StackValue {
}
}
public static StackValue createDefaulValue(@NotNull Type type) {
public static StackValue createDefaultValue(@NotNull Type type) {
if (type.getSort() == Type.OBJECT || type.getSort() == Type.ARRAY) {
return constant(null, type);
}
@@ -297,9 +306,11 @@ public abstract class StackValue {
@Nullable CallableMethod setter,
@NotNull StackValue receiver,
@NotNull ExpressionCodegen codegen,
@Nullable ResolvedCall resolvedCall
@Nullable ResolvedCall resolvedCall,
boolean skipLateinitAssertion
) {
return new Property(descriptor, backingFieldOwner, getter, setter, isStaticBackingField, fieldName, type, receiver, codegen, resolvedCall);
return new Property(descriptor, backingFieldOwner, getter, setter, isStaticBackingField, fieldName, type, receiver, codegen,
resolvedCall, skipLateinitAssertion);
}
@NotNull
@@ -437,16 +448,18 @@ public abstract class StackValue {
@NotNull Type localType,
@NotNull Type classType,
@NotNull String fieldName,
@NotNull Field refWrapper
@NotNull Field refWrapper,
@NotNull VariableDescriptor variableDescriptor
) {
return new FieldForSharedVar(localType, classType, fieldName, refWrapper);
return new FieldForSharedVar(localType, classType, fieldName, refWrapper,
variableDescriptor.isLateInit(), variableDescriptor.getName());
}
@NotNull
public static FieldForSharedVar fieldForSharedVar(@NotNull FieldForSharedVar field, @NotNull StackValue newReceiver) {
Field oldReceiver = (Field) field.receiver;
Field newSharedVarReceiver = field(oldReceiver, newReceiver);
return new FieldForSharedVar(field.type, field.owner, field.name, newSharedVarReceiver);
return new FieldForSharedVar(field.type, field.owner, field.name, newSharedVarReceiver, field.isLateinit, field.variableName);
}
public static StackValue coercion(@NotNull StackValue value, @NotNull Type castType) {
@@ -518,9 +531,11 @@ public abstract class StackValue {
descriptor
);
StackValue extensionReceiver = genReceiver(receiver, codegen, resolvedCall, callableMethod, callExtensionReceiver, true);
Type type = CallReceiver.calcType(resolvedCall, dispatchReceiverParameter, extensionReceiverParameter, codegen.typeMapper, callableMethod, codegen.getState());
assert type != null : "Could not map receiver type for " + resolvedCall;
return new CallReceiver(dispatchReceiver, extensionReceiver, type);
return CallReceiver.generateCallReceiver(
resolvedCall, codegen, callableMethod,
dispatchReceiverParameter, dispatchReceiver,
extensionReceiverParameter, extensionReceiver
);
}
return receiver;
}
@@ -569,14 +584,13 @@ public abstract class StackValue {
}
@Contract("null -> false")
private static boolean isLocalFunCall(@Nullable Callable callableMethod) {
static boolean isLocalFunCall(@Nullable Callable callableMethod) {
return callableMethod != null && callableMethod.getGenerateCalleeType() != null;
}
public static StackValue receiverWithoutReceiverArgument(StackValue receiverWithParameter) {
if (receiverWithParameter instanceof CallReceiver) {
CallReceiver callReceiver = (CallReceiver) receiverWithParameter;
return new CallReceiver(callReceiver.dispatchReceiver, none(), callReceiver.type);
return ((CallReceiver) receiverWithParameter).withoutReceiverArgument();
}
return receiverWithParameter;
}
@@ -594,8 +608,8 @@ public abstract class StackValue {
return field(FieldInfo.createForSingleton(classDescriptor, typeMapper), none());
}
public static Field singletonViaInstance(ClassDescriptor classDescriptor, KotlinTypeMapper typeMapper) {
return field(FieldInfo.createSingletonViaInstance(classDescriptor, typeMapper), none());
public static Field createSingletonViaInstance(@NotNull ClassDescriptor classDescriptor, @NotNull KotlinTypeMapper typeMapper, @NotNull String name) {
return field(FieldInfo.createSingletonViaInstance(classDescriptor, typeMapper, name), none());
}
public static StackValue operation(Type type, Function1<InstructionAdapter, Unit> lambda) {
@@ -625,19 +639,35 @@ public abstract class StackValue {
public static class Local extends StackValue {
public final int index;
private final boolean isLateinit;
private final Name name;
private Local(int index, Type type) {
private Local(int index, Type type, boolean isLateinit, Name name) {
super(type, false);
this.index = index;
if (index < 0) {
throw new IllegalStateException("local variable index must be non-negative");
}
if (isLateinit && name == null) {
throw new IllegalArgumentException("Lateinit local variable should have name: #" + index + " " + type.getDescriptor());
}
this.index = index;
this.isLateinit = isLateinit;
this.name = name;
}
private Local(int index, Type type) {
this(index, type, false, null);
}
@Override
public void putSelector(@NotNull Type type, @NotNull InstructionAdapter v) {
v.load(index, this.type);
if (isLateinit) {
StackValue.genNonNullAssertForLateinit(v, name.asString());
}
coerceTo(type, v);
// TODO unbox
}
@@ -646,6 +676,9 @@ public abstract class StackValue {
public void storeSelector(@NotNull Type topOfStackType, @NotNull InstructionAdapter v) {
coerceFrom(topOfStackType, v);
v.store(index, this.type);
if (isLateinit) {
PseudoInsnsKt.storeNotNull(v);
}
}
}
@@ -1156,20 +1189,17 @@ public abstract class StackValue {
private final CallableMethod getter;
private final CallableMethod setter;
private final Type backingFieldOwner;
private final PropertyDescriptor descriptor;
private final String fieldName;
@NotNull private final ExpressionCodegen codegen;
@Nullable private final ResolvedCall resolvedCall;
private final ExpressionCodegen codegen;
private final ResolvedCall resolvedCall;
private final boolean skipLateinitAssertion;
public Property(
@NotNull PropertyDescriptor descriptor, @Nullable Type backingFieldOwner,
@Nullable CallableMethod getter, @Nullable CallableMethod setter, boolean isStaticBackingField,
@Nullable String fieldName, @NotNull Type type,
@NotNull StackValue receiver,
@NotNull ExpressionCodegen codegen,
@Nullable ResolvedCall resolvedCall
@NotNull PropertyDescriptor descriptor, @Nullable Type backingFieldOwner, @Nullable CallableMethod getter,
@Nullable CallableMethod setter, boolean isStaticBackingField, @Nullable String fieldName, @NotNull Type type,
@NotNull StackValue receiver, @NotNull ExpressionCodegen codegen, @Nullable ResolvedCall resolvedCall,
boolean skipLateinitAssertion
) {
super(type, isStatic(isStaticBackingField, getter), isStatic(isStaticBackingField, setter), receiver, true);
this.backingFieldOwner = backingFieldOwner;
@@ -1179,6 +1209,7 @@ public abstract class StackValue {
this.fieldName = fieldName;
this.codegen = codegen;
this.resolvedCall = resolvedCall;
this.skipLateinitAssertion = skipLateinitAssertion;
}
@Override
@@ -1190,7 +1221,9 @@ public abstract class StackValue {
v.visitFieldInsn(isStaticPut ? GETSTATIC : GETFIELD,
backingFieldOwner.getInternalName(), fieldName, this.type.getDescriptor());
genNotNullAssertionForLateInitIfNeeded(v);
if (!skipLateinitAssertion) {
genNotNullAssertionForLateInitIfNeeded(v);
}
coerceTo(type, v);
}
else {
@@ -1260,12 +1293,7 @@ public abstract class StackValue {
private void genNotNullAssertionForLateInitIfNeeded(@NotNull InstructionAdapter v) {
if (!descriptor.isLateInit()) return;
v.dup();
Label ok = new Label();
v.ifnonnull(ok);
v.visitLdcInsn(descriptor.getName().asString());
v.invokestatic(IntrinsicMethods.INTRINSICS_CLASS_NAME, "throwUninitializedPropertyAccessException", "(Ljava/lang/String;)V", false);
v.mark(ok);
StackValue.genNonNullAssertForLateinit(v, descriptor.getName().asString());
}
@Override
@@ -1329,6 +1357,15 @@ public abstract class StackValue {
}
}
private static void genNonNullAssertForLateinit(@NotNull InstructionAdapter v, @NotNull String name) {
v.dup();
Label ok = new Label();
v.ifnonnull(ok);
v.visitLdcInsn(name);
v.invokestatic(IntrinsicMethods.INTRINSICS_CLASS_NAME, "throwUninitializedPropertyAccessException", "(Ljava/lang/String;)V", false);
v.mark(ok);
}
private static class Expression extends StackValue {
private final KtExpression expression;
private final ExpressionCodegen generator;
@@ -1347,10 +1384,23 @@ public abstract class StackValue {
public static class Shared extends StackValueWithSimpleReceiver {
private final int index;
private final boolean isLateinit;
private final Name name;
public Shared(int index, Type type) {
public Shared(int index, Type type, boolean isLateinit, Name name) {
super(type, false, false, local(index, OBJECT_TYPE), false);
this.index = index;
if (isLateinit && name == null) {
throw new IllegalArgumentException("Lateinit shared local variable should have name: #" + index + " " + type.getDescriptor());
}
this.isLateinit = isLateinit;
this.name = name;
}
public Shared(int index, Type type) {
this(index, type, false, null);
}
public int getIndex() {
@@ -1362,6 +1412,9 @@ public abstract class StackValue {
Type refType = refType(this.type);
Type sharedType = sharedTypeForType(this.type);
v.visitFieldInsn(GETFIELD, sharedType.getInternalName(), "element", refType.getDescriptor());
if (isLateinit) {
StackValue.genNonNullAssertForLateinit(v, name.asString());
}
coerceFrom(refType, v);
coerceTo(type, v);
}
@@ -1399,11 +1452,23 @@ public abstract class StackValue {
public static class FieldForSharedVar extends StackValueWithSimpleReceiver {
final Type owner;
final String name;
final boolean isLateinit;
final Name variableName;
public FieldForSharedVar(Type type, Type owner, String name, StackValue.Field receiver) {
public FieldForSharedVar(
Type type, Type owner, String name, StackValue.Field receiver,
boolean isLateinit, Name variableName
) {
super(type, false, false, receiver, receiver.canHaveSideEffects());
if (isLateinit && variableName == null) {
throw new IllegalArgumentException("variableName should be non-null for captured lateinit variable " + name);
}
this.owner = owner;
this.name = name;
this.isLateinit = isLateinit;
this.variableName = variableName;
}
@Override
@@ -1411,6 +1476,9 @@ public abstract class StackValue {
Type sharedType = sharedTypeForType(this.type);
Type refType = refType(this.type);
v.visitFieldInsn(GETFIELD, sharedType.getInternalName(), "element", refType.getDescriptor());
if (isLateinit) {
StackValue.genNonNullAssertForLateinit(v, variableName.asString());
}
coerceFrom(refType, v);
coerceTo(type, v);
}
@@ -1517,101 +1585,6 @@ public abstract class StackValue {
}
}
public static class CallReceiver extends StackValue {
private final StackValue dispatchReceiver;
private final StackValue extensionReceiver;
public CallReceiver(
@NotNull StackValue dispatchReceiver,
@NotNull StackValue extensionReceiver,
@NotNull Type type
) {
super(type, dispatchReceiver.canHaveSideEffects() || extensionReceiver.canHaveSideEffects());
this.dispatchReceiver = dispatchReceiver;
this.extensionReceiver = extensionReceiver;
}
@Nullable
public static Type calcType(
@NotNull ResolvedCall<?> resolvedCall,
@Nullable ReceiverParameterDescriptor dispatchReceiver,
@Nullable ReceiverParameterDescriptor extensionReceiver,
@NotNull KotlinTypeMapper typeMapper,
@Nullable Callable callableMethod,
@NotNull GenerationState state
) {
if (extensionReceiver != null) {
CallableDescriptor descriptor = resolvedCall.getCandidateDescriptor();
if (descriptor instanceof PropertyDescriptor &&
// hackaround: boxing changes behaviour of T.javaClass intrinsic
state.getIntrinsics().getIntrinsic((PropertyDescriptor) descriptor) != JavaClassProperty.INSTANCE
) {
ReceiverParameterDescriptor receiverCandidate = descriptor.getExtensionReceiverParameter();
assert receiverCandidate != null;
return typeMapper.mapType(receiverCandidate.getType());
}
return callableMethod != null ? callableMethod.getExtensionReceiverType() : typeMapper.mapType(extensionReceiver.getType());
}
else if (dispatchReceiver != null) {
CallableDescriptor descriptor = resolvedCall.getResultingDescriptor();
if (CodegenUtilKt.isJvmStaticInObjectOrClass(descriptor)) {
return Type.VOID_TYPE;
}
if (callableMethod != null) {
return callableMethod.getDispatchReceiverType();
}
// Extract the receiver from the resolved call, workarounding the fact that ResolvedCall#dispatchReceiver doesn't have
// all the needed information, for example there's no way to find out whether or not a smart cast was applied to the receiver.
DeclarationDescriptor container = descriptor.getContainingDeclaration();
if (container instanceof ClassDescriptor) {
return typeMapper.mapClass((ClassDescriptor) container);
}
return typeMapper.mapType(dispatchReceiver);
}
else if (isLocalFunCall(callableMethod)) {
return callableMethod.getGenerateCalleeType();
}
return Type.VOID_TYPE;
}
@Override
public void putSelector(@NotNull Type type, @NotNull InstructionAdapter v) {
StackValue currentExtensionReceiver = extensionReceiver;
boolean hasExtensionReceiver = extensionReceiver != none();
if (extensionReceiver instanceof StackValue.SafeCall) {
currentExtensionReceiver.put(currentExtensionReceiver.type, v);
currentExtensionReceiver = StackValue.onStack(currentExtensionReceiver.type);
}
dispatchReceiver.put(hasExtensionReceiver ? dispatchReceiver.type : type, v);
currentExtensionReceiver
.moveToTopOfStack(hasExtensionReceiver ? type : currentExtensionReceiver.type, v, dispatchReceiver.type.getSize());
}
@Override
public void dup(@NotNull InstructionAdapter v, boolean withReceiver) {
AsmUtil.dup(v, extensionReceiver.type, dispatchReceiver.type);
}
@NotNull
public StackValue getDispatchReceiver() {
return dispatchReceiver;
}
@NotNull
public StackValue getExtensionReceiver() {
return extensionReceiver;
}
}
public abstract static class StackValueWithSimpleReceiver extends StackValue {
public final boolean isStaticPut;

View File

@@ -21,7 +21,7 @@ import org.jetbrains.org.objectweb.asm.commons.InstructionAdapter
class CoercionValue(
val value: StackValue,
val castType: Type
private val castType: Type
) : StackValue(castType, value.canHaveSideEffects()) {
override fun putSelector(type: Type, v: InstructionAdapter) {

View File

@@ -20,7 +20,6 @@ import org.jetbrains.kotlin.descriptors.annotations.Annotated
import org.jetbrains.kotlin.descriptors.annotations.AnnotatedImpl
import org.jetbrains.kotlin.descriptors.annotations.AnnotationDescriptor
import org.jetbrains.kotlin.descriptors.annotations.Annotations
import org.jetbrains.kotlin.name.FqName
interface WrappedAnnotated : Annotated {
val originalAnnotated: Annotated
@@ -34,10 +33,6 @@ class AnnotatedWithOnlyTargetedAnnotations(original: Annotated) : Annotated {
private class UseSiteTargetedAnnotations(private val additionalAnnotations: Annotations) : Annotations {
override fun isEmpty() = true
override fun findAnnotation(fqName: FqName) = null
override fun findExternalAnnotation(fqName: FqName) = null
override fun getUseSiteTargetedAnnotations() = getAdditionalTargetedAnnotations()
override fun getAllAnnotations() = getAdditionalTargetedAnnotations()
@@ -48,4 +43,4 @@ class AnnotatedWithOnlyTargetedAnnotations(original: Annotated) : Annotated {
}
}
class AnnotatedSimple(annotations: Annotations) : AnnotatedImpl(annotations)
class AnnotatedSimple(annotations: Annotations) : AnnotatedImpl(annotations)

View File

@@ -30,16 +30,18 @@ import org.jetbrains.kotlin.codegen.*;
import org.jetbrains.kotlin.codegen.coroutines.CoroutineCodegenUtilKt;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.state.TypeMapperUtilsKt;
import org.jetbrains.kotlin.codegen.when.SwitchCodegenUtil;
import org.jetbrains.kotlin.codegen.when.SwitchCodegenProvider;
import org.jetbrains.kotlin.codegen.when.WhenByEnumsMapping;
import org.jetbrains.kotlin.coroutines.CoroutineUtilKt;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.descriptors.annotations.Annotations;
import org.jetbrains.kotlin.descriptors.impl.AnonymousFunctionDescriptor;
import org.jetbrains.kotlin.descriptors.impl.LocalVariableDescriptor;
import org.jetbrains.kotlin.fileClasses.FileClasses;
import org.jetbrains.kotlin.fileClasses.JvmFileClassesProvider;
import org.jetbrains.kotlin.fileClasses.JvmFileClassUtil;
import org.jetbrains.kotlin.load.java.JvmAbi;
import org.jetbrains.kotlin.load.java.sam.SamConstructorDescriptor;
import org.jetbrains.kotlin.load.kotlin.TypeMappingConfiguration;
import org.jetbrains.kotlin.name.ClassId;
import org.jetbrains.kotlin.name.Name;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.resolve.BindingContext;
@@ -54,7 +56,10 @@ import org.jetbrains.kotlin.resolve.constants.ConstantValue;
import org.jetbrains.kotlin.resolve.constants.EnumValue;
import org.jetbrains.kotlin.resolve.constants.NullValue;
import org.jetbrains.kotlin.resolve.descriptorUtil.DescriptorUtilsKt;
import org.jetbrains.kotlin.resolve.scopes.receivers.ReceiverValue;
import org.jetbrains.kotlin.resolve.scopes.receivers.TransientReceiver;
import org.jetbrains.kotlin.types.KotlinType;
import org.jetbrains.kotlin.types.checker.KotlinTypeChecker;
import org.jetbrains.org.objectweb.asm.Type;
import java.util.*;
@@ -79,18 +84,16 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
private final BindingContext bindingContext;
private final GenerationState.GenerateClassFilter filter;
private final JvmRuntimeTypes runtimeTypes;
private final JvmFileClassesProvider fileClassesProvider;
private final TypeMappingConfiguration<Type> typeMappingConfiguration;
private final boolean shouldInlineConstVals;
private final SwitchCodegenProvider switchCodegenProvider;
public CodegenAnnotatingVisitor(@NotNull GenerationState state) {
this.bindingTrace = state.getBindingTrace();
this.bindingContext = state.getBindingContext();
this.filter = state.getGenerateDeclaredClassFilter();
this.runtimeTypes = state.getJvmRuntimeTypes();
this.fileClassesProvider = state.getFileClassesProvider();
this.typeMappingConfiguration = state.getTypeMapper().getTypeMappingConfiguration();
this.shouldInlineConstVals = state.getShouldInlineConstVals();
this.switchCodegenProvider = new SwitchCodegenProvider(state);
}
@NotNull
@@ -328,17 +331,25 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
if (referencedFunction == null) return;
CallableDescriptor target = referencedFunction.getResultingDescriptor();
ReceiverValue extensionReceiver = referencedFunction.getExtensionReceiver();
ReceiverValue dispatchReceiver = referencedFunction.getDispatchReceiver();
// TransientReceiver corresponds to an unbound reference, other receiver values -- to bound references
KotlinType receiverType =
dispatchReceiver != null && !(dispatchReceiver instanceof TransientReceiver) ? dispatchReceiver.getType() :
extensionReceiver != null && !(extensionReceiver instanceof TransientReceiver) ? extensionReceiver.getType() :
null;
CallableDescriptor callableDescriptor;
Collection<KotlinType> supertypes;
KtExpression receiverExpression = expression.getReceiverExpression();
KotlinType receiverType = receiverExpression != null ? bindingContext.getType(receiverExpression) : null;
if (target instanceof FunctionDescriptor) {
callableDescriptor = bindingContext.get(FUNCTION, expression);
if (callableDescriptor == null) return;
supertypes = runtimeTypes.getSupertypesForFunctionReference((FunctionDescriptor) target, receiverType != null);
supertypes = runtimeTypes.getSupertypesForFunctionReference(
(FunctionDescriptor) target, (AnonymousFunctionDescriptor) callableDescriptor, receiverType != null
);
}
else if (target instanceof PropertyDescriptor) {
callableDescriptor = bindingContext.get(VARIABLE, expression);
@@ -370,33 +381,18 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
@NotNull
private MutableClosure recordClosure(@NotNull ClassDescriptor classDescriptor, @NotNull String name) {
return CodegenBinding.recordClosure(
bindingTrace, classDescriptor, peekFromStack(classStack), Type.getObjectType(name), fileClassesProvider
);
return CodegenBinding.recordClosure(bindingTrace, classDescriptor, peekFromStack(classStack), Type.getObjectType(name));
}
private void recordLocalVariablePropertyMetadata(LocalVariableDescriptor variableDescriptor) {
KotlinType delegateType = JvmCodegenUtil.getPropertyDelegateType(variableDescriptor, bindingContext);
if (delegateType == null) return;
LocalVariableDescriptor delegateVariableDescriptor = new LocalVariableDescriptor(
variableDescriptor.getContainingDeclaration(),
Annotations.Companion.getEMPTY(),
variableDescriptor.getName(),
delegateType,
false,
false,
SourceElement.NO_SOURCE
);
bindingTrace.record(LOCAL_VARIABLE_DELEGATE, variableDescriptor, delegateVariableDescriptor);
LocalVariableDescriptor metadataVariableDescriptor = new LocalVariableDescriptor(
variableDescriptor.getContainingDeclaration(),
Annotations.Companion.getEMPTY(),
Name.identifier(variableDescriptor.getName().asString() + "$metadata"),
ReflectionTypes.Companion.createKPropertyStarType(DescriptorUtilsKt.getModule(variableDescriptor)),
false,
false,
SourceElement.NO_SOURCE
);
bindingTrace.record(LOCAL_VARIABLE_PROPERTY_METADATA, variableDescriptor, metadataVariableDescriptor);
@@ -428,12 +424,44 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
runtimeTypes.getSupertypeForPropertyReference(variableDescriptor, variableDescriptor.isVar(), /* bound = */ false);
ClassDescriptor classDescriptor = recordClassForCallable(delegate, variableDescriptor, Collections.singleton(supertype), name);
recordClosure(classDescriptor, name);
Type containerType = getMetadataOwner(property);
List<VariableDescriptorWithAccessors> descriptors = bindingTrace.get(DELEGATED_PROPERTIES, containerType);
if (descriptors == null) {
descriptors = new ArrayList<>(1);
bindingTrace.record(DELEGATED_PROPERTIES, containerType, descriptors);
}
descriptors.add(variableDescriptor);
bindingTrace.record(DELEGATED_PROPERTY_METADATA_OWNER, variableDescriptor, containerType);
}
super.visitProperty(property);
nameStack.pop();
}
@NotNull
private Type getMetadataOwner(@NotNull KtProperty property) {
for (int i = classStack.size() - 1; i >= 0; i--) {
ClassDescriptor descriptor = classStack.get(i);
// The first "real" containing class (not a synthetic class for lambda) is the owner of the delegated property metadata
if (!(descriptor instanceof SyntheticClassDescriptorForLambda)) {
ClassId classId = DescriptorUtilsKt.getClassId(descriptor);
if (classId == null) {
return CodegenBinding.getAsmType(bindingContext, descriptor);
}
return AsmUtil.asmTypeByClassId(
DescriptorUtils.isInterface(descriptor)
? classId.createNestedClassId(Name.identifier(JvmAbi.DEFAULT_IMPLS_CLASS_NAME))
: classId
);
}
}
return Type.getObjectType(JvmFileClassUtil.getFileClassInternalName(property.getContainingKtFile()));
}
@Override
public void visitNamedFunction(@NotNull KtNamedFunction function) {
FunctionDescriptor functionDescriptor = (FunctionDescriptor) bindingContext.get(DECLARATION_TO_DESCRIPTOR, function);
@@ -517,7 +545,7 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
else if (containingDeclaration instanceof PackageFragmentDescriptor) {
KtFile containingFile = DescriptorToSourceUtils.getContainingFile(descriptor);
assert containingFile != null : "File not found for " + descriptor;
return FileClasses.getFileClassInternalName(fileClassesProvider, containingFile) + '$' + name;
return JvmFileClassUtil.getFileClassInternalName(containingFile) + '$' + name;
}
return null;
@@ -545,6 +573,9 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
if (valueArguments == null) return;
for (ValueParameterDescriptor valueParameter : original.getValueParameters()) {
ValueParameterDescriptor adaptedParameter = descriptor.getValueParameters().get(valueParameter.getIndex());
if (KotlinTypeChecker.DEFAULT.equalTypes(adaptedParameter.getType(), valueParameter.getType())) continue;
SamType samType = SamType.create(TypeMapperUtilsKt.removeExternalProjections(valueParameter.getType()));
if (samType == null) continue;
@@ -664,7 +695,7 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
WhenByEnumsMapping mapping = new WhenByEnumsMapping(classDescriptor, currentClassName, fieldNumber);
for (ConstantValue<?> constant : SwitchCodegenUtil.getAllConstants(expression, bindingContext, shouldInlineConstVals)) {
for (ConstantValue<?> constant : switchCodegenProvider.getAllConstants(expression)) {
if (constant instanceof NullValue) continue;
assert constant instanceof EnumValue : "expression in when should be EnumValue";
@@ -678,10 +709,8 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
private boolean isWhenWithEnums(@NotNull KtWhenExpression expression) {
return WhenChecker.isWhenByEnum(expression, bindingContext) &&
SwitchCodegenUtil.checkAllItemsAreConstantsSatisfying(
switchCodegenProvider.checkAllItemsAreConstantsSatisfying(
expression,
bindingContext,
shouldInlineConstVals,
constant -> constant instanceof EnumValue || constant instanceof NullValue
);
}
@@ -696,7 +725,7 @@ class CodegenAnnotatingVisitor extends KtVisitorVoid {
}
}
return FileClasses.getFacadeClassInternalName(fileClassesProvider, file);
return JvmFileClassUtil.getFacadeClassInternalName(file);
}
private static <T> T peekFromStack(@NotNull Stack<T> stack) {

View File

@@ -24,7 +24,6 @@ import org.jetbrains.kotlin.codegen.SamType;
import org.jetbrains.kotlin.codegen.state.GenerationState;
import org.jetbrains.kotlin.codegen.when.WhenByEnumsMapping;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.fileClasses.JvmFileClassesProvider;
import org.jetbrains.kotlin.name.FqName;
import org.jetbrains.kotlin.psi.*;
import org.jetbrains.kotlin.psi.psiUtil.PsiUtilsKt;
@@ -49,7 +48,7 @@ public class CodegenBinding {
public static final WritableSlice<ClassDescriptor, Boolean> ENUM_ENTRY_CLASS_NEED_SUBCLASS = Slices.createSimpleSetSlice();
public static final WritableSlice<ClassDescriptor, Collection<ClassDescriptor>> INNER_CLASSES = Slices.createSimpleSlice();
private static final WritableSlice<ClassDescriptor, Collection<ClassDescriptor>> INNER_CLASSES = Slices.createSimpleSlice();
public static final WritableSlice<KtExpression, SamType> SAM_VALUE = Slices.createSimpleSlice();
@@ -60,18 +59,19 @@ public class CodegenBinding {
public static final WritableSlice<String, List<WhenByEnumsMapping>> MAPPINGS_FOR_WHENS_BY_ENUM_IN_CLASS_FILE =
Slices.createSimpleSlice();
public static final WritableSlice<VariableDescriptor, VariableDescriptor> LOCAL_VARIABLE_DELEGATE =
Slices.createSimpleSlice();
public static final WritableSlice<VariableDescriptor, VariableDescriptor> LOCAL_VARIABLE_PROPERTY_METADATA =
Slices.createSimpleSlice();
public static final WritableSlice<FunctionDescriptor, FunctionDescriptor> SUSPEND_FUNCTION_TO_JVM_VIEW =
Slices.createSimpleSlice();
public static final WritableSlice<ValueParameterDescriptor, ValueParameterDescriptor> PARAMETER_SYNONYM =
Slices.createSimpleSlice();
public static final WritableSlice<Type, List<VariableDescriptorWithAccessors>> DELEGATED_PROPERTIES =
Slices.createSimpleSlice();
public static final WritableSlice<VariableDescriptorWithAccessors, Type> DELEGATED_PROPERTY_METADATA_OWNER =
Slices.createSimpleSlice();
public static final WritableSlice<VariableDescriptor, VariableDescriptor> LOCAL_VARIABLE_PROPERTY_METADATA =
Slices.createSimpleSlice();
static {
BasicWritableSlice.initSliceDebugNames(CodegenBinding.class);
}
@@ -150,8 +150,7 @@ public class CodegenBinding {
@NotNull BindingTrace trace,
@NotNull ClassDescriptor classDescriptor,
@Nullable ClassDescriptor enclosing,
@NotNull Type asmType,
@NotNull JvmFileClassesProvider fileClassesManager
@NotNull Type asmType
) {
KtElement element = (KtElement) DescriptorToSourceUtils.descriptorToDeclaration(classDescriptor);
assert element != null : "No source element for " + classDescriptor;
@@ -227,32 +226,6 @@ public class CodegenBinding {
return type;
}
@NotNull
public static Collection<ClassDescriptor> getAllInnerClasses(
@NotNull BindingContext bindingContext, @NotNull ClassDescriptor outermostClass
) {
Collection<ClassDescriptor> innerClasses = bindingContext.get(INNER_CLASSES, outermostClass);
if (innerClasses == null || innerClasses.isEmpty()) return Collections.emptySet();
Set<ClassDescriptor> allInnerClasses = new HashSet<>();
Deque<ClassDescriptor> stack = new ArrayDeque<>(innerClasses);
do {
ClassDescriptor currentClass = stack.pop();
if (allInnerClasses.add(currentClass)) {
Collection<ClassDescriptor> nextClasses = bindingContext.get(INNER_CLASSES, currentClass);
if (nextClasses != null) {
for (ClassDescriptor nextClass : nextClasses) {
stack.push(nextClass);
}
}
}
}
while (!stack.isEmpty());
return allInnerClasses;
}
@NotNull
public static VariableDescriptor getDelegatedLocalVariableMetadata(
@NotNull VariableDescriptor variableDescriptor,

Some files were not shown because too many files have changed in this diff Show More