blob: f98f6a529c9f2bd3c6664cd83e17000c3d8003fb [file] [log] [blame]
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +03001/*
Aurimas Liutikasc8879d62021-05-12 21:56:16 +00002 * Copyright 2016-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +03003 */
4
Victor Turanskyfe2fedc2020-08-27 15:47:50 +03005apply plugin: 'org.jetbrains.kotlin.multiplatform'
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +03006apply from: rootProject.file("gradle/compile-jvm-multiplatform.gradle")
7apply from: rootProject.file("gradle/compile-common.gradle")
8apply from: rootProject.file("gradle/compile-js-multiplatform.gradle")
Aurimas Liutikasc8879d62021-05-12 21:56:16 +00009apply from: rootProject.file("gradle/compile-native-multiplatform.gradle")
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +030010apply from: rootProject.file('gradle/publish-npm-js.gradle')
11
Roman Elizarov738f5a22020-10-12 19:03:46 +030012/* ==========================================================================
13 Configure source sets structure for kotlinx-coroutines-core:
14
15 TARGETS SOURCE SETS
16 ------- ----------------------------------------------
17
18 js -----------------------------------------------------+
19 |
20 V
21 jvm -------------------------------> concurrent ---> common
22 ^
23 ios \ |
24 macos | ---> nativeDarwin ---> native --+
25 tvos | ^
26 watchos / |
27 |
28 linux \ ---> nativeOther -------+
29 mingw /
30
31 ========================================================================== */
32
33project.ext.sourceSetSuffixes = ["Main", "Test"]
34
35void defineSourceSet(newName, dependsOn, includedInPred) {
36 for (suffix in project.ext.sourceSetSuffixes) {
37 def newSS = kotlin.sourceSets.maybeCreate(newName + suffix)
38 for (dep in dependsOn) {
39 newSS.dependsOn(kotlin.sourceSets[dep + suffix])
40 }
41 for (curSS in kotlin.sourceSets) {
42 def curName = curSS.name
43 if (curName.endsWith(suffix)) {
44 def prefix = curName.substring(0, curName.length() - suffix.length())
45 if (includedInPred(prefix)) curSS.dependsOn(newSS)
46 }
47 }
48 }
49}
50
51static boolean isNativeDarwin(String name) { return ["ios", "macos", "tvos", "watchos"].any { name.startsWith(it) } }
52static boolean isNativeOther(String name) { return ["linux", "mingw"].any { name.startsWith(it) } }
53
54defineSourceSet("concurrent", ["common"]) { it in ["jvm", "native"] }
Aurimas Liutikasc8879d62021-05-12 21:56:16 +000055defineSourceSet("nativeDarwin", ["native"]) { isNativeDarwin(it) }
56defineSourceSet("nativeOther", ["native"]) { isNativeOther(it) }
Roman Elizarov738f5a22020-10-12 19:03:46 +030057
58/* ========================================================================== */
59
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +030060/*
61 * All platform plugins and configuration magic happens here instead of build.gradle
62 * because JMV-only projects depend on core, thus core should always be initialized before configuration.
63 */
64kotlin {
65 configure(sourceSets) {
66 def srcDir = name.endsWith('Main') ? 'src' : 'test'
67 def platform = name[0..-5]
Roman Elizarov738f5a22020-10-12 19:03:46 +030068 kotlin.srcDirs = ["$platform/$srcDir"]
Vsevolod Tolstopyatov8273a752019-03-15 19:24:41 +030069 if (name == "jvmMain") {
70 resources.srcDirs = ["$platform/resources"]
71 } else if (name == "jvmTest") {
72 resources.srcDirs = ["$platform/test-resources"]
73 }
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +030074 languageSettings {
75 progressiveMode = true
76 experimentalAnnotations.each { useExperimentalAnnotation(it) }
77 }
78 }
79
80 configure(targets) {
Roman Elizarov738f5a22020-10-12 19:03:46 +030081 // Configure additional binaries and test runs -- one for each OS
82 if (["macos", "linux", "mingw"].any { name.startsWith(it) }) {
83 binaries {
84 // Test for memory leaks using a special entry point that does not exit but returns from main
85 binaries.getTest("DEBUG").freeCompilerArgs += ["-e", "kotlinx.coroutines.mainNoExit"]
86 // Configure a separate test where code runs in background
87 test("background", [org.jetbrains.kotlin.gradle.plugin.mpp.NativeBuildType.DEBUG]) {
88 freeCompilerArgs += ["-e", "kotlinx.coroutines.mainBackground"]
89 }
90 }
91 testRuns {
92 background { setExecutionSourceFrom(binaries.backgroundDebugTest) }
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +030093 }
94 }
95 }
96}
97
Roman Elizarovd2f4b2b2019-09-02 17:22:39 +030098configurations {
99 configureKotlinJvmPlatform(kotlinCompilerPluginClasspath)
100}
101
Roman Elizarov90a9faf2020-02-12 16:38:26 +0300102// Update module name for metadata artifact to avoid conflicts
103// see https://github.com/Kotlin/kotlinx.coroutines/issues/1797
104compileKotlinMetadata {
105 kotlinOptions {
106 freeCompilerArgs += ["-module-name", "kotlinx-coroutines-core-common"]
107 }
108}
109
Roman Elizarov738f5a22020-10-12 19:03:46 +0300110// :KLUDGE: Idea.active: This is needed to workaround resolve problems after importing this project to IDEA
111def configureNativeSourceSetPreset(name, preset) {
112 def hostMainCompilation = project.kotlin.targetFromPreset(preset).compilations.main
113 // Look for platform libraries in "implementation" for default source set
114 def implementationConfiguration = configurations[hostMainCompilation.defaultSourceSet.implementationMetadataConfigurationName]
115 // Now find the libraries: Finds platform libs & stdlib, but platform declarations are still not resolved due to IDE bugs
116 def hostNativePlatformLibs = files(
117 provider {
118 implementationConfiguration.findAll {
119 it.path.endsWith(".klib") || it.absolutePath.contains("klib${File.separator}platform") || it.absolutePath.contains("stdlib")
120 }
121 }
122 )
123 // Add all those dependencies
124 for (suffix in sourceSetSuffixes) {
125 configure(kotlin.sourceSets[name + suffix]) {
126 dependencies.add(implementationMetadataConfigurationName, hostNativePlatformLibs)
127 }
128 }
129}
130
131// :KLUDGE: Idea.active: Configure platform libraries for native source sets when working in IDEA
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000132if (Idea.active) {
Roman Elizarov738f5a22020-10-12 19:03:46 +0300133 def manager = project.ext.hostManager
134 def linuxPreset = kotlin.presets.linuxX64
135 def macosPreset = kotlin.presets.macosX64
136 // linux should be always available (cross-compilation capable) -- use it as default
137 assert manager.isEnabled(linuxPreset.konanTarget)
138 // use macOS libs for nativeDarwin if available
139 def macosAvailable = manager.isEnabled(macosPreset.konanTarget)
140 // configure source sets
141 configureNativeSourceSetPreset("native", linuxPreset)
142 configureNativeSourceSetPreset("nativeOther", linuxPreset)
143 configureNativeSourceSetPreset("nativeDarwin", macosAvailable ? macosPreset : linuxPreset)
144}
145
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300146kotlin.sourceSets {
Roman Elizarov0bf172b2020-06-02 10:20:57 +0300147 jvmMain.dependencies {
Vsevolod Tolstopyatov559023d2020-05-14 16:24:18 +0300148 compileOnly "com.google.android:annotations:4.1.1.4"
149 }
150
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300151 jvmTest.dependencies {
Roman Elizarov738f5a22020-10-12 19:03:46 +0300152 api "org.jetbrains.kotlinx:lincheck:$lincheck_version"
Roman Elizarov660c2d72020-02-14 13:18:37 +0300153 api "org.jetbrains.kotlinx:kotlinx-knit-test:$knit_version"
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300154 api "com.esotericsoftware:kryo:4.0.0"
Roman Elizarov738f5a22020-10-12 19:03:46 +0300155 implementation project(":android-unit-tests")
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300156 }
157}
158
159task checkJdk16() {
160 // only fail w/o JDK_16 when actually trying to compile, not during project setup phase
161 doLast {
162 if (!System.env.JDK_16) {
163 throw new GradleException("JDK_16 environment variable is not defined. " +
164 "Can't build against JDK 1.6 runtime and run JDK 1.6 compatibility tests. " +
165 "Please ensure JDK 1.6 is installed and that JDK_16 points to it.")
166 }
167 }
168}
169
170tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile) {
171 kotlinOptions.jdkHome = System.env.JDK_16
172 // only fail when actually trying to compile, not during project setup phase
173 dependsOn(checkJdk16)
174}
175
176jvmTest {
177 minHeapSize = '1g'
178 maxHeapSize = '1g'
179 enableAssertions = true
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000180 systemProperty 'java.security.manager', 'kotlinx.coroutines.TestSecurityManager'
Vsevolod Tolstopyatova64e4da2019-10-10 13:03:06 +0300181 // 'stress' is required to be able to run all subpackage tests like ":jvmTests --tests "*channels*" -Pstress=true"
Roman Elizarov738f5a22020-10-12 19:03:46 +0300182 if (!Idea.active && rootProject.properties['stress'] == null) {
Vsevolod Tolstopyatova64e4da2019-10-10 13:03:06 +0300183 exclude '**/*StressTest.*'
184 }
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000185 systemProperty 'kotlinx.coroutines.scheduler.keep.alive.sec', '100000' // any unpark problem hangs test
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300186}
187
Vsevolod Tolstopyatov70a74872020-04-24 14:59:28 +0300188jvmJar {
189 manifest {
190 attributes "Premain-Class": "kotlinx.coroutines.debug.AgentPremain"
191 attributes "Can-Retransform-Classes": "true"
192 }
193}
194
Roman Elizarov216828a2019-09-28 00:42:51 +0300195task jvmStressTest(type: Test, dependsOn: compileTestKotlinJvm) {
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300196 classpath = files { jvmTest.classpath }
197 testClassesDirs = files { jvmTest.testClassesDirs }
Roman Elizarovfd27d552019-09-25 23:49:34 +0300198 minHeapSize = '1g'
199 maxHeapSize = '1g'
200 include '**/*StressTest.*'
Roman Elizarov0b16abf2019-09-03 11:07:11 +0300201 enableAssertions = true
202 testLogging.showStandardStreams = true
Roman Elizarovfd27d552019-09-25 23:49:34 +0300203 systemProperty 'kotlinx.coroutines.scheduler.keep.alive.sec', '100000' // any unpark problem hangs test
Nikita Kovalac42be92020-04-23 20:01:05 +0300204 systemProperty 'kotlinx.coroutines.semaphore.segmentSize', '2'
205 systemProperty 'kotlinx.coroutines.semaphore.maxSpinCycles', '10'
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300206}
207
208task jdk16Test(type: Test, dependsOn: [compileTestKotlinJvm, checkJdk16]) {
209 classpath = files { jvmTest.classpath }
210 testClassesDirs = files { jvmTest.testClassesDirs }
211 executable = "$System.env.JDK_16/bin/java"
Roman Elizarov7672c522019-08-28 12:04:59 +0300212 exclude '**/*LFStressTest.*' // lock-freedom tests use LockFreedomTestEnvironment which needs JDK8
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000213 exclude '**/*LCStressTest.*' // lin-check tests use LinChecker which needs JDK8
Roman Elizarov7672c522019-08-28 12:04:59 +0300214 exclude '**/exceptions/**' // exceptions tests check suppressed exception which needs JDK8
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300215 exclude '**/ExceptionsGuideTest.*'
Roman Elizarove60bcbd2020-07-17 12:29:59 +0300216 exclude '**/RunInterruptibleStressTest.*' // fails on JDK 1.6 due to JDK bug
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300217}
218
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000219// Run these tests only during nightly stress test
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300220jdk16Test.onlyIf { project.properties['stressTest'] != null }
221
Aurimas Liutikasc8879d62021-05-12 21:56:16 +0000222// Always run those tests
223task moreTest(dependsOn: [jvmStressTest, jdk16Test])
224build.dependsOn moreTest
Vsevolod Tolstopyatove50a0fa2019-01-28 11:34:24 +0300225
226task testsJar(type: Jar, dependsOn: jvmTestClasses) {
227 classifier = 'tests'
228 from compileTestKotlinJvm.destinationDir
229}
230
231artifacts {
232 archives testsJar
233}