2019-01-05 20:21:43 +08:00
// IOCPClient.cpp: implementation of the IOCPClient class.
//
//////////////////////////////////////////////////////////////////////
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
# include "stdafx.h"
2025-06-22 18:23:03 +08:00
# include <WS2tcpip.h>
2025-04-06 19:35:20 +08:00
# else
# include <netdb.h>
# include <sys/socket.h>
# include <netinet/tcp.h>
# include <arpa/inet.h>
# include <netinet/in.h> // For struct sockaddr_in
# include <unistd.h> // For close()
# include <cstring> // For memset()
inline int WSAGetLastError ( ) { return - 1 ; }
# define USING_COMPRESS 1
# endif
2019-01-05 20:21:43 +08:00
# include "IOCPClient.h"
2025-04-06 19:35:20 +08:00
# include <assert.h>
# include <string>
2019-01-17 11:58:26 +08:00
# if USING_ZLIB
2025-03-13 23:34:33 +08:00
# include "zlib/zlib.h"
2019-01-17 11:58:26 +08:00
# define Z_FAILED(p) (Z_OK != (p))
# define Z_SUCCESS(p) (!Z_FAILED(p))
# else
2019-01-17 20:41:51 +08:00
# if USING_LZ4
# include "lz4/lz4.h"
# pragma comment(lib, "lz4 / lz4.lib")
# define Z_FAILED(p) (0 == (p))
# define Z_SUCCESS(p) (!Z_FAILED(p))
# define compress(dest, destLen, source, sourceLen) LZ4_compress_default((const char*)source, (char*)dest, sourceLen, *(destLen))
# define uncompress(dest, destLen, source, sourceLen) LZ4_decompress_safe((const char*)source, (char*)dest, sourceLen, *(destLen))
# else
2019-01-17 11:58:26 +08:00
# include "zstd/zstd.h"
2025-02-06 04:15:34 +08:00
# ifdef _WIN64
# pragma comment(lib, "zstd / zstd_x64.lib")
# else
2019-01-17 11:58:26 +08:00
# pragma comment(lib, "zstd / zstd.lib")
2025-02-06 04:15:34 +08:00
# endif
2019-01-17 11:58:26 +08:00
# define Z_FAILED(p) ZSTD_isError(p)
# define Z_SUCCESS(p) (!Z_FAILED(p))
2025-02-07 18:59:15 +08:00
# define ZSTD_CLEVEL 5
# if USING_CTX
# define compress(dest, destLen, source, sourceLen) ZSTD_compress2(m_Cctx, dest, *(destLen), source, sourceLen)
# define uncompress(dest, destLen, source, sourceLen) ZSTD_decompressDCtx(m_Dctx, dest, *(destLen), source, sourceLen)
# else
2019-01-17 11:58:26 +08:00
# define compress(dest, destLen, source, sourceLen) ZSTD_compress(dest, *(destLen), source, sourceLen, ZSTD_CLEVEL_DEFAULT)
# define uncompress(dest, destLen, source, sourceLen) ZSTD_decompress(dest, *(destLen), source, sourceLen)
# endif
2019-01-17 20:41:51 +08:00
# endif
2025-02-07 18:59:15 +08:00
# endif
2019-01-05 20:21:43 +08:00
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
2025-04-06 19:35:20 +08:00
# ifndef _WIN32
BOOL SetKeepAliveOptions ( int socket , int nKeepAliveSec = 180 ) {
// <20> <> <EFBFBD> <EFBFBD> TCP <20> <> <EFBFBD> <EFBFBD> ѡ <EFBFBD> <D1A1>
int enable = 1 ;
if ( setsockopt ( socket , SOL_SOCKET , SO_KEEPALIVE , & enable , sizeof ( enable ) ) < 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Failed to enable TCP keep-alive \n " ) ;
2025-04-06 19:35:20 +08:00
return FALSE ;
}
// <20> <> <EFBFBD> <EFBFBD> TCP_KEEPIDLE (3<> <33> <EFBFBD> ӿ<EFBFBD> <D3BF> к<EFBFBD> <D0BA> <EFBFBD> ʼ <EFBFBD> <CABC> <EFBFBD> <EFBFBD> keep-alive <20> <> )
if ( setsockopt ( socket , IPPROTO_TCP , TCP_KEEPIDLE , & nKeepAliveSec , sizeof ( nKeepAliveSec ) ) < 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Failed to set TCP_KEEPIDLE \n " ) ;
2025-04-06 19:35:20 +08:00
return FALSE ;
}
// <20> <> <EFBFBD> <EFBFBD> TCP_KEEPINTVL (5<> <35> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Լ<EFBFBD> <D4BC> <EFBFBD> )
int keepAliveInterval = 5 ; // 5<> <35>
if ( setsockopt ( socket , IPPROTO_TCP , TCP_KEEPINTVL , & keepAliveInterval , sizeof ( keepAliveInterval ) ) < 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Failed to set TCP_KEEPINTVL \n " ) ;
2025-04-06 19:35:20 +08:00
return FALSE ;
}
// <20> <> <EFBFBD> <EFBFBD> TCP_KEEPCNT (<28> <> <EFBFBD> <EFBFBD> 5<EFBFBD> <35> ̽<EFBFBD> <CCBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ϊ<EFBFBD> <CEAA> <EFBFBD> ӶϿ<D3B6> )
int keepAliveProbes = 5 ;
if ( setsockopt ( socket , IPPROTO_TCP , TCP_KEEPCNT , & keepAliveProbes , sizeof ( keepAliveProbes ) ) < 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Failed to set TCP_KEEPCNT \n " ) ;
2025-04-06 19:35:20 +08:00
return FALSE ;
}
2025-04-27 01:16:16 +08:00
Mprintf ( " TCP keep-alive settings applied successfully \n " ) ;
2025-04-06 19:35:20 +08:00
return TRUE ;
}
# endif
VOID IOCPClient : : setManagerCallBack ( void * Manager , DataProcessCB dataProcess )
2019-01-05 20:21:43 +08:00
{
m_Manager = Manager ;
2025-04-06 19:35:20 +08:00
m_DataProcess = dataProcess ;
2019-01-05 20:21:43 +08:00
}
2025-04-15 21:37:01 +08:00
IOCPClient : : IOCPClient ( State & bExit , bool exit_while_disconnect ) : g_bExit ( bExit )
2019-01-05 20:21:43 +08:00
{
2025-06-15 04:55:14 +08:00
m_nHostPort = 0 ;
2019-01-15 21:48:37 +08:00
m_Manager = NULL ;
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
WSADATA wsaData ;
WSAStartup ( MAKEWORD ( 2 , 2 ) , & wsaData ) ;
2025-04-06 19:35:20 +08:00
# endif
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
m_sClientSocket = INVALID_SOCKET ;
m_hWorkThread = NULL ;
m_bWorkThread = S_STOP ;
2019-01-17 11:58:26 +08:00
memset ( m_szPacketFlag , 0 , sizeof ( m_szPacketFlag ) ) ;
2019-01-05 20:21:43 +08:00
memcpy ( m_szPacketFlag , " Shine " , FLAG_LENGTH ) ;
m_bIsRunning = TRUE ;
m_bConnected = FALSE ;
m_exit_while_disconnect = exit_while_disconnect ;
2025-02-07 18:59:15 +08:00
# if USING_CTX
m_Cctx = ZSTD_createCCtx ( ) ;
m_Dctx = ZSTD_createDCtx ( ) ;
ZSTD_CCtx_setParameter ( m_Cctx , ZSTD_c_compressionLevel , ZSTD_CLEVEL ) ;
# endif
2019-01-05 20:21:43 +08:00
}
IOCPClient : : ~ IOCPClient ( )
{
m_bIsRunning = FALSE ;
if ( m_sClientSocket ! = INVALID_SOCKET )
{
closesocket ( m_sClientSocket ) ;
m_sClientSocket = INVALID_SOCKET ;
}
if ( m_hWorkThread ! = NULL )
{
CloseHandle ( m_hWorkThread ) ;
m_hWorkThread = NULL ;
}
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
WSACleanup ( ) ;
2025-04-06 19:35:20 +08:00
# endif
2019-01-05 20:21:43 +08:00
while ( S_RUN = = m_bWorkThread )
Sleep ( 10 ) ;
m_bWorkThread = S_END ;
2025-02-07 18:59:15 +08:00
# if USING_CTX
ZSTD_freeCCtx ( m_Cctx ) ;
ZSTD_freeDCtx ( m_Dctx ) ;
# endif
2019-01-05 20:21:43 +08:00
}
2019-05-07 20:27:02 +08:00
// <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ȡIP<49> <50> ַ
2025-06-15 04:55:14 +08:00
std : : string GetIPAddress ( const char * hostName )
2019-05-07 20:27:02 +08:00
{
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2025-06-15 04:55:14 +08:00
struct sockaddr_in sa = { 0 } ;
if ( inet_pton ( AF_INET , hostName , & ( sa . sin_addr ) ) = = 1 ) {
return hostName ;
}
2019-05-07 20:27:02 +08:00
struct hostent * host = gethostbyname ( hostName ) ;
2019-05-08 11:47:55 +08:00
# ifdef _DEBUG
2025-06-15 04:55:14 +08:00
if ( host = = NULL ) return " " ;
2025-01-15 18:49:15 +08:00
Mprintf ( " <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> IP<EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ϊ: %s.\n " , host - > h_addrtype = = AF_INET ? " IPV4 " : " IPV6 " ) ;
2019-05-08 11:47:55 +08:00
for ( int i = 0 ; host - > h_addr_list [ i ] ; + + i )
2025-01-15 18:49:15 +08:00
Mprintf ( " <EFBFBD> <EFBFBD> ȡ<EFBFBD> ĵ<EFBFBD> %d<> <64> IP: %s\n " , i + 1 , inet_ntoa ( * ( struct in_addr * ) host - > h_addr_list [ i ] ) ) ;
2019-05-08 11:47:55 +08:00
# endif
2024-12-27 01:40:40 +08:00
if ( host = = NULL | | host - > h_addr_list = = NULL )
return " " ;
return host - > h_addr_list [ 0 ] ? inet_ntoa ( * ( struct in_addr * ) host - > h_addr_list [ 0 ] ) : " " ;
2025-04-06 19:35:20 +08:00
# else
struct addrinfo hints , * res ;
memset ( & hints , 0 , sizeof ( hints ) ) ;
hints . ai_family = AF_INET ; // IPv4
hints . ai_socktype = SOCK_STREAM ; // TCP socket
int status = getaddrinfo ( hostName , nullptr , & hints , & res ) ;
if ( status ! = 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " getaddrinfo failed: %s \n " , gai_strerror ( status ) ) ;
2025-04-06 19:35:20 +08:00
return " " ;
}
struct sockaddr_in * addr = reinterpret_cast < struct sockaddr_in * > ( res - > ai_addr ) ;
char ip [ INET_ADDRSTRLEN ] ;
inet_ntop ( AF_INET , & ( addr - > sin_addr ) , ip , sizeof ( ip ) ) ;
2025-04-27 01:16:16 +08:00
Mprintf ( " IP Address: %s \n " , ip ) ;
2025-04-06 19:35:20 +08:00
freeaddrinfo ( res ) ; // <20> <> Ҫ<EFBFBD> <D2AA> <EFBFBD> <EFBFBD> <EFBFBD> ͷŵ<CDB7> ַ<EFBFBD> <D6B7> Ϣ
return ip ;
# endif
2019-05-07 20:27:02 +08:00
}
2024-12-28 18:35:34 +08:00
BOOL IOCPClient : : ConnectServer ( const char * szServerIP , unsigned short uPort )
2019-01-05 20:21:43 +08:00
{
2025-06-15 04:55:14 +08:00
if ( szServerIP ! = NULL & & uPort ! = 0 ) {
SetServerAddress ( szServerIP , uPort ) ;
}
m_sCurIP = m_Domain . SelectIP ( ) ;
unsigned short port = m_nHostPort ;
2019-01-05 20:21:43 +08:00
m_sClientSocket = socket ( AF_INET , SOCK_STREAM , IPPROTO_TCP ) ; //<2F> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
if ( m_sClientSocket = = SOCKET_ERROR )
{
return FALSE ;
}
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
//<2F> <> <EFBFBD> <EFBFBD> sockaddr_in<69> ṹ Ҳ<> <D2B2> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ض˵Ľṹ
sockaddr_in ServerAddr ;
ServerAddr . sin_family = AF_INET ; //<2F> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> IP
2025-06-15 04:55:14 +08:00
ServerAddr . sin_port = htons ( port ) ;
ServerAddr . sin_addr . S_un . S_addr = inet_addr ( m_sCurIP . c_str ( ) ) ;
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
if ( connect ( m_sClientSocket , ( SOCKADDR * ) & ServerAddr , sizeof ( sockaddr_in ) ) = = SOCKET_ERROR )
{
if ( m_sClientSocket ! = INVALID_SOCKET )
{
closesocket ( m_sClientSocket ) ;
m_sClientSocket = INVALID_SOCKET ;
}
return FALSE ;
}
2025-04-06 19:35:20 +08:00
# else
sockaddr_in ServerAddr = { } ;
ServerAddr . sin_family = AF_INET ; // <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> IP
2025-06-15 04:55:14 +08:00
ServerAddr . sin_port = htons ( port ) ;
2025-04-06 19:35:20 +08:00
// <20> <> szServerIP<49> <50> <EFBFBD> <EFBFBD> <EFBFBD> ֿ<EFBFBD> ͷ<EFBFBD> <CDB7> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ϊ<EFBFBD> <CEAA> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> IPת<50> <D7AA>
// ʹ <> <CAB9> inet_pton <20> <> <EFBFBD> <EFBFBD> inet_addr (inet_pton <20> <> <EFBFBD> <EFBFBD> ֧<EFBFBD> <D6A7> IPv4 <20> <> IPv6)
2025-06-15 04:55:14 +08:00
if ( inet_pton ( AF_INET , m_sCurIP . c_str ( ) , & ServerAddr . sin_addr ) < = 0 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Invalid address or address not supported \n " ) ;
2025-04-06 19:35:20 +08:00
return false ;
}
// <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <D7BD> <EFBFBD>
m_sClientSocket = socket ( AF_INET , SOCK_STREAM , 0 ) ;
if ( m_sClientSocket = = - 1 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Failed to create socket \n " ) ;
2025-04-06 19:35:20 +08:00
return false ;
}
// <20> <> <EFBFBD> ӵ<EFBFBD> <D3B5> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
if ( connect ( m_sClientSocket , ( struct sockaddr * ) & ServerAddr , sizeof ( ServerAddr ) ) = = - 1 ) {
2025-04-27 01:16:16 +08:00
Mprintf ( " Connection failed \n " ) ;
2025-04-06 19:35:20 +08:00
close ( m_sClientSocket ) ;
m_sClientSocket = - 1 ; // <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <D7BD> <EFBFBD> <EFBFBD> <EFBFBD> Ч
return false ;
}
# endif
2019-01-05 20:21:43 +08:00
const int chOpt = 1 ; // True
// Set KeepAlive <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> , <20> <> ֹ<EFBFBD> <D6B9> <EFBFBD> <EFBFBD> <EFBFBD> ˲<EFBFBD> <CBB2> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
if ( setsockopt ( m_sClientSocket , SOL_SOCKET , SO_KEEPALIVE ,
( char * ) & chOpt , sizeof ( chOpt ) ) = = 0 )
{
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
// <20> <> <EFBFBD> ó<EFBFBD> ʱ<EFBFBD> <CAB1> ϸ<EFBFBD> <CFB8> Ϣ
tcp_keepalive klive ;
klive . onoff = 1 ; // <20> <> <EFBFBD> ñ<EFBFBD> <C3B1> <EFBFBD>
klive . keepalivetime = 1000 * 60 * 3 ; // 3<> <33> <EFBFBD> ӳ<EFBFBD> ʱ Keep Alive
klive . keepaliveinterval = 1000 * 5 ; // <20> <> <EFBFBD> Լ<EFBFBD> <D4BC> <EFBFBD> Ϊ5<CEAA> <35> Resend if No-Reply
WSAIoctl ( m_sClientSocket , SIO_KEEPALIVE_VALS , & klive , sizeof ( tcp_keepalive ) ,
NULL , 0 , ( unsigned long * ) & chOpt , 0 , NULL ) ;
2025-04-06 19:35:20 +08:00
# else
// <20> <> <EFBFBD> ñ<EFBFBD> <C3B1> <EFBFBD> ѡ <EFBFBD> <D1A1>
SetKeepAliveOptions ( m_sClientSocket ) ;
# endif
2019-01-05 20:21:43 +08:00
}
if ( m_hWorkThread = = NULL ) {
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2025-05-03 20:33:40 +08:00
m_hWorkThread = ( HANDLE ) CreateThread ( NULL , 0 , WorkThreadProc , ( LPVOID ) this , 0 , NULL ) ;
2019-01-05 20:21:43 +08:00
m_bWorkThread = m_hWorkThread ? S_RUN : S_STOP ;
2025-04-06 19:35:20 +08:00
# else
pthread_t id = 0 ;
m_hWorkThread = ( HANDLE ) pthread_create ( & id , nullptr , ( void * ( * ) ( void * ) ) IOCPClient : : WorkThreadProc , this ) ;
# endif
2019-01-05 20:21:43 +08:00
}
2025-01-15 18:49:15 +08:00
Mprintf ( " <EFBFBD> <EFBFBD> <EFBFBD> ӷ<EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ˳ɹ<EFBFBD> .\n " ) ;
2019-01-05 20:21:43 +08:00
m_bConnected = TRUE ;
return TRUE ;
}
DWORD WINAPI IOCPClient : : WorkThreadProc ( LPVOID lParam )
{
IOCPClient * This = ( IOCPClient * ) lParam ;
2024-12-27 01:40:40 +08:00
char * szBuffer = new char [ MAX_RECV_BUFFER ] ;
2019-01-05 20:21:43 +08:00
fd_set fd ;
2025-04-06 19:35:20 +08:00
struct timeval tm = { 2 , 0 } ;
2025-05-03 20:33:40 +08:00
This - > m_CompressedBuffer . ClearBuffer ( ) ;
2019-01-05 20:21:43 +08:00
while ( This - > IsRunning ( ) ) // û<> <C3BB> <EFBFBD> ˳<EFBFBD> <CBB3> <EFBFBD> <EFBFBD> <EFBFBD> һ ֱ<D2BB> <D6B1> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ѭ<EFBFBD> <D1AD> <EFBFBD> <EFBFBD>
{
if ( ! This - > IsConnected ( ) )
{
Sleep ( 50 ) ;
continue ;
}
FD_ZERO ( & fd ) ;
FD_SET ( This - > m_sClientSocket , & fd ) ;
2025-04-06 19:35:20 +08:00
# ifdef _WIN32
2019-01-05 20:21:43 +08:00
int iRet = select ( NULL , & fd , NULL , NULL , & tm ) ;
2025-04-06 19:35:20 +08:00
# else
int iRet = select ( This - > m_sClientSocket + 1 , & fd , NULL , NULL , & tm ) ;
# endif
2019-01-05 20:21:43 +08:00
if ( iRet < = 0 )
{
if ( iRet = = 0 ) Sleep ( 50 ) ;
else
{
2025-01-15 18:49:15 +08:00
Mprintf ( " [select] return %d, GetLastError= %d. \n " , iRet , WSAGetLastError ( ) ) ;
2019-01-05 20:21:43 +08:00
This - > Disconnect ( ) ; //<2F> <> <EFBFBD> մ<EFBFBD> <D5B4> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
2025-05-03 20:33:40 +08:00
This - > m_CompressedBuffer . ClearBuffer ( ) ;
2019-01-05 20:21:43 +08:00
if ( This - > m_exit_while_disconnect )
break ;
}
}
else if ( iRet > 0 )
{
2025-05-03 20:33:40 +08:00
int iReceivedLength = recv ( This - > m_sClientSocket , szBuffer , MAX_RECV_BUFFER - 1 , 0 ) ;
2019-01-05 20:21:43 +08:00
if ( iReceivedLength < = 0 )
{
2025-04-06 19:35:20 +08:00
int a = WSAGetLastError ( ) ;
2019-01-05 20:21:43 +08:00
This - > Disconnect ( ) ; //<2F> <> <EFBFBD> մ<EFBFBD> <D5B4> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
2025-05-03 20:33:40 +08:00
This - > m_CompressedBuffer . ClearBuffer ( ) ;
2019-01-05 20:21:43 +08:00
if ( This - > m_exit_while_disconnect )
break ;
} else {
2025-05-03 20:33:40 +08:00
szBuffer [ iReceivedLength ] = 0 ;
2019-01-05 20:21:43 +08:00
//<2F> <> ȷ<EFBFBD> <C8B7> <EFBFBD> վ͵<D5BE> <CDB5> <EFBFBD> OnRead<61> <64> <EFBFBD> <EFBFBD> ,ת<> <D7AA> OnRead
2019-01-10 19:35:03 +08:00
This - > OnServerReceiving ( szBuffer , iReceivedLength ) ;
2019-01-05 20:21:43 +08:00
}
}
}
2025-04-27 01:16:16 +08:00
CloseHandle ( This - > m_hWorkThread ) ;
This - > m_hWorkThread = NULL ;
2019-01-05 20:21:43 +08:00
This - > m_bWorkThread = S_STOP ;
This - > m_bIsRunning = FALSE ;
2024-12-27 01:40:40 +08:00
delete [ ] szBuffer ;
2019-01-05 20:21:43 +08:00
return 0xDEAD ;
}
VOID IOCPClient : : OnServerReceiving ( char * szBuffer , ULONG ulLength )
{
try
{
assert ( ulLength > 0 ) ;
//<2F> <> <EFBFBD> ½ӵ<C2BD> <D3B5> <EFBFBD> <EFBFBD> ݽ<EFBFBD> <DDBD> н<EFBFBD> ѹ<EFBFBD> <D1B9>
m_CompressedBuffer . WriteBuffer ( ( LPBYTE ) szBuffer , ulLength ) ;
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
//<2F> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ƿ<EFBFBD> <C7B7> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ͷ<EFBFBD> <CDB7> С <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ǾͲ<C7BE> <CDB2> <EFBFBD> <EFBFBD> <EFBFBD> ȷ<EFBFBD> <C8B7> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD>
while ( m_CompressedBuffer . GetBufferLength ( ) > HDR_LENGTH )
{
2019-01-17 11:58:26 +08:00
char szPacketFlag [ FLAG_LENGTH + 3 ] = { 0 } ;
2024-12-28 17:14:31 +08:00
LPBYTE src = m_CompressedBuffer . GetBuffer ( ) ;
CopyMemory ( szPacketFlag , src , FLAG_LENGTH ) ;
2019-01-05 20:21:43 +08:00
//<2F> ж<EFBFBD> <D0B6> <EFBFBD> <EFBFBD> <EFBFBD> ͷ
if ( memcmp ( m_szPacketFlag , szPacketFlag , FLAG_LENGTH ) ! = 0 )
{
2025-04-27 01:16:16 +08:00
Mprintf ( " [ERROR] OnServerReceiving memcmp fail: unknown header '%s' \n " , szPacketFlag ) ;
m_CompressedBuffer . ClearBuffer ( ) ;
break ;
2019-01-05 20:21:43 +08:00
}
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
ULONG ulPackTotalLength = 0 ;
2025-04-27 01:16:16 +08:00
CopyMemory ( & ulPackTotalLength , m_CompressedBuffer . GetBuffer ( FLAG_LENGTH ) , sizeof ( ULONG ) ) ;
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
//--- <20> <> <EFBFBD> ݵĴ<DDB5> С <EFBFBD> <D0A1> ȷ<EFBFBD> ж<EFBFBD>
2024-12-28 17:14:31 +08:00
ULONG len = m_CompressedBuffer . GetBufferLength ( ) ;
if ( ulPackTotalLength & & len > = ulPackTotalLength )
2019-01-05 20:21:43 +08:00
{
2025-04-27 01:16:16 +08:00
ULONG ulOriginalLength = 0 ;
2019-01-05 20:21:43 +08:00
2025-04-27 01:16:16 +08:00
m_CompressedBuffer . ReadBuffer ( ( PBYTE ) szPacketFlag , FLAG_LENGTH ) ; //<2F> <> ȡ<EFBFBD> <C8A1> <EFBFBD> <EFBFBD> ͷ<EFBFBD> <CDB7> shine
2019-01-10 19:35:03 +08:00
m_CompressedBuffer . ReadBuffer ( ( PBYTE ) & ulPackTotalLength , sizeof ( ULONG ) ) ;
m_CompressedBuffer . ReadBuffer ( ( PBYTE ) & ulOriginalLength , sizeof ( ULONG ) ) ;
2019-01-05 20:21:43 +08:00
2019-01-10 19:35:03 +08:00
ULONG ulCompressedLength = ulPackTotalLength - HDR_LENGTH ;
2025-04-27 01:16:16 +08:00
const int bufSize = 512 ;
BYTE buf1 [ bufSize ] , buf2 [ bufSize ] ;
PBYTE CompressedBuffer = ulCompressedLength > bufSize ? new BYTE [ ulCompressedLength ] : buf1 ;
PBYTE DeCompressedBuffer = ulCompressedLength > bufSize ? new BYTE [ ulOriginalLength ] : buf2 ;
2019-01-10 19:35:03 +08:00
2019-01-05 20:21:43 +08:00
m_CompressedBuffer . ReadBuffer ( CompressedBuffer , ulCompressedLength ) ;
2019-01-10 19:35:03 +08:00
2025-04-27 01:16:16 +08:00
size_t iRet = uncompress ( DeCompressedBuffer , & ulOriginalLength , CompressedBuffer , ulCompressedLength ) ;
2019-01-10 19:35:03 +08:00
2019-01-17 11:58:26 +08:00
if ( Z_SUCCESS ( iRet ) ) //<2F> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ѹ<EFBFBD> ɹ<EFBFBD>
2019-01-05 20:21:43 +08:00
{
//<2F> <> ѹ<EFBFBD> õ<EFBFBD> <C3B5> <EFBFBD> <EFBFBD> ݺͳ<DDBA> <CDB3> ȴ<EFBFBD> <C8B4> ݸ<EFBFBD> <DDB8> <EFBFBD> <EFBFBD> <EFBFBD> Manager<65> <72> <EFBFBD> д<EFBFBD> <D0B4> <EFBFBD> ע<> <D7A2> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ˶<EFBFBD> ̬
//<2F> <> <EFBFBD> <EFBFBD> m_pManager<65> е <EFBFBD> <D0B5> <EFBFBD> <EFBFBD> һ <E0B2BB> <D2BB> <EFBFBD> <EFBFBD> <EFBFBD> ɵ<EFBFBD> <C9B5> õ<EFBFBD> OnReceive<76> <65> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> һ <EFBFBD> <D2BB>
2025-04-06 19:35:20 +08:00
if ( m_DataProcess )
2025-04-27 01:16:16 +08:00
m_DataProcess ( m_Manager , ( PBYTE ) DeCompressedBuffer , ulOriginalLength ) ;
2019-01-05 20:21:43 +08:00
}
2019-01-17 11:58:26 +08:00
else {
2025-01-15 18:49:15 +08:00
Mprintf ( " [ERROR] uncompress fail: dstLen %d, srcLen %d \n " , ulOriginalLength , ulCompressedLength ) ;
2025-04-27 01:16:16 +08:00
m_CompressedBuffer . ClearBuffer ( ) ;
2019-01-17 11:58:26 +08:00
}
2019-01-10 19:35:03 +08:00
2025-04-27 01:16:16 +08:00
if ( CompressedBuffer ! = buf1 ) delete [ ] CompressedBuffer ;
if ( DeCompressedBuffer ! = buf2 ) delete [ ] DeCompressedBuffer ;
2019-01-05 20:21:43 +08:00
}
2024-12-28 17:14:31 +08:00
else {
2025-04-27 01:16:16 +08:00
break ; // received data is incomplete
2024-12-28 17:14:31 +08:00
}
2019-01-05 20:21:43 +08:00
}
2021-03-14 20:55:22 +08:00
} catch ( . . . ) {
2024-12-28 17:14:31 +08:00
m_CompressedBuffer . ClearBuffer ( ) ;
2025-01-15 18:49:15 +08:00
Mprintf ( " [ERROR] OnServerReceiving catch an error \n " ) ;
2021-03-14 20:55:22 +08:00
}
2019-01-05 20:21:43 +08:00
}
2019-09-07 10:47:50 +08:00
// <20> <> server<65> <72> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ݣ<EFBFBD> ѹ<EFBFBD> <D1B9> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ȽϺ <C8BD> ʱ<EFBFBD> <CAB1>
// <20> ر<EFBFBD> ѹ<EFBFBD> <D1B9> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ʱ<EFBFBD> <CAB1> SendWithSplit<69> ȽϺ <C8BD> ʱ<EFBFBD> <CAB1>
2019-01-18 17:37:15 +08:00
BOOL IOCPClient : : OnServerSending ( const char * szBuffer , ULONG ulOriginalLength ) //Hello
2019-01-05 20:21:43 +08:00
{
2019-05-11 11:28:58 +08:00
AUTO_TICK ( 50 ) ;
2019-01-10 19:35:03 +08:00
assert ( ulOriginalLength > 0 ) ;
2019-01-05 20:21:43 +08:00
{
2019-01-10 19:35:03 +08:00
//<2F> <> <EFBFBD> <EFBFBD> 1.001<EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> Ҳ<EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ѹ<EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ռ <EFBFBD> õ<EFBFBD> <EFBFBD> ڴ<EFBFBD> <EFBFBD> ռ <EFBFBD> <EFBFBD> <EFBFBD> ԭ<EFBFBD> <EFBFBD> һ <EFBFBD> <EFBFBD> +12
2019-01-05 20:21:43 +08:00
//<2F> <> ֹ<EFBFBD> <D6B9> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> // HelloWorld 10 22
//<2F> <> <EFBFBD> <EFBFBD> ѹ<EFBFBD> <D1B9> ѹ<> <D1B9> <EFBFBD> 㷨 <> <CEA2> <EFBFBD> ṩ
//nSize = 436
2019-01-10 19:35:03 +08:00
//destLen = 448
2019-01-17 11:58:26 +08:00
# if USING_ZLIB
2019-01-10 19:35:03 +08:00
unsigned long ulCompressedLength = ( double ) ulOriginalLength * 1.001 + 12 ;
2019-01-17 20:41:51 +08:00
# elif USING_LZ4
unsigned long ulCompressedLength = LZ4_compressBound ( ulOriginalLength ) ;
2019-01-17 11:58:26 +08:00
# else
unsigned long ulCompressedLength = ZSTD_compressBound ( ulOriginalLength ) ;
# endif
2025-04-27 01:16:16 +08:00
BYTE buf [ 1024 ] ;
LPBYTE CompressedBuffer = ulCompressedLength > 1024 ? new BYTE [ ulCompressedLength ] : buf ;
2019-01-05 20:21:43 +08:00
2019-01-10 19:35:03 +08:00
int iRet = compress ( CompressedBuffer , & ulCompressedLength , ( PBYTE ) szBuffer , ulOriginalLength ) ;
2019-01-17 11:58:26 +08:00
if ( Z_FAILED ( iRet ) )
2019-01-05 20:21:43 +08:00
{
2025-04-27 01:16:16 +08:00
Mprintf ( " [ERROR] compress failed: srcLen %d, dstLen %d \n " , ulOriginalLength , ulCompressedLength ) ;
if ( CompressedBuffer ! = buf ) delete [ ] CompressedBuffer ;
2019-01-05 20:21:43 +08:00
return FALSE ;
}
2019-01-17 11:58:26 +08:00
# if !USING_ZLIB
ulCompressedLength = iRet ;
# endif
2019-01-10 19:35:03 +08:00
ULONG ulPackTotalLength = ulCompressedLength + HDR_LENGTH ;
CBuffer m_WriteBuffer ;
2019-01-17 11:58:26 +08:00
m_WriteBuffer . WriteBuffer ( ( PBYTE ) m_szPacketFlag , FLAG_LENGTH ) ;
2019-01-05 20:21:43 +08:00
2019-01-10 19:35:03 +08:00
m_WriteBuffer . WriteBuffer ( ( PBYTE ) & ulPackTotalLength , sizeof ( ULONG ) ) ;
2025-04-27 01:16:16 +08:00
2019-01-10 19:35:03 +08:00
m_WriteBuffer . WriteBuffer ( ( PBYTE ) & ulOriginalLength , sizeof ( ULONG ) ) ;
2025-04-27 01:16:16 +08:00
2019-01-10 19:35:03 +08:00
m_WriteBuffer . WriteBuffer ( CompressedBuffer , ulCompressedLength ) ;
2025-04-27 01:16:16 +08:00
if ( CompressedBuffer ! = buf ) delete [ ] CompressedBuffer ;
2019-09-07 10:47:50 +08:00
2019-01-10 19:35:03 +08:00
// <20> ֿ鷢<D6BF> <E9B7A2>
2025-04-27 01:16:16 +08:00
return SendWithSplit ( ( char * ) m_WriteBuffer . GetBuffer ( ) , m_WriteBuffer . GetBufferLength ( ) , MAX_SEND_BUFFER ) ;
2019-01-05 20:21:43 +08:00
}
}
// 5 2 // 2 2 1
2019-01-10 19:35:03 +08:00
BOOL IOCPClient : : SendWithSplit ( const char * szBuffer , ULONG ulLength , ULONG ulSplitLength )
2019-01-05 20:21:43 +08:00
{
2019-09-07 10:47:50 +08:00
AUTO_TICK ( 25 ) ;
2019-01-05 20:21:43 +08:00
int iReturn = 0 ; //<2F> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> ˶<EFBFBD> <CBB6> <EFBFBD>
2019-01-10 19:35:03 +08:00
const char * Travel = szBuffer ;
2019-01-05 20:21:43 +08:00
int i = 0 ;
2019-01-10 19:35:03 +08:00
int ulSended = 0 ;
const int ulSendRetry = 15 ;
2019-01-05 20:21:43 +08:00
// <20> <> <EFBFBD> η<EFBFBD> <CEB7> <EFBFBD>
for ( i = ulLength ; i > = ulSplitLength ; i - = ulSplitLength )
{
int j = 0 ;
2019-01-10 19:35:03 +08:00
for ( ; j < ulSendRetry ; + + j )
{
iReturn = send ( m_sClientSocket , Travel , ulSplitLength , 0 ) ;
2019-01-05 20:21:43 +08:00
if ( iReturn > 0 )
{
break ;
}
}
if ( j = = ulSendRetry )
{
return FALSE ;
}
2019-01-10 19:35:03 +08:00
ulSended + = iReturn ;
Travel + = ulSplitLength ;
2019-01-05 20:21:43 +08:00
}
// <20> <> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> <EFBFBD> IJ<EFBFBD> <C4B2> <EFBFBD>
if ( i > 0 ) //1024
{
int j = 0 ;
2019-01-10 19:35:03 +08:00
for ( ; j < ulSendRetry ; j + + )
2019-01-05 20:21:43 +08:00
{
iReturn = send ( m_sClientSocket , ( char * ) Travel , i , 0 ) ;
if ( iReturn > 0 )
{
break ;
}
}
if ( j = = ulSendRetry )
{
return FALSE ;
}
2019-01-10 19:35:03 +08:00
ulSended + = iReturn ;
2019-01-05 20:21:43 +08:00
}
2019-01-10 19:35:03 +08:00
return ( ulSended = = ulLength ) ? TRUE : FALSE ;
2019-01-05 20:21:43 +08:00
}
VOID IOCPClient : : Disconnect ( )
{
2025-05-03 20:33:40 +08:00
if ( m_sClientSocket = = INVALID_SOCKET )
return ;
2025-06-26 02:07:00 +08:00
Mprintf ( " Disconnect with [%s:%d]. \n " , m_sCurIP . c_str ( ) , m_nHostPort ) ;
2019-01-05 20:21:43 +08:00
CancelIo ( ( HANDLE ) m_sClientSocket ) ;
closesocket ( m_sClientSocket ) ;
m_sClientSocket = INVALID_SOCKET ;
m_bConnected = FALSE ;
}
2019-01-12 18:21:42 +08:00
VOID IOCPClient : : RunEventLoop ( const BOOL & bCondition )
2019-01-05 20:21:43 +08:00
{
2025-04-27 01:16:16 +08:00
Mprintf ( " ======> RunEventLoop begin \n " ) ;
2025-06-26 02:07:00 +08:00
while ( ( m_bIsRunning & & bCondition ) | | bCondition = = FOREVER_RUN )
2019-01-12 18:21:42 +08:00
Sleep ( 200 ) ;
2025-06-20 04:26:55 +08:00
setManagerCallBack ( NULL , NULL ) ;
2025-04-27 01:16:16 +08:00
Mprintf ( " ======> RunEventLoop end \n " ) ;
2019-01-05 20:21:43 +08:00
}