Add more utilities

This commit is contained in:
Him188 2019-11-20 19:15:11 +08:00
parent 7ea0495f62
commit f0702a7ea9
2 changed files with 36 additions and 9 deletions

View File

@ -15,7 +15,7 @@ fun ByteReadPacket.readIoBuffer(
n: Int = remaining.toInt()//not that safe but adequate
): IoBuffer = IoBuffer.Pool.borrow().also { this.readFully(it, n) }
fun ByteReadPacket.readIoBuffer(n: Number) = this.readIoBuffer(n.toInt())
fun ByteReadPacket.readIoBuffer(n: Short) = this.readIoBuffer(n.toInt())
fun Input.readIP(): String = buildString(4 + 3) {
repeat(4) {
@ -25,6 +25,8 @@ fun Input.readIP(): String = buildString(4 + 3) {
}
}
fun Input.readPacket(length: Int): ByteReadPacket = this.readBytes(length).toReadPacket()
fun Input.readUVarIntLVString(): String = String(this.readUVarIntByteArray())
fun Input.readUShortLVString(): String = String(this.readUShortLVByteArray())
@ -62,7 +64,14 @@ fun Input.readTLVMap(expectingEOF: Boolean = false, tagSize: Int = 1): MutableMa
", duplicating value=${this.readUShortLVByteArray()}" +
", remaining=" + if (expectingEOF) this.readBytes().toUHexString() else "[Not expecting EOF]"
}
map[type.toUInt()] = this.readUShortLVByteArray()
try {
map[type.toUInt()] = this.readUShortLVByteArray()
} catch (e: RuntimeException) { // BufferUnderflowException
if (expectingEOF) {
return map
}
throw e
}
}
return map
}
@ -103,11 +112,24 @@ fun Input.readFlatTUVarIntMap(expectingEOF: Boolean = false, tagSize: Int = 1):
return map
}
fun Map<UInt, ByteArray>.printTLVMap(name: String) =
debugPrintln("TLVMap $name= " + this.mapValues { (_, value) -> value.toUHexString() }.mapKeys { it.key.toInt().toUShort().toUHexString() })
fun Map<UInt, ByteArray>.printTLVMap(name: String = "", keyLength: Int = 1) =
debugPrintln("TLVMap $name= " + this.mapValues { (_, value) -> value.toUHexString() }.mapKeys {
when (keyLength) {
1 -> it.key.toInt().toUByte().toUHexString()
2 -> it.key.toInt().toUShort().toUHexString()
4 -> it.key.toInt().toUInt().toUHexString()
else -> illegalArgument("Expecting 1, 2 or 4 for keyLength")
}
})
@Suppress("NOTHING_TO_INLINE")
internal inline fun unsupported(): Nothing = error("Unsupported")
@Suppress("NOTHING_TO_INLINE")
internal inline fun illegalArgument(message: String? = null): Nothing = error(message ?: "Illegal argument passed")
@JvmName("printTLVStringMap")
fun Map<UInt, String>.printTLVMap(name: String) =
fun Map<UInt, String>.printTLVMap(name: String = "") =
debugPrintln("TLVMap $name= " + this.mapKeys { it.key.toInt().toUShort().toUHexString() })
fun Input.readString(length: Int): String = String(this.readBytes(length))

View File

@ -4,6 +4,8 @@ package net.mamoe.mirai.utils.io
import kotlinx.io.core.*
import kotlinx.io.pool.useInstance
import kotlinx.serialization.SerializationStrategy
import kotlinx.serialization.protobuf.ProtoBuf
import net.mamoe.mirai.contact.GroupId
import net.mamoe.mirai.contact.GroupInternalId
import net.mamoe.mirai.network.protocol.tim.TIMProtocol
@ -57,6 +59,9 @@ fun BytePacketBuilder.writeHex(uHex: String) {
}
}
fun <T> BytePacketBuilder.writeProto(serializer: SerializationStrategy<T>, obj: T) = writeFully(ProtoBuf.dump(serializer, obj))
fun BytePacketBuilder.writeTLV(tag: UByte, values: UByteArray) {
writeUByte(tag)
writeUVarInt(values.size.toUInt())
@ -104,17 +109,17 @@ fun BytePacketBuilder.writeTByteArray(tag: UByte, value: UByteArray) {
/**
* 会使用 [ByteArrayPool] 缓存
*/
fun BytePacketBuilder.encryptAndWrite(key: ByteArray, encoder: BytePacketBuilder.() -> Unit) =
inline fun BytePacketBuilder.encryptAndWrite(key: ByteArray, encoder: BytePacketBuilder.() -> Unit) =
BytePacketBuilder().apply(encoder).build().encryptBy(key) { decrypted -> writeFully(decrypted) }
fun BytePacketBuilder.encryptAndWrite(key: IoBuffer, encoder: BytePacketBuilder.() -> Unit) = ByteArrayPool.useInstance {
inline fun BytePacketBuilder.encryptAndWrite(key: IoBuffer, encoder: BytePacketBuilder.() -> Unit) = ByteArrayPool.useInstance {
key.readFully(it, 0, key.readRemaining)
encryptAndWrite(it, encoder)
}
fun BytePacketBuilder.encryptAndWrite(key: DecrypterByteArray, encoder: BytePacketBuilder.() -> Unit) = encryptAndWrite(key.value, encoder)
inline fun BytePacketBuilder.encryptAndWrite(key: DecrypterByteArray, encoder: BytePacketBuilder.() -> Unit) = encryptAndWrite(key.value, encoder)
fun BytePacketBuilder.encryptAndWrite(keyHex: String, encoder: BytePacketBuilder.() -> Unit) = encryptAndWrite(keyHex.hexToBytes(), encoder)
inline fun BytePacketBuilder.encryptAndWrite(keyHex: String, encoder: BytePacketBuilder.() -> Unit) = encryptAndWrite(keyHex.hexToBytes(), encoder)
fun BytePacketBuilder.writeTLV0006(qq: UInt, password: String, loginTime: Int, loginIP: String, privateKey: PrivateKey) {
val firstMD5 = md5(password)