Skip to content

Commit c4f390a

Browse files
committed
Merge branch 'develop'
2 parents 195f8cd + 3e387b8 commit c4f390a

File tree

142 files changed

+6144
-3044
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

142 files changed

+6144
-3044
lines changed

README.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
[![Download](https://api.bintray.com/packages/kotlin/kotlinx/kotlinx.coroutines/images/download.svg?version=0.19.3) ](https://bintray.com/kotlin/kotlinx/kotlinx.coroutines/0.19.3)
66

77
Library support for Kotlin coroutines.
8-
This is a companion version for Kotlin 1.1.4 release (this is the minimal required Kotlin runtime version).
8+
This is a companion version for Kotlin 1.2.0 release.
99

1010
## Modules
1111

@@ -60,7 +60,7 @@ And make sure that you use the latest Kotlin version:
6060

6161
```xml
6262
<properties>
63-
<kotlin.version>1.1.51</kotlin.version>
63+
<kotlin.version>1.2.0</kotlin.version>
6464
</properties>
6565
```
6666

@@ -76,7 +76,7 @@ And make sure that you use the latest Kotlin version:
7676

7777
```groovy
7878
buildscript {
79-
ext.kotlin_version = '1.1.51'
79+
ext.kotlin_version = '1.2.0'
8080
}
8181
```
8282

benchmarks/build.gradle

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,14 @@ dependencies {
1010
jmh 'com.typesafe.akka:akka-actor:2.0.2'
1111
jmh project(':kotlinx-coroutines-core')
1212
jmh project(':kotlinx-coroutines-core').sourceSets.test.output
13+
jmh project(':kotlinx-coroutines-io')
1314
}
1415

1516
jmh.jmhVersion = '1.19'
1617

1718
jmhJar.archiveName = 'benchmarks.jar'
19+
20+
//jmh {
21+
// include = ['.*Channel.*Benchmark']
22+
// exclude = ['.*Guice.*', '.*PingPong.*']
23+
//}
Lines changed: 325 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,325 @@
1+
package benchmarks
2+
3+
import kotlinx.coroutines.experimental.*
4+
import kotlinx.coroutines.experimental.io.*
5+
import org.openjdk.jmh.annotations.*
6+
import java.io.*
7+
import java.util.concurrent.*
8+
import kotlin.coroutines.experimental.*
9+
import kotlin.coroutines.experimental.intrinsics.*
10+
11+
12+
/*
13+
# Run complete. Total time: 00:01:52
14+
15+
Benchmark Mode Cnt Score Error Units
16+
ChannelCopyBenchmark.cioChannelCopy avgt 5 828,087 ± 11,568 ns/op
17+
ChannelCopyBenchmark.cioCopyToInLaunch avgt 5 2016,028 ± 15,846 ns/op
18+
ChannelCopyBenchmark.cioJoinToBeforeWrite avgt 5 1413,410 ± 20,460 ns/op
19+
ChannelCopyBenchmark.cioJoinToClosed avgt 5 892,200 ± 113,468 ns/op
20+
ChannelCopyBenchmark.cioJustWrite avgt 5 478,995 ± 106,499 ns/op
21+
ChannelCopyBenchmark.cioJustWriteUnintercepted avgt 5 175,821 ± 21,018 ns/op
22+
ChannelCopyBenchmark.cioReadAndWrite avgt 5 513,968 ± 5,142 ns/op
23+
ChannelCopyBenchmark.cioReadAndWriteUnintercepted avgt 5 250,731 ± 9,800 ns/op
24+
ChannelCopyBenchmark.javaPipeConnectFirst avgt 5 239,269 ± 11,470 ns/op
25+
ChannelCopyBenchmark.justRunBlocking avgt 5 228,704 ± 4,349 ns/op
26+
ChannelCopyBenchmark.runBlockingAndLaunch avgt 5 833,390 ± 14,968 ns/op
27+
*/
28+
29+
@Warmup(iterations = 5)
30+
@Measurement(iterations = 5)
31+
@BenchmarkMode(Mode.AverageTime)
32+
@OutputTimeUnit(TimeUnit.NANOSECONDS)
33+
@State(Scope.Benchmark)
34+
@Fork(1)
35+
open class ChannelCopyBenchmark {
36+
private val HelloWorld = "Hello, World!".toByteArray()
37+
private val ABC = "ABC".repeat(100).toByteArray()
38+
private val buffer = ByteArray(4096)
39+
private val ioe = IOException()
40+
41+
@Benchmark
42+
fun javaPipeConnectFirst() {
43+
val pipeIn = PipedInputStream()
44+
val pipeOut = PipedOutputStream()
45+
46+
pipeIn.connect(pipeOut)
47+
48+
pipeOut.write(ABC)
49+
var read = 0
50+
while (read < ABC.size) {
51+
val rc = pipeIn.read(buffer)
52+
if (rc == -1) break
53+
read += rc
54+
}
55+
56+
pipeOut.close()
57+
pipeIn.close()
58+
}
59+
60+
@Benchmark
61+
fun cioChannelCopy() = runBlocking {
62+
val pIn = ByteChannel(true)
63+
val pOut = ByteChannel(true)
64+
65+
pOut.writeFully(ABC)
66+
pOut.close()
67+
68+
pOut.copyAndClose(pIn)
69+
70+
var read = 0
71+
while (read < ABC.size) {
72+
val rc = pIn.readAvailable(buffer)
73+
if (rc == -1) break
74+
read += rc
75+
}
76+
77+
read
78+
}
79+
80+
@Benchmark
81+
fun cioChannelCopyHW() = runBlocking {
82+
val pIn = ByteChannel(true)
83+
val pOut = ByteChannel(true)
84+
85+
pOut.writeFully(HelloWorld)
86+
pOut.close()
87+
88+
pOut.copyAndClose(pIn)
89+
90+
var read = 0
91+
while (read < HelloWorld.size) {
92+
val rc = pIn.readAvailable(buffer)
93+
if (rc == -1) break
94+
read += rc
95+
}
96+
97+
read
98+
}
99+
100+
@Benchmark
101+
fun cioJoinToClosed() = runBlocking {
102+
val pIn = ByteChannel(true)
103+
val pOut = ByteChannel(true)
104+
105+
pOut.writeFully(ABC)
106+
pOut.close()
107+
108+
pOut.joinTo(pIn, true)
109+
110+
var read = 0
111+
while (read < ABC.size) {
112+
val rc = pIn.readAvailable(buffer)
113+
if (rc == -1) break
114+
read += rc
115+
}
116+
117+
read
118+
}
119+
120+
@Benchmark
121+
fun cioJoinToClosedHW() = runBlocking {
122+
val pIn = ByteChannel(true)
123+
val pOut = ByteChannel(true)
124+
125+
pOut.writeFully(HelloWorld)
126+
pOut.close()
127+
128+
pOut.joinTo(pIn, true)
129+
130+
var read = 0
131+
while (read < HelloWorld.size) {
132+
val rc = pIn.readAvailable(buffer)
133+
if (rc == -1) break
134+
read += rc
135+
}
136+
137+
read
138+
}
139+
140+
141+
@Benchmark
142+
fun cioCopyFromEmpty() = runCoroutineFast {
143+
val from = ByteChannel(true)
144+
val to = ByteChannel(true)
145+
146+
from.close()
147+
from.copyAndClose(to)
148+
}
149+
150+
@Benchmark
151+
fun cioJoinFromEmpty() = runCoroutineFast {
152+
val from = ByteChannel(true)
153+
val to = ByteChannel(true)
154+
155+
from.close()
156+
from.joinTo(to, true)
157+
}
158+
159+
@Benchmark
160+
fun cioJoinFromEmptyNonClosed() = runCoroutineFast(allowSuspend = true) {
161+
val from = ByteChannel(true)
162+
val to = ByteChannel(true)
163+
164+
from.joinTo(to, true) // should setup joining and suspend
165+
}
166+
167+
@Benchmark
168+
fun cioJoinToBeforeWrite() = runBlocking {
169+
val pIn = ByteChannel(true)
170+
val pOut = ByteChannel(true)
171+
172+
launch(coroutineContext) {
173+
pOut.joinTo(pIn, true)
174+
}
175+
176+
yield()
177+
178+
pOut.writeFully(ABC)
179+
pOut.close()
180+
181+
var read = 0
182+
while (read < ABC.size) {
183+
val rc = pIn.readAvailable(buffer)
184+
if (rc == -1) break
185+
read += rc
186+
}
187+
188+
read
189+
}
190+
191+
@Benchmark
192+
fun cioJoinToHWBeforeWrite() = runBlocking {
193+
val pIn = ByteChannel(true)
194+
val pOut = ByteChannel(true)
195+
196+
launch(coroutineContext) {
197+
pOut.joinTo(pIn, true)
198+
}
199+
200+
yield()
201+
202+
pOut.writeFully(HelloWorld)
203+
pOut.close()
204+
205+
var read = 0
206+
while (read < HelloWorld.size) {
207+
val rc = pIn.readAvailable(buffer)
208+
if (rc == -1) break
209+
read += rc
210+
}
211+
212+
read
213+
}
214+
215+
@Benchmark
216+
fun cioCopyToInLaunch() = runBlocking {
217+
val pIn = ByteChannel(true)
218+
val pOut = ByteChannel(true)
219+
220+
launch(coroutineContext) {
221+
pOut.copyTo(pIn)
222+
pIn.close()
223+
}
224+
225+
yield()
226+
227+
pOut.writeFully(ABC)
228+
pOut.close()
229+
230+
var read = 0
231+
while (read < ABC.size) {
232+
val rc = pIn.readAvailable(buffer)
233+
if (rc == -1) break
234+
read += rc
235+
}
236+
237+
read
238+
}
239+
240+
@Benchmark
241+
fun cioCopyToHWInLaunch() = runBlocking {
242+
val pIn = ByteChannel(true)
243+
val pOut = ByteChannel(true)
244+
245+
launch(coroutineContext) {
246+
pOut.copyTo(pIn)
247+
pIn.close()
248+
}
249+
250+
yield()
251+
252+
pOut.writeFully(HelloWorld)
253+
pOut.close()
254+
255+
var read = 0
256+
while (read < HelloWorld.size) {
257+
val rc = pIn.readAvailable(buffer)
258+
if (rc == -1) break
259+
read += rc
260+
}
261+
262+
read
263+
}
264+
265+
@Benchmark
266+
fun cioJustWrite() = runBlocking {
267+
val c = ByteChannel()
268+
c.writeFully(ABC)
269+
c.close(ioe)
270+
}
271+
272+
@Benchmark
273+
fun cioJustWriteUnintercepted() = runCoroutineFast {
274+
val c = ByteChannel()
275+
c.writeFully(ABC)
276+
c.close(ioe)
277+
}
278+
279+
@Benchmark
280+
fun cioReadAndWrite() = runBlocking {
281+
val c = ByteChannel(true)
282+
c.writeFully(ABC)
283+
c.readAvailable(buffer)
284+
c.close()
285+
}
286+
287+
@Benchmark
288+
fun cioReadAndWriteUnintercepted() = runCoroutineFast {
289+
val c = ByteChannel(true)
290+
c.writeFully(ABC)
291+
c.readAvailable(buffer)
292+
c.close()
293+
}
294+
295+
@Benchmark
296+
fun justRunBlocking() = runBlocking {
297+
}
298+
299+
@Benchmark
300+
fun runBlockingAndLaunch() = runBlocking {
301+
launch(coroutineContext) {
302+
yield()
303+
}
304+
305+
yield()
306+
}
307+
308+
private fun runCoroutineFast(allowSuspend: Boolean = false, block: suspend () -> Unit) {
309+
if (block.startCoroutineUninterceptedOrReturn(EmptyContinuation) === COROUTINE_SUSPENDED) {
310+
if (!allowSuspend)
311+
throw IllegalStateException("Unexpected suspend")
312+
}
313+
}
314+
315+
object EmptyContinuation : Continuation<Unit> {
316+
override val context: CoroutineContext
317+
get() = EmptyCoroutineContext
318+
319+
override fun resume(value: Unit) {
320+
}
321+
322+
override fun resumeWithException(exception: Throwable) {
323+
}
324+
}
325+
}

build.gradle

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ buildscript {
1313
}
1414
repositories {
1515
jcenter()
16+
maven { url "http://kotlin.bintray.com/kotlinx" }
1617
}
1718
dependencies {
1819
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
@@ -70,7 +71,6 @@ configure(subprojects.findAll { !sourceless.contains(it.name) }) {
7071

7172
repositories {
7273
jcenter()
73-
maven { url "http://jcenter.bintray.com" }
7474
maven { url "http://kotlin.bintray.com/kotlinx" }
7575
maven { url "https://dl.bintray.com/devexperts/Maven/" }
7676
}

0 commit comments

Comments
 (0)