Compare commits

..

4 Commits

Author SHA1 Message Date
e5bbd9730c bump version to 1.3.0
All checks were successful
/ publish (push) Successful in 2m35s
2025-11-10 14:27:26 +01:00
e7e43f9cca refactor HashFunction 2025-11-10 14:27:09 +01:00
e3619a2df1 implement keccak 2025-11-09 20:53:01 +01:00
88d673922a refactor package structure 2025-11-09 20:19:10 +01:00
16 changed files with 271 additions and 116 deletions

View File

@@ -1,5 +1,5 @@
group = "com.infendro" group = "com.infendro"
version = "1.2.2" version = "1.3.0"
repositories { repositories {
maven("https://git.infendro.com/api/packages/Infendro/maven") maven("https://git.infendro.com/api/packages/Infendro/maven")
@@ -23,6 +23,10 @@ kotlin {
implementation(libs.bytearray) implementation(libs.bytearray)
} }
} }
compilerOptions {
freeCompilerArgs.add("-opt-in=kotlin.ExperimentalUnsignedTypes")
}
} }
publishing { publishing {

View File

@@ -1,6 +1,6 @@
[versions] [versions]
kotlin = "2.1.20" kotlin = "2.1.20"
bytearray = "1.1.1" bytearray = "1.2.0"
[plugins] [plugins]
multiplatform = { id = "org.jetbrains.kotlin.multiplatform", version.ref = "kotlin" } multiplatform = { id = "org.jetbrains.kotlin.multiplatform", version.ref = "kotlin" }

View File

@@ -1,11 +1,13 @@
package com.infendro.hash package com.infendro.hash
sealed class HashFunction { abstract class HashFunction {
abstract val bytes: Int abstract val bytes: Int
@Suppress("UNUSED")
val bits: Int val bits: Int
get() = bytes * 8 get() = bytes * 8
abstract fun hash( abstract fun hash(
value: ByteArray, value: UByteArray,
): ByteArray ): UByteArray
} }

View File

@@ -0,0 +1,107 @@
package com.infendro.hash.keccak
import com.infendro.bytearray.ByteOrder.LITTLE_ENDIAN
import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toULongArray
import com.infendro.hash.HashFunction
import kotlin.math.min
@Suppress("UNUSED")
open class Keccak internal constructor(
override val bytes: Int,
private val rate: Int,
private val domain: UByte,
) : HashFunction() {
private val rc = ulongArrayOf(
0x0000000000000001UL, 0x0000000000008082UL, 0x800000000000808aUL, 0x8000000080008000UL,
0x000000000000808bUL, 0x0000000080000001UL, 0x8000000080008081UL, 0x8000000000008009UL,
0x000000000000008aUL, 0x0000000000000088UL, 0x0000000080008009UL, 0x000000008000000aUL,
0x000000008000808bUL, 0x800000000000008bUL, 0x8000000000008089UL, 0x8000000000008003UL,
0x8000000000008002UL, 0x8000000000000080UL, 0x000000000000800aUL, 0x800000008000000aUL,
0x8000000080008081UL, 0x8000000000008080UL, 0x0000000080000001UL, 0x8000000080008008UL
)
private val rotation = arrayOf(
intArrayOf(0, 36, 3, 41, 18),
intArrayOf(1, 44, 10, 45, 2),
intArrayOf(62, 6, 43, 15, 61),
intArrayOf(28, 55, 25, 21, 56),
intArrayOf(27, 20, 39, 8, 14),
)
override fun hash(
value: UByteArray,
): UByteArray {
val paddedValue = buildList {
addAll(value)
add(domain)
while ((size % rate) != (rate - 1)) {
add(0x00U)
}
add(0x80U)
}
val state = ULongArray(25)
// absorb
val chunks = paddedValue
.chunked(rate) { it.toUByteArray() }
for (chunk in chunks) {
val numbers = chunk.toULongArray(LITTLE_ENDIAN)
for ((i, number) in numbers.withIndex()) {
state[i] = state[i] xor number
}
permute(state)
}
// squeeze
return buildList {
var i = 0
while (size < bytes) {
if (i == rate / 8) {
permute(state)
i = 0
}
addAll(
state[i++].toUByteArray(LITTLE_ENDIAN)
.take(min(bytes - size, 8))
)
}
}.toUByteArray()
}
private fun permute(
a: ULongArray,
) {
val b = ULongArray(25)
val c = ULongArray(5)
val d = ULongArray(5)
repeat(24) { round ->
// θ
for (x in 0..4) {
c[x] = a[x] xor a[x + 5] xor a[x + 10] xor a[x + 15] xor a[x + 20]
}
for (x in 0..4) {
d[x] = c[(x + 4) % 5] xor c[(x + 1) % 5].rotateLeft(1)
}
for (x in 0..4) for (y in 0..4) {
a[x + 5 * y] = a[x + 5 * y] xor d[x]
}
// ρ and π
for (x in 0..4) for (y in 0..4) {
b[y + 5 * ((2 * x + 3 * y) % 5)] = a[x + 5 * y].rotateLeft(rotation[x][y])
}
// χ
for (x in 0..4) for (y in 0..4) {
a[x + 5 * y] = b[x + 5 * y] xor ((b[((x + 1) % 5) + 5 * y].inv()) and b[((x + 2) % 5) + 5 * y])
}
// ι
a[0] = a[0] xor rc[round]
}
}
}

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.sha3
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
object `SHA3-224` : Keccak(28, 144, 0x06U)

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.sha3
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
object `SHA3-256` : Keccak(32, 136, 0x06U)

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.sha3
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
object `SHA3-384` : Keccak(48, 104, 0x06U)

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.sha3
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
object `SHA3-512` : Keccak(64, 72, 0x06U)

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.shake
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
class SHAKE128(bytes: Int) : Keccak(bytes, 168, 0x1FU)

View File

@@ -0,0 +1,6 @@
package com.infendro.hash.keccak.shake
import com.infendro.hash.keccak.Keccak
@Suppress("UNUSED")
class SHAKE256(bytes: Int) : Keccak(bytes, 136, 0x1FU)

View File

@@ -1,15 +1,16 @@
package com.infendro.hash package com.infendro.hash.md
import com.infendro.bytearray.ByteOrder.LITTLE_ENDIAN import com.infendro.bytearray.ByteOrder.LITTLE_ENDIAN
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toUIntArray import com.infendro.bytearray.toUIntArray
import com.infendro.hash.HashFunction
@Suppress("UNUSED")
object MD5 : HashFunction() { object MD5 : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 16 get() = 16
private val s = arrayOf( private val s = intArrayOf(
7, 12, 17, 22, 7, 12, 17, 22,
7, 12, 17, 22, 7, 12, 17, 22,
7, 12, 17, 22, 7, 12, 17, 22,
@@ -28,7 +29,7 @@ object MD5 : HashFunction() {
6, 10, 15, 21, 6, 10, 15, 21,
) )
private val k = arrayOf( private val k = uintArrayOf(
0xd76aa478U, 0xe8c7b756U, 0x242070dbU, 0xc1bdceeeU, 0xd76aa478U, 0xe8c7b756U, 0x242070dbU, 0xc1bdceeeU,
0xf57c0fafU, 0x4787c62aU, 0xa8304613U, 0xfd469501U, 0xf57c0fafU, 0x4787c62aU, 0xa8304613U, 0xfd469501U,
0x698098d8U, 0x8b44f7afU, 0xffff5bb1U, 0x895cd7beU, 0x698098d8U, 0x8b44f7afU, 0xffff5bb1U, 0x895cd7beU,
@@ -48,8 +49,8 @@ object MD5 : HashFunction() {
) )
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var a0 = 0x67452301U var a0 = 0x67452301U
var b0 = 0xefcdab89U var b0 = 0xefcdab89U
var c0 = 0x98badcfeU var c0 = 0x98badcfeU
@@ -58,15 +59,15 @@ object MD5 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 64 != 56) { while (size % 64 != 56) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray(LITTLE_ENDIAN)) addAll(ml.toUByteArray(LITTLE_ENDIAN))
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(64) .chunked(64) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toUIntArray(LITTLE_ENDIAN)) addAll(chunk.toUIntArray(LITTLE_ENDIAN))
@@ -102,11 +103,11 @@ object MD5 : HashFunction() {
d0 += d d0 += d
} }
return byteArrayOf( return ubyteArrayOf(
*a0.toByteArray(LITTLE_ENDIAN), *a0.toUByteArray(LITTLE_ENDIAN),
*b0.toByteArray(LITTLE_ENDIAN), *b0.toUByteArray(LITTLE_ENDIAN),
*c0.toByteArray(LITTLE_ENDIAN), *c0.toUByteArray(LITTLE_ENDIAN),
*d0.toByteArray(LITTLE_ENDIAN), *d0.toUByteArray(LITTLE_ENDIAN),
) )
} }
} }

View File

@@ -1,16 +1,17 @@
package com.infendro.hash package com.infendro.hash.sha1
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toUIntArray import com.infendro.bytearray.toUIntArray
import com.infendro.hash.HashFunction
@Suppress("UNUSED")
object SHA1 : HashFunction() { object SHA1 : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 20 get() = 20
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var h0 = 0x67452301U var h0 = 0x67452301U
var h1 = 0xefcdaB89U var h1 = 0xefcdaB89U
var h2 = 0x98badcfeU var h2 = 0x98badcfeU
@@ -20,15 +21,15 @@ object SHA1 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 64 != 56) { while (size % 64 != 56) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray()) addAll(ml.toUByteArray())
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(64) .chunked(64) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toUIntArray()) addAll(chunk.toUIntArray())
@@ -72,12 +73,12 @@ object SHA1 : HashFunction() {
h4 += e h4 += e
} }
return byteArrayOf( return ubyteArrayOf(
*h0.toByteArray(), *h0.toUByteArray(),
*h1.toByteArray(), *h1.toUByteArray(),
*h2.toByteArray(), *h2.toUByteArray(),
*h3.toByteArray(), *h3.toUByteArray(),
*h4.toByteArray(), *h4.toUByteArray(),
) )
} }
} }

View File

@@ -1,14 +1,15 @@
package com.infendro.hash package com.infendro.hash.sha2
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toUIntArray import com.infendro.bytearray.toUIntArray
import com.infendro.hash.HashFunction
object SHA224 : HashFunction() { @Suppress("UNUSED")
object `SHA-224` : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 28 get() = 28
private val k = arrayOf( private val k = uintArrayOf(
0x428a2f98U, 0x71374491U, 0xb5c0fbcfU, 0xe9b5dba5U, 0x3956c25bU, 0x59f111f1U, 0x923f82a4U, 0xab1c5ed5U, 0x428a2f98U, 0x71374491U, 0xb5c0fbcfU, 0xe9b5dba5U, 0x3956c25bU, 0x59f111f1U, 0x923f82a4U, 0xab1c5ed5U,
0xd807aa98U, 0x12835b01U, 0x243185beU, 0x550c7dc3U, 0x72be5d74U, 0x80deb1feU, 0x9bdc06a7U, 0xc19bf174U, 0xd807aa98U, 0x12835b01U, 0x243185beU, 0x550c7dc3U, 0x72be5d74U, 0x80deb1feU, 0x9bdc06a7U, 0xc19bf174U,
0xe49b69c1U, 0xefbe4786U, 0x0fc19dc6U, 0x240ca1ccU, 0x2de92c6fU, 0x4a7484aaU, 0x5cb0a9dcU, 0x76f988daU, 0xe49b69c1U, 0xefbe4786U, 0x0fc19dc6U, 0x240ca1ccU, 0x2de92c6fU, 0x4a7484aaU, 0x5cb0a9dcU, 0x76f988daU,
@@ -20,8 +21,8 @@ object SHA224 : HashFunction() {
) )
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var h0 = 0xc1059ed8U var h0 = 0xc1059ed8U
var h1 = 0x367cd507U var h1 = 0x367cd507U
var h2 = 0x3070dd17U var h2 = 0x3070dd17U
@@ -34,15 +35,15 @@ object SHA224 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 64 != 56) { while (size % 64 != 56) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray()) addAll(ml.toUByteArray())
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(64) .chunked(64) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toUIntArray()) addAll(chunk.toUIntArray())
@@ -63,10 +64,10 @@ object SHA224 : HashFunction() {
var h = h7 var h = h7
for (i in 0..<64) { for (i in 0..<64) {
val s0 = a.rotateRight(2) xor a.rotateRight(13) xor a.rotateRight(22)
val s1 = e.rotateRight(6) xor e.rotateRight(11) xor e.rotateRight(25) val s1 = e.rotateRight(6) xor e.rotateRight(11) xor e.rotateRight(25)
val ch = (e and f) xor (e.inv() and g) val ch = (e and f) xor (e.inv() and g)
val temp1 = h + s1 + ch + k[i] + w[i] val temp1 = h + s1 + ch + k[i] + w[i]
val s0 = a.rotateRight(2) xor a.rotateRight(13) xor a.rotateRight(22)
val maj = (a and b) xor (a and c) xor (b and c) val maj = (a and b) xor (a and c) xor (b and c)
val temp2 = s0 + maj val temp2 = s0 + maj
@@ -90,14 +91,14 @@ object SHA224 : HashFunction() {
h7 += h h7 += h
} }
return byteArrayOf( return ubyteArrayOf(
*h0.toByteArray(), *h0.toUByteArray(),
*h1.toByteArray(), *h1.toUByteArray(),
*h2.toByteArray(), *h2.toUByteArray(),
*h3.toByteArray(), *h3.toUByteArray(),
*h4.toByteArray(), *h4.toUByteArray(),
*h5.toByteArray(), *h5.toUByteArray(),
*h6.toByteArray(), *h6.toUByteArray(),
) )
} }
} }

View File

@@ -1,14 +1,15 @@
package com.infendro.hash package com.infendro.hash.sha2
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toUIntArray import com.infendro.bytearray.toUIntArray
import com.infendro.hash.HashFunction
object SHA256 : HashFunction() { @Suppress("UNUSED")
object `SHA-256` : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 32 get() = 32
private val k = arrayOf( private val k = uintArrayOf(
0x428a2f98U, 0x71374491U, 0xb5c0fbcfU, 0xe9b5dba5U, 0x3956c25bU, 0x59f111f1U, 0x923f82a4U, 0xab1c5ed5U, 0x428a2f98U, 0x71374491U, 0xb5c0fbcfU, 0xe9b5dba5U, 0x3956c25bU, 0x59f111f1U, 0x923f82a4U, 0xab1c5ed5U,
0xd807aa98U, 0x12835b01U, 0x243185beU, 0x550c7dc3U, 0x72be5d74U, 0x80deb1feU, 0x9bdc06a7U, 0xc19bf174U, 0xd807aa98U, 0x12835b01U, 0x243185beU, 0x550c7dc3U, 0x72be5d74U, 0x80deb1feU, 0x9bdc06a7U, 0xc19bf174U,
0xe49b69c1U, 0xefbe4786U, 0x0fc19dc6U, 0x240ca1ccU, 0x2de92c6fU, 0x4a7484aaU, 0x5cb0a9dcU, 0x76f988daU, 0xe49b69c1U, 0xefbe4786U, 0x0fc19dc6U, 0x240ca1ccU, 0x2de92c6fU, 0x4a7484aaU, 0x5cb0a9dcU, 0x76f988daU,
@@ -20,8 +21,8 @@ object SHA256 : HashFunction() {
) )
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var h0 = 0x6a09e667U var h0 = 0x6a09e667U
var h1 = 0xbb67ae85U var h1 = 0xbb67ae85U
var h2 = 0x3c6ef372U var h2 = 0x3c6ef372U
@@ -34,15 +35,15 @@ object SHA256 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 64 != 56) { while (size % 64 != 56) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray()) addAll(ml.toUByteArray())
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(64) .chunked(64) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toUIntArray()) addAll(chunk.toUIntArray())
@@ -90,15 +91,15 @@ object SHA256 : HashFunction() {
h7 += h h7 += h
} }
return byteArrayOf( return ubyteArrayOf(
*h0.toByteArray(), *h0.toUByteArray(),
*h1.toByteArray(), *h1.toUByteArray(),
*h2.toByteArray(), *h2.toUByteArray(),
*h3.toByteArray(), *h3.toUByteArray(),
*h4.toByteArray(), *h4.toUByteArray(),
*h5.toByteArray(), *h5.toUByteArray(),
*h6.toByteArray(), *h6.toUByteArray(),
*h7.toByteArray(), *h7.toUByteArray(),
) )
} }
} }

View File

@@ -1,14 +1,15 @@
package com.infendro.hash package com.infendro.hash.sha2
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toULongArray import com.infendro.bytearray.toULongArray
import com.infendro.hash.HashFunction
object SHA384 : HashFunction() { @Suppress("UNUSED")
object `SHA-384` : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 48 get() = 48
private val k = arrayOf( private val k = ulongArrayOf(
0x428a2f98d728ae22UL, 0x7137449123ef65cdUL, 0xb5c0fbcfec4d3b2fUL, 0xe9b5dba58189dbbcUL, 0x3956c25bf348b538UL, 0x428a2f98d728ae22UL, 0x7137449123ef65cdUL, 0xb5c0fbcfec4d3b2fUL, 0xe9b5dba58189dbbcUL, 0x3956c25bf348b538UL,
0x59f111f1b605d019UL, 0x923f82a4af194f9bUL, 0xab1c5ed5da6d8118UL, 0xd807aa98a3030242UL, 0x12835b0145706fbeUL, 0x59f111f1b605d019UL, 0x923f82a4af194f9bUL, 0xab1c5ed5da6d8118UL, 0xd807aa98a3030242UL, 0x12835b0145706fbeUL,
0x243185be4ee4b28cUL, 0x550c7dc3d5ffb4e2UL, 0x72be5d74f27b896fUL, 0x80deb1fe3b1696b1UL, 0x9bdc06a725c71235UL, 0x243185be4ee4b28cUL, 0x550c7dc3d5ffb4e2UL, 0x72be5d74f27b896fUL, 0x80deb1fe3b1696b1UL, 0x9bdc06a725c71235UL,
@@ -28,8 +29,8 @@ object SHA384 : HashFunction() {
) )
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var h0 = 0xcbbb9d5dc1059ed8UL var h0 = 0xcbbb9d5dc1059ed8UL
var h1 = 0x629a292a367cd507UL var h1 = 0x629a292a367cd507UL
var h2 = 0x9159015a3070dd17UL var h2 = 0x9159015a3070dd17UL
@@ -42,15 +43,15 @@ object SHA384 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 128 != 120) { while (size % 128 != 120) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray()) addAll(ml.toUByteArray())
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(128) .chunked(128) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toULongArray()) addAll(chunk.toULongArray())
@@ -98,13 +99,13 @@ object SHA384 : HashFunction() {
h7 += h h7 += h
} }
return byteArrayOf( return ubyteArrayOf(
*h0.toByteArray(), *h0.toUByteArray(),
*h1.toByteArray(), *h1.toUByteArray(),
*h2.toByteArray(), *h2.toUByteArray(),
*h3.toByteArray(), *h3.toUByteArray(),
*h4.toByteArray(), *h4.toUByteArray(),
*h5.toByteArray(), *h5.toUByteArray(),
) )
} }
} }

View File

@@ -1,14 +1,15 @@
package com.infendro.hash package com.infendro.hash.sha2
import com.infendro.bytearray.addAll import com.infendro.bytearray.toUByteArray
import com.infendro.bytearray.toByteArray
import com.infendro.bytearray.toULongArray import com.infendro.bytearray.toULongArray
import com.infendro.hash.HashFunction
object SHA512 : HashFunction() { @Suppress("UNUSED")
object `SHA-512` : HashFunction() {
override val bytes: Int override val bytes: Int
get() = 64 get() = 64
private val k = arrayOf( private val k = ulongArrayOf(
0x428a2f98d728ae22UL, 0x7137449123ef65cdUL, 0xb5c0fbcfec4d3b2fUL, 0xe9b5dba58189dbbcUL, 0x3956c25bf348b538UL, 0x428a2f98d728ae22UL, 0x7137449123ef65cdUL, 0xb5c0fbcfec4d3b2fUL, 0xe9b5dba58189dbbcUL, 0x3956c25bf348b538UL,
0x59f111f1b605d019UL, 0x923f82a4af194f9bUL, 0xab1c5ed5da6d8118UL, 0xd807aa98a3030242UL, 0x12835b0145706fbeUL, 0x59f111f1b605d019UL, 0x923f82a4af194f9bUL, 0xab1c5ed5da6d8118UL, 0xd807aa98a3030242UL, 0x12835b0145706fbeUL,
0x243185be4ee4b28cUL, 0x550c7dc3d5ffb4e2UL, 0x72be5d74f27b896fUL, 0x80deb1fe3b1696b1UL, 0x9bdc06a725c71235UL, 0x243185be4ee4b28cUL, 0x550c7dc3d5ffb4e2UL, 0x72be5d74f27b896fUL, 0x80deb1fe3b1696b1UL, 0x9bdc06a725c71235UL,
@@ -28,8 +29,8 @@ object SHA512 : HashFunction() {
) )
override fun hash( override fun hash(
value: ByteArray, value: UByteArray,
): ByteArray { ): UByteArray {
var h0 = 0x6a09e667f3bcc908UL var h0 = 0x6a09e667f3bcc908UL
var h1 = 0xbb67ae8584caa73bUL var h1 = 0xbb67ae8584caa73bUL
var h2 = 0x3c6ef372fe94f82bUL var h2 = 0x3c6ef372fe94f82bUL
@@ -42,15 +43,15 @@ object SHA512 : HashFunction() {
val paddedValue = buildList { val paddedValue = buildList {
addAll(value) addAll(value)
add(0x80.toByte()) add(0x80U)
while (size % 128 != 120) { while (size % 128 != 120) {
add(0x00.toByte()) add(0x00U)
} }
addAll(ml.toByteArray()) addAll(ml.toUByteArray())
} }
val chunks = paddedValue val chunks = paddedValue
.chunked(128) .chunked(128) { it.toUByteArray() }
for (chunk in chunks) { for (chunk in chunks) {
val w = buildList { val w = buildList {
addAll(chunk.toULongArray()) addAll(chunk.toULongArray())
@@ -98,15 +99,15 @@ object SHA512 : HashFunction() {
h7 += h h7 += h
} }
return byteArrayOf( return ubyteArrayOf(
*h0.toByteArray(), *h0.toUByteArray(),
*h1.toByteArray(), *h1.toUByteArray(),
*h2.toByteArray(), *h2.toUByteArray(),
*h3.toByteArray(), *h3.toUByteArray(),
*h4.toByteArray(), *h4.toUByteArray(),
*h5.toByteArray(), *h5.toUByteArray(),
*h6.toByteArray(), *h6.toUByteArray(),
*h7.toByteArray(), *h7.toUByteArray(),
) )
} }
} }