Skip to content

Commit ad14063

Browse files
authored
Delegate Int|Short|Long.reverseBytes to Java Stdlib (#414)
JVM's JIT compiler can't pattern match bytes reversal, so it's worth explicitly delegating to Java Stdlib functions, that are intrinsics candidates. For long values, the new implementation shows 20% perf improvement for reversal itself. Functions depending on it, like readXXXLe or writeXXXLe also show some moderate performance improvement from the change.
1 parent e856d57 commit ad14063

File tree

5 files changed

+50
-12
lines changed

5 files changed

+50
-12
lines changed

core/common/src/-Util.kt

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2017-2023 JetBrains s.r.o. and respective authors and developers.
2+
* Copyright 2017-2024 JetBrains s.r.o. and respective authors and developers.
33
* Use of this source code is governed by the Apache 2.0 license that can be found in the LICENCE file.
44
*/
55

@@ -52,21 +52,27 @@ internal inline fun checkByteCount(byteCount: Long) {
5252
require(byteCount >= 0) { "byteCount ($byteCount) < 0" }
5353
}
5454

55-
internal fun Short.reverseBytes(): Short {
55+
internal expect fun Short.reverseBytes(): Short
56+
57+
internal inline fun Short.reverseBytesCommon(): Short {
5658
val i = toInt() and 0xffff
5759
val reversed = (i and 0xff00 ushr 8) or
5860
(i and 0x00ff shl 8)
5961
return reversed.toShort()
6062
}
6163

62-
internal fun Int.reverseBytes(): Int {
64+
internal expect fun Int.reverseBytes(): Int
65+
66+
internal inline fun Int.reverseBytesCommon(): Int {
6367
return (this and -0x1000000 ushr 24) or
6468
(this and 0x00ff0000 ushr 8) or
6569
(this and 0x0000ff00 shl 8) or
6670
(this and 0x000000ff shl 24)
6771
}
6872

69-
internal fun Long.reverseBytes(): Long {
73+
internal expect fun Long.reverseBytes(): Long
74+
75+
internal inline fun Long.reverseBytesCommon(): Long {
7076
return (this and -0x100000000000000L ushr 56) or
7177
(this and 0x00ff000000000000L ushr 40) or
7278
(this and 0x0000ff0000000000L ushr 24) or
@@ -79,14 +85,6 @@ internal fun Long.reverseBytes(): Long {
7985

8086
/* ktlint-enable no-multi-spaces indent */
8187

82-
internal inline infix fun Int.leftRotate(bitCount: Int): Int {
83-
return (this shl bitCount) or (this ushr (32 - bitCount))
84-
}
85-
86-
internal inline infix fun Long.rightRotate(bitCount: Int): Long {
87-
return (this ushr bitCount) or (this shl (64 - bitCount))
88-
}
89-
9088
// Syntactic sugar.
9189
internal inline infix fun Byte.shr(other: Int): Int = toInt() shr other
9290

core/js/src/UtilsJs.kt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/*
2+
* Copyright 2010-2024 JetBrains s.r.o. and respective authors and developers.
3+
* Use of this source code is governed by the Apache 2.0 license that can be found in the LICENCE file.
4+
*/
5+
6+
package kotlinx.io
7+
8+
internal actual fun Short.reverseBytes(): Short = reverseBytesCommon()
9+
internal actual fun Int.reverseBytes(): Int = reverseBytesCommon()
10+
internal actual fun Long.reverseBytes(): Long = reverseBytesCommon()

core/jvm/src/-UtilsJvm.kt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/*
2+
* Copyright 2010-2024 JetBrains s.r.o. and respective authors and developers.
3+
* Use of this source code is governed by the Apache 2.0 license that can be found in the LICENCE file.
4+
*/
5+
6+
package kotlinx.io
7+
8+
internal actual fun Short.reverseBytes(): Short = java.lang.Short.reverseBytes(this)
9+
internal actual fun Int.reverseBytes(): Int = java.lang.Integer.reverseBytes(this)
10+
internal actual fun Long.reverseBytes(): Long = java.lang.Long.reverseBytes(this)

core/native/src/UtilsNative.kt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/*
2+
* Copyright 2010-2024 JetBrains s.r.o. and respective authors and developers.
3+
* Use of this source code is governed by the Apache 2.0 license that can be found in the LICENCE file.
4+
*/
5+
6+
package kotlinx.io
7+
8+
internal actual fun Short.reverseBytes(): Short = reverseBytesCommon()
9+
internal actual fun Int.reverseBytes(): Int = reverseBytesCommon()
10+
internal actual fun Long.reverseBytes(): Long = reverseBytesCommon()

core/wasm/src/UtilsWasm.kt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/*
2+
* Copyright 2010-2024 JetBrains s.r.o. and respective authors and developers.
3+
* Use of this source code is governed by the Apache 2.0 license that can be found in the LICENCE file.
4+
*/
5+
6+
package kotlinx.io
7+
8+
internal actual fun Short.reverseBytes(): Short = reverseBytesCommon()
9+
internal actual fun Int.reverseBytes(): Int = reverseBytesCommon()
10+
internal actual fun Long.reverseBytes(): Long = reverseBytesCommon()

0 commit comments

Comments
 (0)