Commit fcaadfdb authored by Him188moe's avatar Him188moe

Updated network

parent ef98f22d
...@@ -2,7 +2,10 @@ package net.mamoe.mirai.network ...@@ -2,7 +2,10 @@ package net.mamoe.mirai.network
import net.mamoe.mirai.network.BotNetworkHandlerImpl.BotSocket import net.mamoe.mirai.network.BotNetworkHandlerImpl.BotSocket
import net.mamoe.mirai.network.BotNetworkHandlerImpl.Login import net.mamoe.mirai.network.BotNetworkHandlerImpl.Login
import net.mamoe.mirai.network.handler.* import net.mamoe.mirai.network.handler.ActionPacketHandler
import net.mamoe.mirai.network.handler.DataPacketSocket
import net.mamoe.mirai.network.handler.MessagePacketHandler
import net.mamoe.mirai.network.handler.PacketHandler
import net.mamoe.mirai.network.packet.ClientPacket import net.mamoe.mirai.network.packet.ClientPacket
import net.mamoe.mirai.network.packet.Packet import net.mamoe.mirai.network.packet.Packet
import net.mamoe.mirai.network.packet.ServerEventPacket import net.mamoe.mirai.network.packet.ServerEventPacket
...@@ -35,13 +38,6 @@ interface BotNetworkHandler : Closeable { ...@@ -35,13 +38,6 @@ interface BotNetworkHandler : Closeable {
*/ */
val socket: DataPacketSocket val socket: DataPacketSocket
/**
* Debug 包处理器. 仅输出包的信息. 调试阶段使用
*
* java 调用方式: `botNetWorkHandler.getDebug()`
*/
var debug: DebugPacketHandler
/** /**
* 消息处理. 如发送好友消息, 接受群消息并触发事件 * 消息处理. 如发送好友消息, 接受群消息并触发事件
* *
......
...@@ -35,7 +35,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -35,7 +35,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
lateinit var login: Login lateinit var login: Login
override lateinit var debug: DebugPacketHandler
override lateinit var message: MessagePacketHandler override lateinit var message: MessagePacketHandler
override lateinit var action: ActionPacketHandler override lateinit var action: ActionPacketHandler
...@@ -75,11 +74,9 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -75,11 +74,9 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
private fun onLoggedIn(sessionKey: ByteArray) { private fun onLoggedIn(sessionKey: ByteArray) {
val session = LoginSession(bot, sessionKey, socket) val session = LoginSession(bot, sessionKey, socket)
debug = DebugPacketHandler(session)
message = MessagePacketHandler(session) message = MessagePacketHandler(session)
action = ActionPacketHandler(session) action = ActionPacketHandler(session)
packetHandlers.add(debug.asNode())
packetHandlers.add(message.asNode()) packetHandlers.add(message.asNode())
packetHandlers.add(action.asNode()) packetHandlers.add(action.asNode())
} }
...@@ -104,8 +101,18 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -104,8 +101,18 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
return return
} }
//For debug
kotlin.run {
if (!packet.javaClass.name.endsWith("Encrypted") && !packet.javaClass.name.endsWith("Raw")) {
bot.notice("Packet received: $packet")
}
if (packet is ServerEventPacket) {
sendPacket(ClientMessageResponsePacket(bot.account.qqNumber, packet.packetId, sessionKey, packet.eventIdentity))
}
}
if (ServerPacketReceivedEvent(bot, packet).broadcast().isCancelled) { if (ServerPacketReceivedEvent(bot, packet).broadcast().isCancelled) {
debug.onPacketReceived(packet)
return return
} }
...@@ -368,6 +375,14 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -368,6 +375,14 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
socket.sendPacket(ClientHeartbeatPacket(bot.account.qqNumber, sessionKey)) socket.sendPacket(ClientHeartbeatPacket(bot.account.qqNumber, sessionKey))
}, 90000, 90000, TimeUnit.MILLISECONDS) }, 90000, 90000, TimeUnit.MILLISECONDS)
this.tlv0105 = packet.tlv0105
socket.loginFuture!!.complete(LoginState.SUCCESS)
login.changeOnlineStatus(ClientLoginStatus.ONLINE)
}
is ServerLoginSuccessPacket -> {
BotLoginSucceedEvent(bot).broadcast() BotLoginSucceedEvent(bot).broadcast()
//登录成功后会收到大量上次的消息, 忽略掉 //登录成功后会收到大量上次的消息, 忽略掉
...@@ -375,9 +390,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -375,9 +390,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
message.ignoreMessage = false message.ignoreMessage = false
}, 3, TimeUnit.SECONDS) }, 3, TimeUnit.SECONDS)
this.tlv0105 = packet.tlv0105
socket.loginFuture!!.complete(LoginState.SUCCESS)
onLoggedIn(sessionKey) onLoggedIn(sessionKey)
} }
...@@ -391,7 +403,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -391,7 +403,6 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
is ServerTouchResponsePacket.Encrypted -> socket.distributePacket(packet.decrypt()) is ServerTouchResponsePacket.Encrypted -> socket.distributePacket(packet.decrypt())
is ServerLoginSuccessPacket,
is ServerHeartbeatResponsePacket, is ServerHeartbeatResponsePacket,
is UnknownServerPacket -> { is UnknownServerPacket -> {
//ignored //ignored
...@@ -402,6 +413,10 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler { ...@@ -402,6 +413,10 @@ internal class BotNetworkHandlerImpl(private val bot: Bot) : BotNetworkHandler {
} }
} }
fun changeOnlineStatus(status: ClientLoginStatus) {
socket.sendPacket(ClientChangeOnlineStatusPacket(bot.account.qqNumber, sessionKey, status))
}
override fun close() { override fun close() {
this.captchaCache = null this.captchaCache = null
......
...@@ -9,9 +9,7 @@ import net.mamoe.mirai.network.packet.action.ServerCanAddFriendResponsePacket ...@@ -9,9 +9,7 @@ import net.mamoe.mirai.network.packet.action.ServerCanAddFriendResponsePacket
import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageFailedPacket import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageFailedPacket
import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageResponsePacket import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageResponsePacket
import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageSuccessPacket import net.mamoe.mirai.network.packet.image.ServerTryUploadGroupImageSuccessPacket
import net.mamoe.mirai.network.packet.login.ClientChangeOnlineStatusPacket
import net.mamoe.mirai.task.MiraiThreadPool import net.mamoe.mirai.task.MiraiThreadPool
import net.mamoe.mirai.utils.ClientLoginStatus
import net.mamoe.mirai.utils.getGTK import net.mamoe.mirai.utils.getGTK
import java.awt.image.BufferedImage import java.awt.image.BufferedImage
import java.io.Closeable import java.io.Closeable
...@@ -96,11 +94,6 @@ class ActionPacketHandler(session: LoginSession) : PacketHandler(session) { ...@@ -96,11 +94,6 @@ class ActionPacketHandler(session: LoginSession) : PacketHandler(session) {
session.socket.sendPacket(ClientSKeyRequestPacket(session.bot.account.qqNumber, session.sessionKey)) session.socket.sendPacket(ClientSKeyRequestPacket(session.bot.account.qqNumber, session.sessionKey))
} }
@ExperimentalUnsignedTypes
fun changeOnlineStatus(status: ClientLoginStatus) {
session.socket.sendPacket(ClientChangeOnlineStatusPacket(session.bot.account.qqNumber, session.sessionKey, status))
}
@ExperimentalUnsignedTypes @ExperimentalUnsignedTypes
fun requestAccountInfo() { fun requestAccountInfo() {
session.socket.sendPacket(ClientAccountInfoRequestPacket(session.bot.account.qqNumber, session.sessionKey)) session.socket.sendPacket(ClientAccountInfoRequestPacket(session.bot.account.qqNumber, session.sessionKey))
......
package net.mamoe.mirai.network.handler
import net.mamoe.mirai.network.LoginSession
import net.mamoe.mirai.network.packet.ClientMessageResponsePacket
import net.mamoe.mirai.network.packet.ServerEventPacket
import net.mamoe.mirai.network.packet.ServerPacket
import net.mamoe.mirai.utils.notice
/**
* Kind of [PacketHandler] that prints all packets received in the format of hex byte array.
*
* @author Him188moe
*/
class DebugPacketHandler(session: LoginSession) : PacketHandler(session) {
@ExperimentalUnsignedTypes
override fun onPacketReceived(packet: ServerPacket) {
if (!packet.javaClass.name.endsWith("Encrypted") && !packet.javaClass.name.endsWith("Raw")) {
session.bot.notice("Packet received: $packet")
}
if (packet is ServerEventPacket) {
session.socket.sendPacket(ClientMessageResponsePacket(session.bot.account.qqNumber, packet.packetId, session.sessionKey, packet.eventIdentity))
}
}
}
\ No newline at end of file
@file:Suppress("EXPERIMENTAL_API_USAGE")
//to simplify code
package net.mamoe.mirai.network.packet package net.mamoe.mirai.network.packet
import net.mamoe.mirai.network.packet.PacketNameFormatter.adjustName import net.mamoe.mirai.network.packet.PacketNameFormatter.adjustName
...@@ -46,7 +50,6 @@ abstract class ServerPacket(val input: DataInputStream) : Packet { ...@@ -46,7 +50,6 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
companion object { companion object {
@ExperimentalUnsignedTypes
fun ofByteArray(bytes: ByteArray): ServerPacket { fun ofByteArray(bytes: ByteArray): ServerPacket {
val stream = bytes.dataInputStream() val stream = bytes.dataInputStream()
...@@ -119,9 +122,8 @@ abstract class ServerPacket(val input: DataInputStream) : Packet { ...@@ -119,9 +122,8 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
} }
@ExperimentalUnsignedTypes
override fun toString(): String { override fun toString(): String {
return adjustName(this.javaClass.simpleName + "(${this.getFixedId()})") + this.getAllDeclaredFields().filterNot { it.name == "idHex" || it.name == "encoded" }.joinToString(", ", "{", "}") { return adjustName(this.javaClass.simpleName + "(${this.getFixedId()})") + this.getAllDeclaredFields().filterNot { it.name == "idHex" || it.name == "idByteArray" || it.name == "encoded" }.joinToString(", ", "{", "}") {
it.trySetAccessible(); it.name + "=" + it.get(this).let { value -> it.trySetAccessible(); it.name + "=" + it.get(this).let { value ->
when (value) { when (value) {
is ByteArray -> value.toUHexString() is ByteArray -> value.toUHexString()
...@@ -146,26 +148,26 @@ abstract class ServerPacket(val input: DataInputStream) : Packet { ...@@ -146,26 +148,26 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
return decryptAsByteArray(key).dataInputStream() return decryptAsByteArray(key).dataInputStream()
} }
@ExperimentalUnsignedTypes
fun decryptBy(keyHex: String): DataInputStream { fun decryptBy(keyHex: String): DataInputStream {
return this.decryptBy(keyHex.hexToBytes()) return this.decryptBy(keyHex.hexToBytes())
} }
fun decryptBy(key1: ByteArray, key2: ByteArray): DataInputStream { fun decryptBy(key1: ByteArray, key2: ByteArray): DataInputStream {
return TEA.decrypt(this.decryptAsByteArray(key1), key2).dataInputStream(); return TEA.decrypt(this.decryptAsByteArray(key1), key2).dataInputStream()
} }
@ExperimentalUnsignedTypes
fun decryptBy(key1: String, key2: ByteArray): DataInputStream { fun decryptBy(key1: String, key2: ByteArray): DataInputStream {
return this.decryptBy(key1.hexToBytes(), key2) return this.decryptBy(key1.hexToBytes(), key2)
} }
@ExperimentalUnsignedTypes
fun decryptBy(key1: ByteArray, key2: String): DataInputStream { fun decryptBy(key1: ByteArray, key2: String): DataInputStream {
return this.decryptBy(key1, key2.hexToBytes()) return this.decryptBy(key1, key2.hexToBytes())
} }
@ExperimentalUnsignedTypes
fun decryptBy(keyHex1: String, keyHex2: String): DataInputStream { fun decryptBy(keyHex1: String, keyHex2: String): DataInputStream {
return this.decryptBy(keyHex1.hexToBytes(), keyHex2.hexToBytes()) return this.decryptBy(keyHex1.hexToBytes(), keyHex2.hexToBytes())
} }
...@@ -177,7 +179,6 @@ abstract class ServerPacket(val input: DataInputStream) : Packet { ...@@ -177,7 +179,6 @@ abstract class ServerPacket(val input: DataInputStream) : Packet {
} }
@ExperimentalUnsignedTypes
fun DataInputStream.readIP(): String { fun DataInputStream.readIP(): String {
var buff = "" var buff = ""
for (i in 0..3) { for (i in 0..3) {
...@@ -208,7 +209,7 @@ fun ByteArray.dataInputStream(): DataInputStream = DataInputStream(this.inputStr ...@@ -208,7 +209,7 @@ fun ByteArray.dataInputStream(): DataInputStream = DataInputStream(this.inputStr
*/ */
infix fun <N : Number> DataInputStream.goto(position: N): DataInputStream { infix fun <N : Number> DataInputStream.goto(position: N): DataInputStream {
this.reset() this.reset()
this.skip(position.toLong()); this.skip(position.toLong())
return this return this
} }
...@@ -239,26 +240,26 @@ fun DataInputStream.readNBytesIn(range: IntRange): ByteArray { ...@@ -239,26 +240,26 @@ fun DataInputStream.readNBytesIn(range: IntRange): ByteArray {
fun <N : Number> DataInputStream.readIntAt(position: N): Int { fun <N : Number> DataInputStream.readIntAt(position: N): Int {
this.goto(position) this.goto(position)
return this.readInt(); return this.readInt()
} }
@ExperimentalUnsignedTypes
fun <N : Number> DataInputStream.readUIntAt(position: N): UInt { fun <N : Number> DataInputStream.readUIntAt(position: N): UInt {
this.goto(position) this.goto(position)
return this.readNBytes(4).toUInt(); return this.readNBytes(4).toUInt()
} }
fun <N : Number> DataInputStream.readByteAt(position: N): Byte { fun <N : Number> DataInputStream.readByteAt(position: N): Byte {
this.goto(position) this.goto(position)
return this.readByte(); return this.readByte()
} }
fun <N : Number> DataInputStream.readShortAt(position: N): Short { fun <N : Number> DataInputStream.readShortAt(position: N): Short {
this.goto(position) this.goto(position)
return this.readShort(); return this.readShort()
} }
@ExperimentalUnsignedTypes
@JvmSynthetic @JvmSynthetic
fun DataInputStream.gotoWhere(matcher: UByteArray): DataInputStream { fun DataInputStream.gotoWhere(matcher: UByteArray): DataInputStream {
return this.gotoWhere(matcher.toByteArray()) return this.gotoWhere(matcher.toByteArray())
......
...@@ -29,4 +29,6 @@ class ClientChangeOnlineStatusPacket( ...@@ -29,4 +29,6 @@ class ClientChangeOnlineStatusPacket(
it.writeHex("00 01 00 01 00 04 00 00 00 00") it.writeHex("00 01 00 01 00 04 00 00 00 00")
} }
} }
} }
\ No newline at end of file
package net.mamoe.mirai.network.packet.login package net.mamoe.mirai.network.packet.login
import net.mamoe.mirai.network.packet.PacketId
import net.mamoe.mirai.network.packet.ServerPacket import net.mamoe.mirai.network.packet.ServerPacket
import java.io.DataInputStream import java.io.DataInputStream
...@@ -8,4 +9,5 @@ import java.io.DataInputStream ...@@ -8,4 +9,5 @@ import java.io.DataInputStream
* *
* @author Him188moe * @author Him188moe
*/ */
@PacketId("00 EC")
class ServerLoginSuccessPacket(input: DataInputStream) : ServerPacket(input) class ServerLoginSuccessPacket(input: DataInputStream) : ServerPacket(input)
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment