1
0
mirror of https://github.com/Mrs4s/MiraiGo.git synced 2025-05-04 11:07:40 +08:00

client: pack packet by transport

This commit is contained in:
wdvxdr 2021-12-22 22:29:36 +08:00
parent 3e2b57eab5
commit d2dc2e472d
No known key found for this signature in database
GPG Key ID: 703F8C071DE7A1B6
17 changed files with 343 additions and 347 deletions

View File

@ -10,6 +10,7 @@ import (
"github.com/Mrs4s/MiraiGo/binary/jce"
"github.com/Mrs4s/MiraiGo/client/internal/auth"
"github.com/Mrs4s/MiraiGo/client/internal/codec"
"github.com/Mrs4s/MiraiGo/client/internal/network"
"github.com/Mrs4s/MiraiGo/client/pb"
"github.com/Mrs4s/MiraiGo/client/pb/cmd0x352"
"github.com/Mrs4s/MiraiGo/client/pb/msg"
@ -90,9 +91,16 @@ func (c *QQClient) buildLoginPacket() (uint16, []byte) {
w.Write(tlv.T521(0))
w.Write(tlv.T525(tlv.T536([]byte{0x01, 0x00})))
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildDeviceLockLoginPacket() (uint16, []byte) {
@ -102,13 +110,19 @@ func (c *QQClient) buildDeviceLockLoginPacket() (uint16, []byte) {
w.WriteUInt16(4)
w.Write(tlv.T8(2052))
w.Write(tlv.T104(c.t104))
w.Write(tlv.T104(c.sig.T104))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
w.Write(tlv.T401(c.g))
w.Write(tlv.T401(c.sig.G))
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildQRCodeFetchRequestPacket() (uint16, []byte) {
@ -133,13 +147,21 @@ func (c *QQClient) buildQRCodeFetchRequestPacket() (uint16, []byte) {
w.Write(tlv.T35(8))
}))
}))
sso := packets.BuildSsoPacket(seq, watch.AppId, c.version.SubAppId, "wtlogin.trans_emp", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(0, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: 0,
CommandName: "wtlogin.trans_emp",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildQRCodeResultQueryRequestPacket(sig []byte) (uint16, []byte) {
watch := auth.AndroidWatch.Version()
version := c.transport.Version
c.transport.Version = auth.AndroidWatch.Version()
seq := c.nextSeq()
req := c.buildOicqRequestPacket(0, 0x0812, binary.NewWriterF(func(w *binary.Writer) {
w.WriteHex(`0000620000001000000072000000`) // trans header
@ -156,9 +178,18 @@ func (c *QQClient) buildQRCodeResultQueryRequestPacket(sig []byte) (uint16, []by
w.WriteUInt16(0) // const
}))
}))
sso := packets.BuildSsoPacket(seq, watch.AppId, c.version.SubAppId, "wtlogin.trans_emp", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(0, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: 0,
CommandName: "wtlogin.trans_emp",
Body: req,
}
payload := c.transport.PackPacket(&req2)
c.transport.Version = version
return seq, payload
}
func (c *QQClient) buildQRCodeLoginPacket(t106, t16a, t318 []byte) (uint16, []byte) {
@ -230,9 +261,16 @@ func (c *QQClient) buildQRCodeLoginPacket(t106, t16a, t318 []byte) (uint16, []by
w.Write(wb)
cl()
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildCaptchaPacket(result string, sign []byte) (uint16, []byte) {
@ -243,12 +281,19 @@ func (c *QQClient) buildCaptchaPacket(result string, sign []byte) (uint16, []byt
w.Write(tlv.T2(result, sign))
w.Write(tlv.T8(2052))
w.Write(tlv.T104(c.t104))
w.Write(tlv.T104(c.sig.T104))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildSMSRequestPacket() (uint16, []byte) {
@ -258,15 +303,22 @@ func (c *QQClient) buildSMSRequestPacket() (uint16, []byte) {
w.WriteUInt16(6)
w.Write(tlv.T8(2052))
w.Write(tlv.T104(c.t104))
w.Write(tlv.T104(c.sig.T104))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
w.Write(tlv.T174(c.t174))
w.Write(tlv.T174(c.sig.T174))
w.Write(tlv.T17A(9))
w.Write(tlv.T197())
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildSMSCodeSubmitPacket(code string) (uint16, []byte) {
@ -276,16 +328,23 @@ func (c *QQClient) buildSMSCodeSubmitPacket(code string) (uint16, []byte) {
w.WriteUInt16(7)
w.Write(tlv.T8(2052))
w.Write(tlv.T104(c.t104))
w.Write(tlv.T104(c.sig.T104))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
w.Write(tlv.T174(c.t174))
w.Write(tlv.T174(c.sig.T174))
w.Write(tlv.T17C(code))
w.Write(tlv.T401(c.g))
w.Write(tlv.T401(c.sig.G))
w.Write(tlv.T198())
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildTicketSubmitPacket(ticket string) (uint16, []byte) {
@ -296,12 +355,19 @@ func (c *QQClient) buildTicketSubmitPacket(ticket string) (uint16, []byte) {
w.Write(tlv.T193(ticket))
w.Write(tlv.T8(2052))
w.Write(tlv.T104(c.t104))
w.Write(tlv.T104(c.sig.T104))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.login", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildRequestTgtgtNopicsigPacket() (uint16, []byte) {
@ -314,14 +380,14 @@ func (c *QQClient) buildRequestTgtgtNopicsigPacket() (uint16, []byte) {
w.Write(tlv.T1(uint32(c.Uin), c.deviceInfo.IpAddress))
wb, cl := binary.OpenWriterF(func(bw *binary.Writer) {
bw.WriteUInt16(0x106)
bw.WriteBytesShort(c.sigInfo.EncryptedA1)
bw.WriteBytesShort(c.sig.EncryptedA1)
})
w.Write(wb)
cl()
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
w.Write(tlv.T100(c.version.SSOVersion, 2, c.version.MainSigMap))
w.Write(tlv.T107(0))
w.Write(tlv.T108(c.ksid))
w.Write(tlv.T108(c.sig.Ksid))
w.Write(tlv.T144(
c.deviceInfo.AndroidId,
c.deviceInfo.GenDeviceInfoData(),
@ -337,7 +403,7 @@ func (c *QQClient) buildRequestTgtgtNopicsigPacket() (uint16, []byte) {
))
w.Write(tlv.T142(c.version.ApkId))
w.Write(tlv.T145(c.deviceInfo.Guid))
w.Write(tlv.T16A(c.sigInfo.SrmToken))
w.Write(tlv.T16A(c.sig.SrmToken))
w.Write(tlv.T154(seq))
w.Write(tlv.T141(c.deviceInfo.SimInfo, c.deviceInfo.APN))
w.Write(tlv.T8(2052))
@ -348,7 +414,7 @@ func (c *QQClient) buildRequestTgtgtNopicsigPacket() (uint16, []byte) {
}))
w.Write(tlv.T147(16, []byte(c.version.SortVersionName), c.version.ApkSign))
w.Write(tlv.T177(c.version.BuildTime, c.version.SdkVersion))
w.Write(tlv.T400(c.g, c.Uin, c.deviceInfo.Guid, c.dpwd, 1, 16, c.randSeed))
w.Write(tlv.T400(c.sig.G, c.Uin, c.deviceInfo.Guid, c.sig.Dpwd, 1, 16, c.sig.RandSeed))
w.Write(tlv.T187(c.deviceInfo.MacAddress))
w.Write(tlv.T188(c.deviceInfo.AndroidId))
w.Write(tlv.T194(c.deviceInfo.IMSIMd5))
@ -363,23 +429,20 @@ func (c *QQClient) buildRequestTgtgtNopicsigPacket() (uint16, []byte) {
oicq := codec.OICQ{
Uin: uint32(c.Uin),
Command: 0x810,
EncryptMethod: crypto.NewEncryptSession(c.sigInfo.T133),
Key: c.sigInfo.WtSessionTicketKey,
EncryptMethod: crypto.NewEncryptSession(c.sig.T133),
Key: c.sig.WtSessionTicketKey,
Body: req,
}
uni := codec.Uni{
nreq := network.Request{
Type: network.RequestTypeSimple,
EncryptType: network.EncryptTypeEmptyKey,
Uin: c.Uin,
Seq: seq,
SequenceID: int32(seq),
CommandName: "wtlogin.exchange_emp",
EncryptType: 2,
SessionID: c.OutGoingPacketSessionId,
ExtraData: EmptyBytes,
Key: make([]byte, 16),
Body: oicq.Encode(),
}
return seq, uni.Encode()
return seq, c.transport.PackPacket(&nreq)
}
func (c *QQClient) buildRequestChangeSigPacket(mainSigMap uint32) (uint16, []byte) {
@ -389,10 +452,10 @@ func (c *QQClient) buildRequestChangeSigPacket(mainSigMap uint32) (uint16, []byt
w.WriteUInt16(17)
w.Write(tlv.T100(c.version.SSOVersion, 100, mainSigMap))
w.Write(tlv.T10A(c.sigInfo.TGT))
w.Write(tlv.T10A(c.sig.TGT))
w.Write(tlv.T116(c.version.MiscBitmap, c.version.SubSigmap))
w.Write(tlv.T108(c.ksid))
h := md5.Sum(c.sigInfo.D2Key)
w.Write(tlv.T108(c.sig.Ksid))
h := md5.Sum(c.sig.D2Key)
w.Write(tlv.T144(
c.deviceInfo.AndroidId,
c.deviceInfo.GenDeviceInfoData(),
@ -406,7 +469,7 @@ func (c *QQClient) buildRequestChangeSigPacket(mainSigMap uint32) (uint16, []byt
c.deviceInfo.Brand,
h[:],
))
w.Write(tlv.T143(c.sigInfo.D2))
w.Write(tlv.T143(c.sig.D2))
w.Write(tlv.T142(c.version.ApkId))
w.Write(tlv.T154(seq))
w.Write(tlv.T18(16, uint32(c.Uin)))
@ -424,9 +487,16 @@ func (c *QQClient) buildRequestChangeSigPacket(mainSigMap uint32) (uint16, []byt
}))
// w.Write(tlv.T202(c.deviceInfo.WifiBSSID, c.deviceInfo.WifiSSID))
}))
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "wtlogin.exchange_emp", c.deviceInfo.IMEI, c.sigInfo.TGT, c.OutGoingPacketSessionId, req, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 2, make([]byte, 16), sso, EmptyBytes)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeEmptyKey,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.exchange_emp",
Body: req,
}
return seq, c.transport.PackPacket(&req2)
}
// StatSvc.register
@ -472,9 +542,16 @@ func (c *QQClient) buildClientRegisterPacket() (uint16, []byte) {
Context: make(map[string]string),
Status: make(map[string]string),
}
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "StatSvc.register", c.deviceInfo.IMEI, c.sigInfo.TGT, c.OutGoingPacketSessionId, pkt.ToBytes(), c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 1, c.sigInfo.D2Key, sso, c.sigInfo.D2)
return seq, packet
req2 := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeD2Key,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "StatSvc.register",
Body: pkt.ToBytes(),
}
return seq, c.transport.PackPacket(&req2)
}
func (c *QQClient) buildStatusSetPacket(status, extStatus int32) (uint16, []byte) {
@ -766,7 +843,7 @@ func (c *QQClient) buildGroupMemberInfoRequestPacket(groupCode, uin int64) (uint
// MessageSvc.PbGetMsg
func (c *QQClient) buildGetMessageRequestPacket(flag msg.SyncFlag, msgTime int64) (uint16, []byte) {
cook := c.syncCookie
cook := c.sig.SyncCookie
if cook == nil {
cook, _ = proto.Marshal(&msg.SyncCookie{
Time: &msgTime,
@ -1075,7 +1152,7 @@ func (c *QQClient) buildAppInfoRequestPacket(id string) (uint16, []byte) {
TraceId: proto.String(fmt.Sprintf("%v_%v_%v", c.Uin, time.Now().Format("0102150405"), rand.Int63())),
}
payload, _ := proto.Marshal(body)
packet := packets.BuildUniPacket(c.Uin, seq, "LightAppSvc.mini_app_info.GetAppInfoById", 1, c.OutGoingPacketSessionId, EmptyBytes, c.sigInfo.d2Key, payload)
packet := packets.BuildUniPacket(c.Uin, seq, "LightAppSvc.mini_app_info.GetAppInfoById", 1, c.SessionId, EmptyBytes, c.sigInfo.d2Key, payload)
return seq, packet
}
*/

View File

@ -40,8 +40,8 @@ const (
)
func (c *QQClient) c2cMessageSyncProcessor(rsp *msg.GetMessageResponse, info *network.IncomingPacketInfo) {
c.syncCookie = rsp.SyncCookie
c.pubAccountCookie = rsp.PubAccountCookie
c.sig.SyncCookie = rsp.SyncCookie
c.sig.PubAccountCookie = rsp.PubAccountCookie
// c.msgCtrlBuf = rsp.MsgCtrlBuf
if rsp.UinPairMsgs == nil {
return

View File

@ -20,7 +20,6 @@ import (
"github.com/Mrs4s/MiraiGo/client/internal/network"
"github.com/Mrs4s/MiraiGo/client/pb/msg"
"github.com/Mrs4s/MiraiGo/internal/crypto"
"github.com/Mrs4s/MiraiGo/internal/packets"
"github.com/Mrs4s/MiraiGo/utils"
)
@ -48,11 +47,13 @@ type QQClient struct {
GuildService *GuildService
// protocol public field
SequenceId atomic.Int32
OutGoingPacketSessionId []byte
RandomKey []byte
TCP *network.TCPListener // todo: combine other protocol state into one struct
ConnectTime time.Time
SequenceId atomic.Int32
SessionId []byte
RandomKey []byte
TCP *network.TCPListener // todo: combine other protocol state into one struct
ConnectTime time.Time
transport *network.Transport
// internal state
handlers HandlerMap
@ -65,29 +66,10 @@ type QQClient struct {
alive bool
ecdh *crypto.EncryptECDH
// tlv cache
t104 []byte
t174 []byte
g []byte
t402 []byte
randSeed []byte // t403
// rollbackSig []byte
// t149 []byte
// t150 []byte
// t528 []byte
// t530 []byte
// sync info
syncCookie []byte
pubAccountCookie []byte
ksid []byte
// msgCtrlBuf []byte
// session info
qwebSeq atomic.Int64
sigInfo *auth.SigInfo
sig *auth.SigInfo
highwaySession *highway.Session
dpwd []byte
// pwdFlag bool
// timeDiff int64
@ -176,22 +158,33 @@ func NewClientEmpty() *QQClient {
func NewClientMd5(uin int64, passwordMd5 [16]byte) *QQClient {
cli := &QQClient{
Uin: uin,
PasswordMd5: passwordMd5,
AllowSlider: true,
RandomKey: make([]byte, 16),
OutGoingPacketSessionId: []byte{0x02, 0xB0, 0x5B, 0x8B},
TCP: &network.TCPListener{},
sigInfo: &auth.SigInfo{},
eventHandlers: &eventHandlers{},
msgSvcCache: utils.NewCache(time.Second * 15),
transCache: utils.NewCache(time.Second * 15),
onlinePushCache: utils.NewCache(time.Second * 15),
servers: []*net.TCPAddr{},
alive: true,
ecdh: crypto.NewEcdh(),
highwaySession: new(highway.Session),
Uin: uin,
PasswordMd5: passwordMd5,
AllowSlider: true,
RandomKey: make([]byte, 16),
TCP: &network.TCPListener{},
sig: &auth.SigInfo{
OutPacketSessionID: []byte{0x02, 0xB0, 0x5B, 0x8B},
},
eventHandlers: &eventHandlers{},
msgSvcCache: utils.NewCache(time.Second * 15),
transCache: utils.NewCache(time.Second * 15),
onlinePushCache: utils.NewCache(time.Second * 15),
servers: []*net.TCPAddr{},
alive: true,
ecdh: crypto.NewEcdh(),
highwaySession: new(highway.Session),
version: new(auth.AppVersion),
deviceInfo: new(auth.Device),
}
cli.transport = &network.Transport{
Sig: cli.sig,
Version: cli.version,
Device: cli.deviceInfo,
}
{ // init atomic values
cli.SequenceId.Store(0x3635)
cli.requestPacketRequestID.Store(1921334513)
@ -256,10 +249,10 @@ func NewClientMd5(uin int64, passwordMd5 [16]byte) *QQClient {
}
func (c *QQClient) UseDevice(info *auth.Device) {
c.version = info.Protocol.Version()
*c.version = *info.Protocol.Version()
*c.deviceInfo = *info
c.highwaySession.AppID = int32(c.version.AppId)
c.ksid = []byte(fmt.Sprintf("|%s|A8.2.7.27f6ea96", info.IMEI))
c.deviceInfo = info
c.sig.Ksid = []byte(fmt.Sprintf("|%s|A8.2.7.27f6ea96", info.IMEI))
}
func (c *QQClient) Release() {
@ -301,14 +294,14 @@ func (c *QQClient) TokenLogin(token []byte) error {
{
r := binary.NewReader(token)
c.Uin = r.ReadInt64()
c.sigInfo.D2 = r.ReadBytesShort()
c.sigInfo.D2Key = r.ReadBytesShort()
c.sigInfo.TGT = r.ReadBytesShort()
c.sigInfo.SrmToken = r.ReadBytesShort()
c.sigInfo.T133 = r.ReadBytesShort()
c.sigInfo.EncryptedA1 = r.ReadBytesShort()
c.sigInfo.WtSessionTicketKey = r.ReadBytesShort()
c.OutGoingPacketSessionId = r.ReadBytesShort()
c.sig.D2 = r.ReadBytesShort()
c.sig.D2Key = r.ReadBytesShort()
c.sig.TGT = r.ReadBytesShort()
c.sig.SrmToken = r.ReadBytesShort()
c.sig.T133 = r.ReadBytesShort()
c.sig.EncryptedA1 = r.ReadBytesShort()
c.sig.WtSessionTicketKey = r.ReadBytesShort()
c.sig.OutPacketSessionID = r.ReadBytesShort()
// SystemDeviceInfo.TgtgtKey = r.ReadBytesShort()
c.deviceInfo.TgtgtKey = r.ReadBytesShort()
}
@ -406,7 +399,7 @@ func (c *QQClient) RequestSMS() bool {
}
func (c *QQClient) init(tokenLogin bool) error {
if len(c.g) == 0 {
if len(c.sig.G) == 0 {
c.Warning("device lock is disable. http api may fail.")
}
c.highwaySession.Uin = strconv.FormatInt(c.Uin, 10)
@ -449,14 +442,14 @@ func (c *QQClient) init(tokenLogin bool) error {
func (c *QQClient) GenToken() []byte {
return binary.NewWriterF(func(w *binary.Writer) {
w.WriteUInt64(uint64(c.Uin))
w.WriteBytesShort(c.sigInfo.D2)
w.WriteBytesShort(c.sigInfo.D2Key)
w.WriteBytesShort(c.sigInfo.TGT)
w.WriteBytesShort(c.sigInfo.SrmToken)
w.WriteBytesShort(c.sigInfo.T133)
w.WriteBytesShort(c.sigInfo.EncryptedA1)
w.WriteBytesShort(c.sigInfo.WtSessionTicketKey)
w.WriteBytesShort(c.OutGoingPacketSessionId)
w.WriteBytesShort(c.sig.D2)
w.WriteBytesShort(c.sig.D2Key)
w.WriteBytesShort(c.sig.TGT)
w.WriteBytesShort(c.sig.SrmToken)
w.WriteBytesShort(c.sig.T133)
w.WriteBytesShort(c.sig.EncryptedA1)
w.WriteBytesShort(c.sig.WtSessionTicketKey)
w.WriteBytesShort(c.sig.OutPacketSessionID)
w.WriteBytesShort(c.deviceInfo.TgtgtKey)
})
}
@ -681,11 +674,11 @@ func (c *QQClient) SolveFriendRequest(req *NewFriendRequest, accept bool) {
}
func (c *QQClient) getSKey() string {
if c.sigInfo.SKeyExpiredTime < time.Now().Unix() && len(c.g) > 0 {
if c.sig.SKeyExpiredTime < time.Now().Unix() && len(c.sig.G) > 0 {
c.Debug("skey expired. refresh...")
_, _ = c.sendAndWait(c.buildRequestTgtgtNopicsigPacket())
}
return string(c.sigInfo.SKey)
return string(c.sig.SKey)
}
func (c *QQClient) getCookies() string {
@ -695,7 +688,7 @@ func (c *QQClient) getCookies() string {
func (c *QQClient) getCookiesWithDomain(domain string) string {
cookie := c.getCookies()
if psKey, ok := c.sigInfo.PsKeyMap[domain]; ok {
if psKey, ok := c.sig.PsKeyMap[domain]; ok {
return fmt.Sprintf("%s p_uin=o%d; p_skey=%s;", cookie, c.Uin, psKey)
} else {
return cookie
@ -800,8 +793,15 @@ func (c *QQClient) doHeartbeat() {
for c.Online.Load() {
time.Sleep(time.Second * 30)
seq := c.nextSeq()
sso := packets.BuildSsoPacket(seq, c.version.AppId, c.version.SubAppId, "Heartbeat.Alive", c.deviceInfo.IMEI, EmptyBytes, c.OutGoingPacketSessionId, EmptyBytes, c.ksid)
packet := packets.BuildLoginPacket(c.Uin, 0, EmptyBytes, sso, EmptyBytes)
req := network.Request{
Type: network.RequestTypeLogin,
EncryptType: network.EncryptTypeNoEncrypt,
SequenceID: int32(seq),
Uin: c.Uin,
CommandName: "wtlogin.login",
Body: EmptyBytes,
}
packet := c.transport.PackPacket(&req)
_, err := c.sendAndWait(seq, packet)
if errors.Is(err, network.ErrConnectionClosed) {
continue

View File

@ -39,10 +39,10 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
reader.ReadUInt16()
m := reader.ReadTlvMap(2)
if m.Exists(0x402) {
c.dpwd = []byte(utils.RandomString(16))
c.t402 = m[0x402]
h := md5.Sum(append(append(c.deviceInfo.Guid, c.dpwd...), c.t402...))
c.g = h[:]
c.sig.Dpwd = []byte(utils.RandomString(16))
c.sig.T402 = m[0x402]
h := md5.Sum(append(append(c.deviceInfo.Guid, c.sig.Dpwd...), c.sig.T402...))
c.sig.G = h[:]
}
if t == 0 { // login success
// if t150, ok := m[0x150]; ok {
@ -52,7 +52,7 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
c.decodeT161(t161)
}
if m.Exists(0x403) {
c.randSeed = m[0x403]
c.sig.RandSeed = m[0x403]
}
c.decodeT119(m[0x119], c.deviceInfo.TgtgtKey)
return LoginResponse{
@ -60,7 +60,7 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
}, nil
}
if t == 2 {
c.t104 = m[0x104]
c.sig.T104 = m[0x104]
if m.Exists(0x192) {
return LoginResponse{
Success: false,
@ -97,9 +97,9 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
if t == 160 || t == 239 {
if t174, ok := m[0x174]; ok { // 短信验证
c.t104 = m[0x104]
c.t174 = t174
c.randSeed = m[0x403]
c.sig.T104 = m[0x104]
c.sig.T174 = t174
c.sig.RandSeed = m[0x403]
phone := func() string {
r := binary.NewReader(m[0x178])
return r.ReadStringLimit(int(r.ReadInt32()))
@ -122,7 +122,7 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
}
if _, ok := m[0x17b]; ok { // 二次验证
c.t104 = m[0x104]
c.sig.T104 = m[0x104]
return LoginResponse{
Success: false,
Error: SMSNeededError,
@ -146,8 +146,8 @@ func decodeLoginResponse(c *QQClient, _ *network.IncomingPacketInfo, payload []b
}
if t == 204 {
c.t104 = m[0x104]
c.randSeed = m[0x403]
c.sig.T104 = m[0x104]
c.sig.RandSeed = m[0x403]
return c.sendAndWait(c.buildDeviceLockLoginPacket())
} // drive lock
@ -210,7 +210,7 @@ func decodeExchangeEmpResponse(c *QQClient, _ *network.IncomingPacketInfo, paylo
c.decodeT119R(m[0x119])
}
if cmd == 11 {
h := md5.Sum(c.sigInfo.D2Key)
h := md5.Sum(c.sig.D2Key)
c.decodeT119(m[0x119], h[:])
}
return nil, nil

View File

@ -663,7 +663,7 @@ func (s *GuildService) fetchChannelListState(guildId uint64, channels []*Channel
2: ids,
},
})
packet := packets.BuildUniPacket(s.c.Uin, seq, "OidbSvcTrpcTcp.0x1008_1", 1, s.c.OutGoingPacketSessionId, []byte{}, s.c.sigInfo.d2Key, payload)
packet := packets.BuildUniPacket(s.c.Uin, seq, "OidbSvcTrpcTcp.0x1008_1", 1, s.c.SessionId, []byte{}, s.c.sigInfo.d2Key, payload)
rsp, err := s.c.sendAndWaitDynamic(seq, packet)
if err != nil {
return

View File

@ -127,4 +127,26 @@ type SigInfo struct {
PsKeyMap map[string][]byte
Pt4TokenMap map[string][]byte
// Others
OutPacketSessionID []byte
Dpwd []byte
// tlv cache
T104 []byte
T174 []byte
G []byte
T402 []byte
RandSeed []byte // t403
// rollbackSig []byte
// t149 []byte
// t150 []byte
// t528 []byte
// t530 []byte
// sync info
SyncCookie []byte
PubAccountCookie []byte
Ksid []byte
// msgCtrlBuf []byte
}

View File

@ -1,41 +0,0 @@
package codec
import (
"strconv"
"github.com/Mrs4s/MiraiGo/binary"
)
type Uni struct {
Uin int64
Seq uint16
CommandName string
EncryptType byte
SessionID []byte
ExtraData []byte
Key []byte
Body []byte
}
func (u *Uni) Encode() []byte {
return binary.NewWriterF(func(w *binary.Writer) {
w2 := binary.SelectWriter()
{ // w.WriteIntLvPacket
w2.WriteUInt32(0x0B)
w2.WriteByte(u.EncryptType)
w2.WriteUInt32(uint32(u.Seq))
w2.WriteByte(0)
w2.WriteString(strconv.FormatInt(u.Uin, 10))
// inline NewWriterF
w3 := binary.SelectWriter()
w3.WriteUniPacket(u.CommandName, u.SessionID, u.ExtraData, u.Body)
w2.EncryptAndWrite(u.Key, w3.Bytes())
binary.PutWriter(w3)
}
data := w2.Bytes()
w.WriteUInt32(uint32(len(data) + 4))
w.Write(data)
binary.PutWriter(w2)
})
}

View File

@ -22,6 +22,6 @@ type Request struct {
EncryptType EncryptType
SequenceID int32
Uin int64
Method string
CommandName string
Body []byte
}

View File

@ -11,95 +11,96 @@ import (
// Transport is a network transport.
type Transport struct {
sessionMu sync.Mutex
// todo: combine session fields to a struct
tgt []byte
d2key []byte
sessionID []byte
ksid []byte
version *auth.AppVersion
device *auth.Device
Sig *auth.SigInfo
Version *auth.AppVersion
Device *auth.Device
// connection
conn *TCPListener
// conn *TCPListener
}
func (t *Transport) packBody(req *Request, w *binary.Writer) {
func (t *Transport) packBody(req *Request) []byte {
w := binary.SelectWriter()
defer binary.PutWriter(w)
w.WriteIntLvPacket(4, func(writer *binary.Writer) {
if req.Type == RequestTypeLogin {
writer.WriteUInt32(uint32(req.SequenceID))
writer.WriteUInt32(t.version.AppId)
writer.WriteUInt32(t.version.SubAppId)
writer.WriteUInt32(t.Version.AppId)
writer.WriteUInt32(t.Version.SubAppId)
writer.Write([]byte{0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00})
if len(t.tgt) == 0 || len(t.tgt) == 4 {
tgt := t.Sig.TGT
if len(tgt) == 0 || len(tgt) == 4 {
writer.WriteUInt32(0x04)
} else {
writer.WriteUInt32(uint32(len(t.tgt) + 4))
writer.Write(t.tgt)
writer.WriteUInt32(uint32(len(tgt) + 4))
writer.Write(tgt)
}
}
writer.WriteString(req.Method)
writer.WriteUInt32(uint32(len(t.sessionID) + 4))
w.Write(t.sessionID)
writer.WriteString(req.CommandName)
writer.WriteIntLvPacket(4, func(w *binary.Writer) {
w.Write(t.Sig.OutPacketSessionID)
})
// writer.WriteUInt32(uint32(len(t.Sig.OutPacketSessionID) + 4))
// w.Write(t.Sig.OutPacketSessionID)
if req.Type == RequestTypeLogin {
writer.WriteString(t.device.IMEI)
writer.WriteString(t.Device.IMEI)
writer.WriteUInt32(0x04)
{
writer.WriteUInt16(uint16(len(t.ksid)) + 2)
writer.Write(t.ksid)
writer.WriteUInt16(uint16(len(t.Sig.Ksid)) + 2)
writer.Write(t.Sig.Ksid)
}
}
writer.WriteUInt32(0x04)
})
w.WriteUInt32(uint32(len(req.Body) + 4))
w.Write(req.Body)
w.WriteIntLvPacket(4, func(w *binary.Writer) {
w.Write(req.Body)
})
// w.WriteUInt32(uint32(len(req.Body) + 4))
// w.Write(req.Body)
return append([]byte(nil), w.Bytes()...)
}
func (t *Transport) Send(req *Request) error {
// todo: return response
// PackPacket packs a packet.
func (t *Transport) PackPacket(req *Request) []byte {
// todo(wdvxdr): combine pack packet, send packet and return the response
if len(t.Sig.D2) == 0 {
req.EncryptType = EncryptTypeEmptyKey
}
body := t.packBody(req)
// encrypt body
switch req.EncryptType {
case EncryptTypeD2Key:
body = binary.NewTeaCipher(t.Sig.D2Key).Encrypt(body)
case EncryptTypeEmptyKey:
body = binary.NewTeaCipher(emptyKey).Encrypt(body)
}
head := binary.NewWriterF(func(w *binary.Writer) {
w.WriteUInt32(uint32(req.Type))
w.WriteUInt32(uint32(req.EncryptType))
w.WriteByte(byte(req.EncryptType))
switch req.Type {
case RequestTypeLogin:
switch req.EncryptType {
case EncryptTypeD2Key:
w.WriteUInt32(uint32(len(t.d2key) + 4))
w.Write(t.d2key)
w.WriteUInt32(uint32(len(t.Sig.D2) + 4))
w.Write(t.Sig.D2)
default:
w.WriteUInt32(4)
}
case RequestTypeSimple:
w.WriteUInt32(uint32(req.SequenceID))
}
w.WriteByte(0x00)
w.WriteString(strconv.FormatInt(req.Uin, 10))
})
w := binary.SelectWriter()
defer binary.PutWriter(w)
t.packBody(req, w)
body := w.Bytes()
// encrypt body
switch req.EncryptType {
case EncryptTypeD2Key:
body = binary.NewTeaCipher(t.d2key).Encrypt(body)
case EncryptTypeEmptyKey:
body = binary.NewTeaCipher(emptyKey).Encrypt(body)
}
w2 := binary.SelectWriter()
defer binary.PutWriter(w2)
w2.WriteUInt32(uint32(len(head) + len(body) + 4))
w2.Write(head)
w2.Write(body)
err := t.conn.Write(w2.Bytes())
if err != nil {
return err
}
return nil
w.WriteUInt32(uint32(len(head)+len(body)) + 4)
w.Write(head)
w.Write(body)
return append([]byte(nil), w.Bytes()...) // copy
}
func (t *Transport) parse(head []byte) *Request {
@ -119,7 +120,7 @@ func (t *Transport) parse(head []byte) *Request {
case EncryptTypeNoEncrypt:
req.Body = body
case EncryptTypeD2Key:
req.Body = binary.NewTeaCipher(t.d2key).Decrypt(body)
req.Body = binary.NewTeaCipher(t.Sig.D2Key).Decrypt(body)
case EncryptTypeEmptyKey:
req.Body = binary.NewTeaCipher(emptyKey).Decrypt(body)
}

View File

@ -42,7 +42,7 @@ type (
)
func (c *QQClient) getGtk(domain string) int {
if psKey, ok := c.sigInfo.PsKeyMap[domain]; ok {
if psKey, ok := c.sig.PsKeyMap[domain]; ok {
accu := 5381
for _, b := range psKey {
accu = accu + (accu << 5) + int(b)

View File

@ -291,7 +291,7 @@ func (c *QQClient) netLoop() {
continue
}
data, _ := c.TCP.ReadBytes(int(l) - 4)
pkt, err := packets.ParseIncomingPacket(data, c.sigInfo.D2Key)
pkt, err := packets.ParseIncomingPacket(data, c.sig.D2Key)
if err != nil {
c.Error("parse incoming packet error: %v", err)
if errors.Is(err, packets.ErrSessionExpired) || errors.Is(err, packets.ErrPacketDropped) {
@ -306,7 +306,7 @@ func (c *QQClient) netLoop() {
continue
}
if pkt.Flag2 == 2 {
pkt.Payload, err = pkt.DecryptPayload(c.ecdh.InitialShareKey, c.RandomKey, c.sigInfo.WtSessionTicketKey)
pkt.Payload, err = pkt.DecryptPayload(c.ecdh.InitialShareKey, c.RandomKey, c.sig.WtSessionTicketKey)
if err != nil {
c.Error("decrypt payload error: %v", err)
if errors.Is(err, packets.ErrUnknownFlag) {

View File

@ -2,6 +2,7 @@ package client
import (
"github.com/Mrs4s/MiraiGo/client/internal/codec"
"github.com/Mrs4s/MiraiGo/client/internal/network"
)
//go:noinline
@ -19,30 +20,26 @@ func (c *QQClient) buildOicqRequestPacket(uin int64, command uint16, body []byte
//go:noinline
func (c *QQClient) uniPacket(command string, body []byte) (uint16, []byte) {
seq := c.nextSeq()
req := codec.Uni{
req := network.Request{
Type: network.RequestTypeSimple,
EncryptType: network.EncryptTypeD2Key,
Uin: c.Uin,
Seq: seq,
SequenceID: int32(seq),
CommandName: command,
EncryptType: 1,
SessionID: c.OutGoingPacketSessionId,
ExtraData: EmptyBytes,
Key: c.sigInfo.D2Key,
Body: body,
}
return seq, req.Encode()
return seq, c.transport.PackPacket(&req)
}
//go:noinline
func (c *QQClient) uniPacketWithSeq(seq uint16, command string, body []byte) []byte {
req := codec.Uni{
req := network.Request{
Type: network.RequestTypeSimple,
EncryptType: network.EncryptTypeD2Key,
Uin: c.Uin,
Seq: seq,
SequenceID: int32(seq),
CommandName: command,
EncryptType: 1,
SessionID: c.OutGoingPacketSessionId,
ExtraData: EmptyBytes,
Key: c.sigInfo.D2Key,
Body: body,
}
return req.Encode()
return c.transport.PackPacket(&req)
}

View File

@ -139,7 +139,7 @@ func (c *QQClient) buildGetOneDayRoamMsgRequest(target, lastMsgTime, random int6
ReadCnt: &count,
}
payload, _ := proto.Marshal(req)
packet := packets.BuildUniPacket(c.Uin, seq, "MessageSvc.PbGetOneDayRoamMsg", 1, c.OutGoingPacketSessionId, EmptyBytes, c.sigInfo.d2Key, payload)
packet := packets.BuildUniPacket(c.Uin, seq, "MessageSvc.PbGetOneDayRoamMsg", 1, c.SessionId, EmptyBytes, c.sigInfo.d2Key, payload)
return seq, packet
}
*/

View File

@ -157,11 +157,11 @@ func (c *QQClient) buildGetOfflineMsgRequestPacket() (uint16, []byte) {
Channel: 4,
Inst: 1,
ChannelEx: 1,
SyncCookie: c.syncCookie,
SyncCookie: c.sig.SyncCookie,
SyncFlag: 0, // START
RambleFlag: 0,
GeneralAbi: 1,
PubAccountCookie: c.pubAccountCookie,
PubAccountCookie: c.sig.PubAccountCookie,
},
GroupMsg: &jce.SvcReqPullGroupMsgSeq{
VerifyType: 0,
@ -172,7 +172,7 @@ func (c *QQClient) buildGetOfflineMsgRequestPacket() (uint16, []byte) {
flag := msg.SyncFlag_START
msgReq, _ := proto.Marshal(&msg.GetMessageRequest{
SyncFlag: &flag,
SyncCookie: c.syncCookie,
SyncCookie: c.sig.SyncCookie,
RambleFlag: proto.Int32(0),
ContextFlag: proto.Int32(1),
OnlineSyncFlag: proto.Int32(0),
@ -224,11 +224,11 @@ func (c *QQClient) buildSyncMsgRequestPacket() (uint16, []byte) {
Channel: 4,
Inst: 1,
ChannelEx: 1,
SyncCookie: c.syncCookie,
SyncCookie: c.sig.SyncCookie,
SyncFlag: 0, // START
RambleFlag: 0,
GeneralAbi: 1,
PubAccountCookie: c.pubAccountCookie,
PubAccountCookie: c.sig.PubAccountCookie,
},
GroupMask: 2,
EndSeq: int64(rand.Uint32()),
@ -237,7 +237,7 @@ func (c *QQClient) buildSyncMsgRequestPacket() (uint16, []byte) {
flag := msg.SyncFlag_START
msgReq := &msg.GetMessageRequest{
SyncFlag: &flag,
SyncCookie: c.syncCookie,
SyncCookie: c.sig.SyncCookie,
RambleFlag: proto.Int32(0),
ContextFlag: proto.Int32(1),
OnlineSyncFlag: proto.Int32(0),
@ -248,7 +248,7 @@ func (c *QQClient) buildSyncMsgRequestPacket() (uint16, []byte) {
offMsg, _ := proto.Marshal(msgReq)
msgReq.MsgReqType = proto.Int32(2)
msgReq.SyncCookie = nil
msgReq.PubaccountCookie = c.pubAccountCookie
msgReq.PubaccountCookie = c.sig.PubAccountCookie
pubMsg, _ := proto.Marshal(msgReq)
buf := &jce.RequestDataVersion3{Map: map[string][]byte{
"req_PbOffMsg": jce.NewJceWriter().WriteBytes(append([]byte{0, 0, 0, 0}, offMsg...), 0).Bytes(),
@ -280,7 +280,7 @@ func (c *QQClient) buildPrivateMsgReadedPacket(uin, time int64) (uint16, []byte)
PeerUin: proto.Uint64(uint64(uin)),
LastReadTime: proto.Uint32(uint32(time)),
},
}, SyncCookie: c.syncCookie}})
}, SyncCookie: c.sig.SyncCookie}})
return c.uniPacket("PbMessageSvc.PbMsgReadedReport", req)
}

View File

@ -5,7 +5,6 @@ import (
"fmt"
"time"
"github.com/Mrs4s/MiraiGo/client/internal/auth"
"github.com/Mrs4s/MiraiGo/utils"
"github.com/Mrs4s/MiraiGo/binary"
@ -44,7 +43,7 @@ func (c *QQClient) decodeT119(data, ek []byte) {
}
*/
if t108, ok := m[0x108]; ok {
c.ksid = t108
c.sig.Ksid = t108
}
var (
@ -91,29 +90,28 @@ func (c *QQClient) decodeT119(data, ek []byte) {
}
// we don't use `c.sigInfo = &auth.SigInfo{...}` here,
// because we need spread `SigInfo` to other places
*c.sigInfo = auth.SigInfo{
LoginBitmap: 0,
SrmToken: utils.Select(m[0x16a], c.sigInfo.SrmToken),
T133: utils.Select(m[0x133], c.sigInfo.T133),
EncryptedA1: utils.Select(m[0x106], c.sigInfo.EncryptedA1),
TGT: m[0x10a],
TGTKey: m[0x10d],
UserStKey: m[0x10e],
UserStWebSig: m[0x103],
SKey: m[0x120],
SKeyExpiredTime: time.Now().Unix() + 21600,
D2: m[0x143],
D2Key: m[0x305],
WtSessionTicketKey: utils.Select(m[0x134], c.sigInfo.WtSessionTicketKey),
DeviceToken: m[0x322],
// because we need keep other fields in `c.sigInfo`
s := c.sig
s.LoginBitmap = 0
s.SrmToken = utils.Select(m[0x16a], s.SrmToken)
s.T133 = utils.Select(m[0x133], s.T133)
s.EncryptedA1 = utils.Select(m[0x106], s.EncryptedA1)
s.TGT = m[0x10a]
s.TGTKey = m[0x10d]
s.UserStKey = m[0x10e]
s.UserStWebSig = m[0x103]
s.SKey = m[0x120]
s.SKeyExpiredTime = time.Now().Unix() + 21600
s.D2 = m[0x143]
s.D2Key = m[0x305]
s.WtSessionTicketKey = utils.Select(m[0x134], s.WtSessionTicketKey)
s.DeviceToken = m[0x322]
PsKeyMap: psKeyMap,
Pt4TokenMap: pt4TokenMap,
}
s.PsKeyMap = psKeyMap
s.Pt4TokenMap = pt4TokenMap
if len(c.PasswordMd5[:]) > 0 {
key := md5.Sum(append(append(c.PasswordMd5[:], []byte{0x00, 0x00, 0x00, 0x00}...), binary.NewWriterF(func(w *binary.Writer) { w.WriteUInt32(uint32(c.Uin)) })...))
decrypted := binary.NewTeaCipher(key[:]).Decrypt(c.sigInfo.EncryptedA1)
decrypted := binary.NewTeaCipher(key[:]).Decrypt(c.sig.EncryptedA1)
if len(decrypted) > 51+16 {
dr := binary.NewReader(decrypted)
dr.ReadBytes(51)
@ -132,9 +130,9 @@ func (c *QQClient) decodeT119R(data []byte) {
reader.ReadBytes(2)
m := reader.ReadTlvMap(2)
if t120, ok := m[0x120]; ok {
c.sigInfo.SKey = t120
c.sigInfo.SKeyExpiredTime = time.Now().Unix() + 21600
c.Debug("skey updated: %v", c.sigInfo.SKey)
c.sig.SKey = t120
c.sig.SKeyExpiredTime = time.Now().Unix() + 21600
c.Debug("skey updated: %v", c.sig.SKey)
}
if t11a, ok := m[0x11a]; ok {
c.Nickname, c.Age, c.Gender = readT11A(t11a)

View File

@ -1,26 +0,0 @@
package packets
import (
"strconv"
"github.com/Mrs4s/MiraiGo/binary"
)
func BuildLoginPacket(uin int64, bodyType byte, key, body, extraData []byte) []byte {
return binary.NewWriterF(func(w *binary.Writer) {
w.WriteIntLvPacket(4, func(w *binary.Writer) {
w.WriteUInt32(0x00_00_00_0A)
w.WriteByte(bodyType)
w.WriteIntLvPacket(4, func(w *binary.Writer) {
w.Write(extraData)
})
w.WriteByte(0x00)
w.WriteString(strconv.FormatInt(uin, 10))
if len(key) == 0 {
w.Write(body)
} else {
w.EncryptAndWrite(key, body)
}
})
})
}

View File

@ -46,38 +46,6 @@ func BuildCode2DRequestPacket(seq uint32, j uint64, cmd uint16, bodyFunc func(wr
})
}
func BuildSsoPacket(seq uint16, appID, subAppID uint32, commandName, imei string, extData, outPacketSessionId, body, ksid []byte) []byte {
return binary.NewWriterF(func(p *binary.Writer) {
p.WriteIntLvPacket(4, func(writer *binary.Writer) {
writer.WriteUInt32(uint32(seq))
writer.WriteUInt32(appID)
writer.WriteUInt32(subAppID)
writer.Write([]byte{0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00})
if len(extData) == 0 || len(extData) == 4 {
writer.WriteUInt32(0x04)
} else {
writer.WriteUInt32(uint32(len(extData) + 4))
writer.Write(extData)
}
writer.WriteString(commandName)
writer.WriteIntLvPacket(4, func(w *binary.Writer) {
w.Write(outPacketSessionId)
})
writer.WriteString(imei)
writer.WriteUInt32(0x04)
{
writer.WriteUInt16(uint16(len(ksid)) + 2)
writer.Write(ksid)
}
writer.WriteUInt32(0x04)
})
p.WriteIntLvPacket(4, func(writer *binary.Writer) {
writer.Write(body)
})
})
}
func ParseIncomingPacket(payload, d2key []byte) (*IncomingPacket, error) {
if len(payload) < 6 {
return nil, errors.WithStack(ErrInvalidPayload)