mirror of
https://github.com/mamoe/mirai.git
synced 2025-03-24 14:30:09 +08:00
Session finished
This commit is contained in:
parent
8606c4c778
commit
4508c66225
@ -21,9 +21,12 @@ import java.util.LinkedList;
|
||||
import java.util.Scanner;
|
||||
|
||||
public class MiraiServer {
|
||||
@Getter
|
||||
private static MiraiServer instance;
|
||||
|
||||
public static MiraiServer getInstance() {
|
||||
return instance;
|
||||
}
|
||||
|
||||
//mirai version
|
||||
private final static String MIRAI_VERSION = "1.0.0";
|
||||
|
||||
@ -35,7 +38,7 @@ public class MiraiServer {
|
||||
private boolean unix;
|
||||
|
||||
@Getter//file path
|
||||
private File parentFolder;
|
||||
public File parentFolder;
|
||||
|
||||
@Getter
|
||||
MiraiEventManager eventManager;
|
||||
|
@ -1,18 +1,24 @@
|
||||
package net.mamoe.mirai.network
|
||||
|
||||
import io.netty.channel.Channel
|
||||
import net.mamoe.mirai.MiraiServer
|
||||
import net.mamoe.mirai.network.packet.client.ClientPacket
|
||||
import net.mamoe.mirai.network.packet.client.login.*
|
||||
import net.mamoe.mirai.network.packet.client.session.ClientHandshake1Packet
|
||||
import net.mamoe.mirai.network.packet.client.session.ClientLoginStatusPacket
|
||||
import net.mamoe.mirai.network.packet.client.session.ClientSKeyRequestPacket
|
||||
import net.mamoe.mirai.network.packet.client.writeHex
|
||||
import net.mamoe.mirai.network.packet.client.writeRandom
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import net.mamoe.mirai.network.packet.server.login.*
|
||||
import net.mamoe.mirai.network.packet.server.security.ServerSessionKeyResponsePacket
|
||||
import net.mamoe.mirai.network.packet.server.security.ServerSessionKeyResponsePacketEncrypted
|
||||
import net.mamoe.mirai.network.packet.server.security.*
|
||||
import net.mamoe.mirai.network.packet.server.touch.ServerTouchResponsePacket
|
||||
import net.mamoe.mirai.network.packet.server.touch.ServerTouchResponsePacketEncrypted
|
||||
import net.mamoe.mirai.task.MiraiTaskManager
|
||||
import net.mamoe.mirai.util.*
|
||||
import net.mamoe.mirai.utils.MiraiLogger
|
||||
import java.io.ByteArrayInputStream
|
||||
import java.io.FileOutputStream
|
||||
import java.net.DatagramPacket
|
||||
import java.net.DatagramSocket
|
||||
import java.net.InetSocketAddress
|
||||
@ -24,6 +30,7 @@ import java.util.*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class RobotNetworkHandler(val number: Int, private val password: String) {
|
||||
|
||||
private var sequence: Int = 0
|
||||
|
||||
private var channel: Channel? = null
|
||||
@ -36,16 +43,23 @@ class RobotNetworkHandler(val number: Int, private val password: String) {
|
||||
|
||||
private lateinit var serverAddress: InetSocketAddress
|
||||
|
||||
private lateinit var token00BA: ByteArray
|
||||
private lateinit var token00BA: ByteArray //这些数据全部是login用的
|
||||
private lateinit var token0825: ByteArray
|
||||
private var loginTime: Int = 0
|
||||
private lateinit var loginIP: String
|
||||
private var tgtgtKey: ByteArray? = null
|
||||
private var tlv0105: ByteArray
|
||||
private lateinit var _0828_rec_decr_key: ByteArray
|
||||
|
||||
|
||||
private lateinit var sessionKey: ByteArray//这两个是登录成功后得到的
|
||||
private lateinit var sKey: String
|
||||
|
||||
/**
|
||||
* Kind of key, similar to sessionKey
|
||||
* Used to access web API(for friends list etc.)
|
||||
*/
|
||||
private var tlv0105: ByteArray
|
||||
private lateinit var cookies: String
|
||||
private var gtk: Int = 0
|
||||
|
||||
init {
|
||||
tlv0105 = lazyEncode {
|
||||
@ -57,11 +71,6 @@ class RobotNetworkHandler(val number: Int, private val password: String) {
|
||||
}
|
||||
}
|
||||
|
||||
private lateinit var sessionKey: ByteArray
|
||||
/**
|
||||
* Kind of key, similar to sessionKey
|
||||
*/
|
||||
private lateinit var _0828_rec_decr_key: ByteArray
|
||||
|
||||
@ExperimentalUnsignedTypes
|
||||
private var md5_32: ByteArray = getRandomKey(32)
|
||||
@ -100,6 +109,12 @@ class RobotNetworkHandler(val number: Int, private val password: String) {
|
||||
sendPacket(ClientLoginVerificationCodePacket(this.number, this.token0825, this.sequence, this.token00BA))
|
||||
}
|
||||
|
||||
with(MiraiServer.getInstance().parentFolder + "verifyCode.png") {
|
||||
ByteArrayInputStream(packet.verifyCode).transferTo(FileOutputStream(this))
|
||||
println("验证码已写入到 " + this.path)
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
is ServerLoginResponseSuccessPacket -> {
|
||||
@ -148,12 +163,30 @@ class RobotNetworkHandler(val number: Int, private val password: String) {
|
||||
is ServerSessionKeyResponsePacket -> {
|
||||
this.sessionKey = packet.sessionKey
|
||||
this.tlv0105 = packet.tlv0105
|
||||
sendPacket(ClientLoginStatusPacket(this.number, sessionKey, ClientLoginStatus.ONLINE))
|
||||
}
|
||||
|
||||
is ServerLoginSuccessPacket -> {
|
||||
sendPacket(ClientSKeyRequestPacket(this.number, this.sessionKey))
|
||||
}
|
||||
|
||||
is ServerSKeyResponsePacket -> {
|
||||
this.sKey = packet.sKey
|
||||
this.cookies = "uin=o" + this.number + ";skey=" + this.sKey + ";"
|
||||
|
||||
MiraiTaskManager.getInstance().repeatingTask({
|
||||
TODO("时钟_refreshSkey")
|
||||
}, 1800000)
|
||||
this.gtk = getGTK(sKey)
|
||||
sendPacket(ClientHandshake1Packet(this.number, this.sessionKey))
|
||||
}
|
||||
|
||||
is ServerLoginResponseVerificationCodePacketEncrypted -> onPacketReceived(packet.decrypt())
|
||||
is ServerLoginResponseResendPacketEncrypted -> onPacketReceived(packet.decrypt(this.tgtgtKey!!))
|
||||
is ServerLoginResponseSuccessPacketEncrypted -> onPacketReceived(packet.decrypt(this.tgtgtKey!!))
|
||||
is ServerSessionKeyResponsePacketEncrypted -> onPacketReceived(packet.decrypt(this._0828_rec_decr_key))
|
||||
is ServerTouchResponsePacketEncrypted -> onPacketReceived(packet.decrypt())
|
||||
is ServerSKeyResponsePacketEncrypted -> onPacketReceived(packet.decrypt(this.sessionKey))
|
||||
|
||||
else -> throw IllegalArgumentException(packet.toString())
|
||||
}
|
||||
@ -328,3 +361,4 @@ private lateinit var ctx: ChannelHandlerContext
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,29 @@
|
||||
package net.mamoe.mirai.network.packet.client.session
|
||||
|
||||
import net.mamoe.mirai.network.Protocol
|
||||
import net.mamoe.mirai.network.packet.PacketId
|
||||
import net.mamoe.mirai.network.packet.client.*
|
||||
import net.mamoe.mirai.util.ClientLoginStatus
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
@ExperimentalUnsignedTypes
|
||||
@PacketId("00 EC")
|
||||
class ClientLoginStatusPacket(
|
||||
private val qq: Int,
|
||||
private val sessionKey: ByteArray,
|
||||
private val loginStatus: ClientLoginStatus
|
||||
|
||||
) : ClientPacket() {
|
||||
override fun encode() {
|
||||
this.writeRandom(2)//part of packet id
|
||||
this.writeQQ(qq)
|
||||
this.writeHex(Protocol._fixVer)
|
||||
this.encryptAndWrite(sessionKey) {
|
||||
it.writeHex("01 00")
|
||||
it.writeByte(loginStatus.id)
|
||||
it.writeHex("00 01 00 01 00 04 00 00 00 00")
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,25 @@
|
||||
package net.mamoe.mirai.network.packet.client.session
|
||||
|
||||
import net.mamoe.mirai.network.Protocol
|
||||
import net.mamoe.mirai.network.packet.PacketId
|
||||
import net.mamoe.mirai.network.packet.client.*
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
@ExperimentalUnsignedTypes
|
||||
@PacketId("00 1D")
|
||||
class ClientSKeyRequestPacket(
|
||||
private val qq: Int,
|
||||
private val sessionKey: ByteArray
|
||||
) : ClientPacket() {
|
||||
override fun encode() {
|
||||
this.writeRandom(2)//part of packet id
|
||||
|
||||
this.writeQQ(qq)
|
||||
this.writeHex(Protocol._fixVer)
|
||||
this.encryptAndWrite(sessionKey) {
|
||||
it.writeHex("33 00 05 00 08 74 2E 71 71 2E 63 6F 6D 00 0A 71 75 6E 2E 71 71 2E 63 6F 6D 00 0C 71 7A 6F 6E 65 2E 71 71 2E 63 6F 6D 00 0C 6A 75 62 61 6F 2E 71 71 2E 63 6F 6D 00 09 6B 65 2E 71 71 2E 63 6F 6D")
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,34 @@
|
||||
package net.mamoe.mirai.network.packet.client.session
|
||||
|
||||
import net.mamoe.mirai.network.Protocol
|
||||
import net.mamoe.mirai.network.packet.PacketId
|
||||
import net.mamoe.mirai.network.packet.client.*
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
@ExperimentalUnsignedTypes
|
||||
@PacketId("00 5C")
|
||||
class ClientHandshake1Packet(
|
||||
val qq: Int,
|
||||
val sessionKey: ByteArray
|
||||
) : ClientPacket() {
|
||||
override fun encode() {
|
||||
this.writeRandom(2)//part of packet id
|
||||
this.writeQQ(qq)
|
||||
this.writeHex(Protocol._fixVer)
|
||||
this.encryptAndWrite(sessionKey) {
|
||||
it.writeByte(0x88)
|
||||
it.writeQQ(qq)
|
||||
it.writeByte(0x00)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class ServerHandshake1ResponsePacket(input: DataInputStream) : ServerPacket(input) {
|
||||
override fun decode() {
|
||||
|
||||
}
|
||||
}
|
@ -2,27 +2,25 @@ package net.mamoe.mirai.network.packet.client.touch
|
||||
|
||||
import net.mamoe.mirai.network.Protocol
|
||||
import net.mamoe.mirai.network.packet.PacketId
|
||||
import net.mamoe.mirai.network.packet.client.ClientPacket
|
||||
import net.mamoe.mirai.network.packet.client.writeHex
|
||||
import net.mamoe.mirai.network.packet.client.writeQQ
|
||||
import net.mamoe.mirai.network.packet.client.writeRandom
|
||||
import net.mamoe.mirai.util.TEACryptor
|
||||
import net.mamoe.mirai.network.packet.client.*
|
||||
import java.io.IOException
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
@ExperimentalUnsignedTypes
|
||||
@PacketId("00 58")//todo check
|
||||
class ClientHeartbeatPacket : ClientPacket() {
|
||||
var qq: Int = 0
|
||||
var sessionKey: ByteArray? = null//登录后获得
|
||||
|
||||
@PacketId("00 58")
|
||||
class ClientHeartbeatPacket(
|
||||
private val qq: Int,
|
||||
private val sessionKey: ByteArray
|
||||
) : ClientPacket() {
|
||||
@Throws(IOException::class)
|
||||
override fun encode() {
|
||||
this.writeRandom(2)
|
||||
this.writeQQ(qq)
|
||||
this.writeHex(Protocol.fixVer)
|
||||
this.write(TEACryptor.encrypt(byteArrayOf(0x00, 0x01, 0x00, 0x01), sessionKey))
|
||||
this.encryptAndWrite(sessionKey) {
|
||||
it.writeHex("00 01 00 01")
|
||||
}
|
||||
}
|
||||
}
|
@ -3,6 +3,9 @@ package net.mamoe.mirai.network.packet.server
|
||||
import net.mamoe.mirai.network.packet.Packet
|
||||
import net.mamoe.mirai.network.packet.client.toHexString
|
||||
import net.mamoe.mirai.network.packet.server.login.*
|
||||
import net.mamoe.mirai.network.packet.server.security.ServerLoginSuccessPacket
|
||||
import net.mamoe.mirai.network.packet.server.security.ServerSKeyResponsePacketEncrypted
|
||||
import net.mamoe.mirai.network.packet.server.security.ServerSessionKeyResponsePacketEncrypted
|
||||
import net.mamoe.mirai.network.packet.server.touch.ServerTouchResponsePacket
|
||||
import net.mamoe.mirai.network.packet.server.touch.ServerTouchResponsePacketEncrypted
|
||||
import net.mamoe.mirai.util.getAllDeclaredFields
|
||||
@ -28,7 +31,9 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
|
||||
|
||||
return when (val idHex = stream.readInt().toHexString(" ")) {
|
||||
"08 25 31 01" -> ServerTouchResponsePacketEncrypted(ServerTouchResponsePacket.Type.TYPE_08_25_31_01, stream)
|
||||
|
||||
"08 25 31 02" -> ServerTouchResponsePacketEncrypted(ServerTouchResponsePacket.Type.TYPE_08_25_31_02, stream)
|
||||
|
||||
"08 36 31 03", "08 36 31 04", "08 36 31 05", "08 36 31 06" -> {
|
||||
when (bytes.size) {
|
||||
271, 207 -> return ServerLoginResponseResendPacketEncrypted(stream, when (idHex) {
|
||||
@ -37,7 +42,7 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
|
||||
println("flag=$idHex"); ServerLoginResponseResendPacket.Flag.OTHER
|
||||
}
|
||||
})
|
||||
871 -> return ServerLoginResponseVerificationCodePacket(stream, bytes.size)
|
||||
871 -> return ServerLoginResponseVerificationCodePacketEncrypted(stream)
|
||||
}
|
||||
|
||||
if (bytes.size > 700) {
|
||||
@ -53,14 +58,23 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
|
||||
359 -> ServerLoginResponseFailedPacket.State.TAKEN_BACK
|
||||
|
||||
//unknown
|
||||
63 -> throw IllegalArgumentException(bytes.size.toString())//可能是已经完成登录, 服务器拒绝第二次登录
|
||||
351 -> throw IllegalArgumentException(bytes.size.toString())
|
||||
63 -> throw IllegalArgumentException(bytes.size.toString() + " (Already logged in)")//可能是已经完成登录, 服务器拒绝第二次登录
|
||||
351 -> throw IllegalArgumentException(bytes.size.toString() + " (Illegal package data)")//包数据有误
|
||||
|
||||
else -> throw IllegalArgumentException(bytes.size.toString())
|
||||
}, stream)
|
||||
}
|
||||
|
||||
else -> throw IllegalArgumentException(idHex)
|
||||
"08 28 04 34" -> ServerSessionKeyResponsePacketEncrypted(stream)
|
||||
|
||||
|
||||
else -> when (idHex.substring(0, 2)) {
|
||||
"00 EC" -> ServerLoginSuccessPacket(stream)
|
||||
"00 1D" -> ServerSKeyResponsePacketEncrypted(stream)
|
||||
// "00 5C" ->
|
||||
|
||||
else -> throw IllegalArgumentException(idHex)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -79,10 +93,6 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
|
||||
}
|
||||
|
||||
|
||||
fun DataInputStream.skipUntil(byte: Byte) {
|
||||
while (readByte() != byte);
|
||||
}
|
||||
|
||||
fun DataInputStream.readUntil(byte: Byte): ByteArray {
|
||||
var buff = byteArrayOf()
|
||||
var b: Byte
|
||||
|
@ -4,7 +4,6 @@ import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import net.mamoe.mirai.network.packet.server.dataInputStream
|
||||
import net.mamoe.mirai.network.packet.server.goto
|
||||
import net.mamoe.mirai.util.TEACryptor
|
||||
import net.mamoe.mirai.util.toUHexString
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
@ -30,8 +29,7 @@ class ServerLoginResponseVerificationCodePacket(input: DataInputStream, val pack
|
||||
|
||||
this.input.skip(1)
|
||||
|
||||
val b = this.input.readByte()
|
||||
println(b.toUHexString())
|
||||
this.unknownBoolean = this.input.readByte().toInt() == 1
|
||||
|
||||
this.token00BA = this.input.goto(packetLength - 60).readNBytes(40)
|
||||
}
|
||||
|
@ -0,0 +1,13 @@
|
||||
package net.mamoe.mirai.network.packet.server.security
|
||||
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerLoginSuccessPacket(input: DataInputStream) : ServerPacket(input) {
|
||||
override fun decode() {
|
||||
|
||||
}
|
||||
}
|
@ -0,0 +1,35 @@
|
||||
package net.mamoe.mirai.network.packet.server.security
|
||||
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import net.mamoe.mirai.network.packet.server.dataInputStream
|
||||
import net.mamoe.mirai.network.packet.server.goto
|
||||
import net.mamoe.mirai.util.TEACryptor
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSKeyResponsePacket(input: DataInputStream) : ServerPacket(input) {
|
||||
lateinit var sKey: String
|
||||
|
||||
override fun decode() {
|
||||
this.sKey = String(this.input.goto(4).readNBytes(10))
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Encrypted using [0828_rec_decr_key], decrypting in RobotNetworkHandler
|
||||
*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSKeyResponsePacketEncrypted(inputStream: DataInputStream) : ServerPacket(inputStream) {
|
||||
override fun decode() {
|
||||
|
||||
}
|
||||
|
||||
fun decrypt(sessionKey: ByteArray): ServerSKeyResponsePacket {
|
||||
this.input goto 14
|
||||
val data = this.input.readAllBytes().let { it.copyOfRange(0, it.size - 1) }
|
||||
return ServerSKeyResponsePacket(TEACryptor.decrypt(data, sessionKey).dataInputStream());
|
||||
}
|
||||
}
|
@ -0,0 +1,71 @@
|
||||
package net.mamoe.mirai.network.packet.server.security
|
||||
|
||||
import net.mamoe.mirai.network.packet.client.writeHex
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import net.mamoe.mirai.network.packet.server.dataInputStream
|
||||
import net.mamoe.mirai.network.packet.server.goto
|
||||
import net.mamoe.mirai.util.TEACryptor
|
||||
import net.mamoe.mirai.util.lazyEncode
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
* Dispose_0828
|
||||
*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSessionKeyResponsePacket(inputStream: DataInputStream, val dataLength: Int) : ServerPacket(inputStream) {
|
||||
lateinit var sessionKey: ByteArray
|
||||
lateinit var tlv0105: ByteArray
|
||||
|
||||
@ExperimentalUnsignedTypes
|
||||
override fun decode() {
|
||||
when (dataLength) {
|
||||
407 -> {
|
||||
input goto 25
|
||||
sessionKey = input.readNBytes(16)
|
||||
}
|
||||
|
||||
439 -> {
|
||||
input.goto(63)
|
||||
sessionKey = input.readNBytes(16)
|
||||
}
|
||||
|
||||
512,
|
||||
527 -> {
|
||||
input.goto(63)
|
||||
sessionKey = input.readNBytes(16)
|
||||
tlv0105 = lazyEncode {
|
||||
it.writeHex("01 05 00 88 00 01 01 02 00 40 02 01 03 3C 01 03 00 00")
|
||||
input.goto(dataLength - 122)
|
||||
it.write(input.readNBytes(56))
|
||||
it.writeHex("00 40 02 02 03 3C 01 03 00 00")
|
||||
input.goto(dataLength - 55)
|
||||
it.write(input.readNBytes(56))
|
||||
} //todo 这个 tlv0105似乎可以保存起来然后下次登录时使用.
|
||||
}
|
||||
|
||||
else -> throw IllegalArgumentException(dataLength.toString())
|
||||
}
|
||||
|
||||
|
||||
//tlv0105 = "01 05 00 88 00 01 01 02 00 40 02 01 03 3C 01 03 00 00" + 取文本中间(data, 取文本长度(data) - 367, 167) + “00 40 02 02 03 3C 01 03 00 00 ” + 取文本中间 (data, 取文本长度 (data) - 166, 167)
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Encrypted using [0828_rec_decr_key], decrypting in RobotNetworkHandler
|
||||
*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSessionKeyResponsePacketEncrypted(inputStream: DataInputStream) : ServerPacket(inputStream) {
|
||||
override fun decode() {
|
||||
|
||||
}
|
||||
|
||||
fun decrypt(_0828_rec_decr_key: ByteArray): ServerSessionKeyResponsePacket {
|
||||
this.input goto 14
|
||||
val data = this.input.readAllBytes().let { it.copyOfRange(0, it.size - 1) }
|
||||
return ServerSessionKeyResponsePacket(TEACryptor.decrypt(data, _0828_rec_decr_key).dataInputStream(), data.size);
|
||||
}
|
||||
}
|
@ -1,54 +0,0 @@
|
||||
package net.mamoe.mirai.network.packet.server.security
|
||||
|
||||
import net.mamoe.mirai.network.packet.server.ServerPacket
|
||||
import net.mamoe.mirai.network.packet.server.dataInputStream
|
||||
import net.mamoe.mirai.util.TEACryptor
|
||||
import java.io.DataInputStream
|
||||
|
||||
/**
|
||||
* Dispose_0828
|
||||
*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSessionKeyResponsePacket(inputStream: DataInputStream) : ServerPacket(inputStream) {
|
||||
lateinit var sessionKey: ByteArray
|
||||
lateinit var tlv0105: ByteArray
|
||||
override fun decode() {
|
||||
var data = this.input.readAllBytes();
|
||||
val input = data.dataInputStream()
|
||||
|
||||
sessionKey = when (data.size) {
|
||||
407 -> {
|
||||
input.skip(25)
|
||||
input.readNBytes(16)
|
||||
}
|
||||
|
||||
439, 527 -> {
|
||||
input.skip(63)
|
||||
input.readNBytes(16)
|
||||
}
|
||||
|
||||
else -> throw IllegalStateException()
|
||||
}
|
||||
|
||||
//tlv0105 = "01 05 00 88 00 01 01 02 00 40 02 01 03 3C 01 03 00 00" + 取文本中间(data, 取文本长度(data) - 367, 167) + “00 40 02 02 03 3C 01 03 00 00 ” + 取文本中间 (data, 取文本长度 (data) - 166, 167)
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Encrypted using []0828_rec_decr_key], decrypting in RobotNetworkHandler
|
||||
*
|
||||
* @author Him188moe
|
||||
*/
|
||||
class ServerSessionKeyResponsePacketEncrypted(inputStream: DataInputStream) : ServerPacket(inputStream) {
|
||||
override fun decode() {
|
||||
|
||||
}
|
||||
|
||||
fun decrypt(_0828_rec_decr_key: ByteArray): ServerSessionKeyResponsePacket {//todo test
|
||||
this.input.skip(7)
|
||||
return ServerSessionKeyResponsePacket(TEACryptor.decrypt(this.input.readAllBytes().let { it.copyOfRange(0, it.size - 1) }, _0828_rec_decr_key).dataInputStream());
|
||||
//TeaDecrypt(取文本中间(data, 43, 取文本长度(data) - 45), m_0828_rec_decr_key)
|
||||
}
|
||||
}
|
@ -1,7 +1,6 @@
|
||||
package net.mamoe.mirai.task;
|
||||
|
||||
|
||||
import net.mamoe.mirai.MiraiServer;
|
||||
import net.mamoe.mirai.event.MiraiEventHook;
|
||||
import net.mamoe.mirai.event.events.server.ServerDisableEvent;
|
||||
|
||||
@ -90,26 +89,26 @@ public class MiraiTaskManager {
|
||||
定时任务
|
||||
*/
|
||||
|
||||
public void repeatingTask(Runnable runnable, long interval){
|
||||
this.repeatingTask(runnable,interval, MiraiTaskExceptionHandler.byDefault());
|
||||
public void repeatingTask(Runnable runnable, long intervalMillis) {
|
||||
this.repeatingTask(runnable, intervalMillis, MiraiTaskExceptionHandler.byDefault());
|
||||
}
|
||||
|
||||
public void repeatingTask(Runnable runnable, long interval, MiraiTaskExceptionHandler handler){
|
||||
this.repeatingTask(runnable,interval,a -> true,handler);
|
||||
public void repeatingTask(Runnable runnable, long intervalMillis, MiraiTaskExceptionHandler handler) {
|
||||
this.repeatingTask(runnable, intervalMillis, a -> true, handler);
|
||||
}
|
||||
|
||||
public void repeatingTask(Runnable runnable, long interval, int times){
|
||||
this.repeatingTask(runnable,interval,times, MiraiTaskExceptionHandler.byDefault());
|
||||
public void repeatingTask(Runnable runnable, long intervalMillis, int times) {
|
||||
this.repeatingTask(runnable, intervalMillis, times, MiraiTaskExceptionHandler.byDefault());
|
||||
}
|
||||
|
||||
public void repeatingTask(Runnable runnable, long interval, int times, MiraiTaskExceptionHandler handler){
|
||||
public void repeatingTask(Runnable runnable, long intervalMillis, int times, MiraiTaskExceptionHandler handler) {
|
||||
AtomicInteger integer = new AtomicInteger(times-1);
|
||||
this.repeatingTask(
|
||||
runnable,interval, a -> integer.getAndDecrement() > 0, handler
|
||||
runnable, intervalMillis, a -> integer.getAndDecrement() > 0, handler
|
||||
);
|
||||
}
|
||||
|
||||
public <D extends Runnable> void repeatingTask(D runnable, long interval, Predicate<D> shouldContinue, MiraiTaskExceptionHandler handler){
|
||||
public <D extends Runnable> void repeatingTask(D runnable, long intervalMillis, Predicate<D> shouldContinue, MiraiTaskExceptionHandler handler) {
|
||||
new Thread(() -> {
|
||||
do {
|
||||
this.pool.execute(() -> {
|
||||
@ -120,7 +119,7 @@ public class MiraiTaskManager {
|
||||
}
|
||||
});
|
||||
try {
|
||||
Thread.sleep(interval);
|
||||
Thread.sleep(intervalMillis);
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
@ -128,10 +127,10 @@ public class MiraiTaskManager {
|
||||
}).start();
|
||||
}
|
||||
|
||||
public void deletingTask(Runnable runnable, long interval){
|
||||
public void deletingTask(Runnable runnable, long intervalMillis) {
|
||||
new Thread(() -> {
|
||||
try{
|
||||
Thread.sleep(interval);
|
||||
Thread.sleep(intervalMillis);
|
||||
} catch (InterruptedException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
@ -0,0 +1,15 @@
|
||||
package net.mamoe.mirai.util;
|
||||
|
||||
/**
|
||||
* @author Him188moe
|
||||
*/
|
||||
public enum ClientLoginStatus {
|
||||
ONLINE(0x0A);
|
||||
|
||||
// TODO: 2019/8/31 add more
|
||||
public final int id;//1byte
|
||||
|
||||
ClientLoginStatus(int id) {
|
||||
this.id = id;
|
||||
}
|
||||
}
|
@ -24,11 +24,11 @@ fun ByteArray.decryptionDebugLogging() {
|
||||
}
|
||||
|
||||
fun ServerPacket.logging() {
|
||||
DebugLogger.buff.append(this.toString())
|
||||
DebugLogger.buff.append(this.toString()).append("\n")
|
||||
|
||||
}
|
||||
|
||||
@ExperimentalUnsignedTypes
|
||||
fun ClientPacket.logging() {
|
||||
DebugLogger.buff.append(this.toString())
|
||||
DebugLogger.buff.append(this.toString()).append("\n")
|
||||
}
|
@ -3,6 +3,7 @@ package net.mamoe.mirai.util
|
||||
import net.mamoe.mirai.network.Protocol
|
||||
import java.io.ByteArrayOutputStream
|
||||
import java.io.DataOutputStream
|
||||
import java.io.File
|
||||
import java.lang.reflect.Field
|
||||
import java.util.*
|
||||
import java.util.zip.CRC32
|
||||
@ -79,6 +80,24 @@ fun getRandomKey(length: Int): ByteArray {
|
||||
return bytes.toByteArray()
|
||||
}
|
||||
|
||||
operator fun File.plus(child: String): File = File(this, child)
|
||||
|
||||
private const val GTK_BASE_VALUE: Int = 5381
|
||||
|
||||
fun getGTK(sKey: String): Int {
|
||||
var value = GTK_BASE_VALUE
|
||||
for (c in sKey.toCharArray()) {
|
||||
value += (value shl 5) + c.toInt()
|
||||
}
|
||||
|
||||
value = value and Int.MAX_VALUE
|
||||
return value
|
||||
}
|
||||
|
||||
fun main() {
|
||||
println(getGTK("ABCDEFGEFC"))
|
||||
}
|
||||
|
||||
fun getCrc32(key: ByteArray): Int = CRC32().let { it.update(key); it.value.toInt() }
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user