186 lines
5.3 KiB
C++
186 lines
5.3 KiB
C++
#include "precompile.h"
|
|
|
|
#include <memory.h>
|
|
#include <string.h>
|
|
|
|
#include <f8/netmsghandler.h>
|
|
#include <f8/udplog.h>
|
|
|
|
#include "kcpsession.h"
|
|
#include "longsessionmgr.h"
|
|
#include "jsondatamgr.h"
|
|
#include "app.h"
|
|
|
|
static const int DEFAULT_MAX_RECV_BUFFERSIZE = 1024 * 64;
|
|
|
|
static int UdpOutput(const char *buf, int len, ikcpcb *kcp, void *user)
|
|
{
|
|
KcpSession* session = (KcpSession*)user;
|
|
a8::UdpPacket pkt;
|
|
pkt.buf = buf;
|
|
pkt.buf_len = len;
|
|
pkt.remote_addr = session->GetAddr();
|
|
LongSessionMgr::Instance()->GetUdpListener()->SendUdpPacket(&pkt);
|
|
return 0;
|
|
}
|
|
|
|
KcpSession::KcpSession()
|
|
{
|
|
|
|
}
|
|
|
|
KcpSession::~KcpSession()
|
|
{
|
|
|
|
}
|
|
|
|
void KcpSession::Init(int socket_handle, int secret_key_place)
|
|
{
|
|
socket_handle_ = socket_handle;
|
|
secret_key_ = App::Instance()->NewUuid();
|
|
kcp_ = ikcp_create(socket_handle_, (void*)this);
|
|
const KcpConf& kcp_conf = JsonDataMgr::Instance()->GetKcpConf();
|
|
ikcp_wndsize(kcp_, kcp_conf.sndwnd, kcp_conf.rcvwnd);
|
|
ikcp_nodelay(kcp_, kcp_conf.nodelay, kcp_conf.interval, kcp_conf.resend, kcp_conf.nc);
|
|
kcp_->rx_minrto = kcp_conf.rx_minrto;
|
|
kcp_->fastresend = kcp_conf.fastresend;
|
|
secret_key_place_ = secret_key_place;
|
|
if (secret_key_place_ > 0) {
|
|
secret_key_place_ = 1;
|
|
} else if (secret_key_place_ < 0) {
|
|
secret_key_place_ = 0;
|
|
}
|
|
kcp_->output = UdpOutput;
|
|
init_tick_ = a8::XGetTickCount();
|
|
}
|
|
|
|
void KcpSession::UnInit()
|
|
{
|
|
if (kcp_) {
|
|
ikcp_release(kcp_);
|
|
kcp_ = nullptr;
|
|
}
|
|
}
|
|
|
|
void KcpSession::Update(long long tick)
|
|
{
|
|
ikcp_update(kcp_, tick - init_tick_);
|
|
UpdateInput();
|
|
}
|
|
|
|
void KcpSession::SendClientMsg(char* buf, int buf_len)
|
|
{
|
|
ikcp_send(kcp_, buf, buf_len);
|
|
}
|
|
|
|
void KcpSession::OnRecvPacket(a8::UdpPacket* pkt)
|
|
{
|
|
const int IKCP_OVERHEAD = 24;
|
|
|
|
remote_addr_ = pkt->remote_addr;
|
|
if (GetSecretKeyPlace()) {
|
|
char* buf = (char*)malloc(pkt->buf_len - GetSecretKeyLen());
|
|
int buflen = pkt->buf_len - GetSecretKeyLen();
|
|
memmove(buf, pkt->buf, IKCP_OVERHEAD);
|
|
if (pkt->buf_len > IKCP_OVERHEAD + GetSecretKeyLen()) {
|
|
memmove(buf + IKCP_OVERHEAD, pkt->buf + IKCP_OVERHEAD + GetSecretKeyLen(), buflen - IKCP_OVERHEAD);
|
|
}
|
|
ikcp_input(kcp_, buf, buflen);
|
|
free(buf);
|
|
} else {
|
|
ikcp_input(kcp_, pkt->buf, pkt->buf_len);
|
|
}
|
|
}
|
|
|
|
void KcpSession::UpdateInput()
|
|
{
|
|
char buf[DEFAULT_MAX_RECV_BUFFERSIZE];
|
|
int buflen = ikcp_recv(kcp_, buf, DEFAULT_MAX_RECV_BUFFERSIZE - 10);
|
|
if (buflen <= 0) {
|
|
return;
|
|
}
|
|
OnSocketRead(buf, buflen);
|
|
}
|
|
|
|
void KcpSession::DecodeUserPacket(char* buf, int& offset, unsigned int buflen)
|
|
{
|
|
if (GetSecretKeyPlace()) {
|
|
DecodeUserPacketNew(buf, offset, buflen);
|
|
} else {
|
|
DecodeUserPacketOld(buf, offset, buflen);
|
|
}
|
|
}
|
|
|
|
int KcpSession::GetSecretKeyPlace()
|
|
{
|
|
return secret_key_place_;
|
|
}
|
|
|
|
void KcpSession::DecodeUserPacketOld(char* buf, int& offset, unsigned int buflen)
|
|
{
|
|
bool warning = false;
|
|
while (buflen - offset >= sizeof(f8::PackHead) + GetSecretKeyLen()) {
|
|
long long secret_key = KcpSession::ReadSecretKey(&buf[offset], buflen);
|
|
if (secret_key != secret_key_) {
|
|
warning = true;
|
|
offset++;
|
|
continue;
|
|
}
|
|
f8::PackHead* p = (f8::PackHead*)&buf[offset + GetSecretKeyLen()];
|
|
if (p->magic_code == f8::MAGIC_CODE) {
|
|
if (buflen - offset < sizeof(f8::PackHead) + p->packlen + GetSecretKeyLen()) {
|
|
break;
|
|
}
|
|
App::Instance()->AddSocketMsg(SF_Client,
|
|
socket_handle_,
|
|
0,
|
|
//saddr,
|
|
p->msgid,
|
|
p->seqid,
|
|
&buf[offset + sizeof(f8::PackHead) + GetSecretKeyLen()],
|
|
p->packlen,
|
|
ST_Udp);
|
|
offset += sizeof(f8::PackHead) + p->packlen + GetSecretKeyLen();
|
|
} else {
|
|
warning = true;
|
|
offset++;
|
|
continue;
|
|
}
|
|
}
|
|
|
|
if (warning) {
|
|
f8::UdpLog::Instance()->Warning("收到kcp client非法数据包1", {});
|
|
}
|
|
}
|
|
|
|
void KcpSession::DecodeUserPacketNew(char* buf, int& offset, unsigned int buflen)
|
|
{
|
|
bool warning = false;
|
|
while (buflen - offset >= sizeof(f8::PackHead)) {
|
|
f8::PackHead* p = (f8::PackHead*)&buf[offset];
|
|
if (p->magic_code == f8::MAGIC_CODE) {
|
|
if (buflen - offset < sizeof(f8::PackHead) + p->packlen) {
|
|
break;
|
|
}
|
|
App::Instance()->AddSocketMsg(SF_Client,
|
|
socket_handle_,
|
|
0,
|
|
//saddr,
|
|
p->msgid,
|
|
p->seqid,
|
|
&buf[offset + sizeof(f8::PackHead)],
|
|
p->packlen,
|
|
ST_Udp);
|
|
offset += sizeof(f8::PackHead) + p->packlen;
|
|
} else {
|
|
warning = true;
|
|
offset++;
|
|
continue;
|
|
}
|
|
}
|
|
|
|
if (warning) {
|
|
f8::UdpLog::Instance()->Warning("收到kcp client非法数据包2", {});
|
|
}
|
|
}
|