34 virtual void *
get()
const = 0;
36 template <
typename _Ty >
37 _Ty *
get()
const {
return reinterpret_cast<_Ty *
>( this->
get() ); }
118 protoUnspec = 0, protoIp = 0,
121 protoIpip, protoIpv4 = protoIpip,
149 #if defined(_MSC_VER) || defined(WIN32) 158 static int const MsgOob;
159 static int const MsgPeek;
160 static int const MsgDontRoute;
163 static int const MsgTryHard;
165 static int const MsgCTrunc;
166 static int const MsgProxy;
167 static int const MsgTrunc;
168 static int const MsgDontWait;
169 static int const MsgEor;
170 static int const MsgWaitAll;
171 static int const MsgFin;
172 static int const MsgSyn;
173 static int const MsgConfirm;
174 static int const MsgRst;
175 static int const MsgErrQueue;
176 static int const MsgNoSignal;
177 static int const MsgMore;
178 static int const MsgWaitForOne;
179 static int const MsgCMsgCloexec;
195 explicit Socket(
int sock = -1,
bool isNewSock =
false );
200 #ifndef MOVE_SEMANTICS_DISABLED 225 int shutdown(
int how = SdSend );
228 int send(
void const * data,
size_t size,
int msgFlags = MsgDefault );
237 bool sendUntil(
size_t targetSize,
void const * data,
int msgFlags = MsgDefault );
255 FunctionSuccessCallback eachSuccessCallback = FunctionSuccessCallback(),
256 void * param =
nullptr,
257 int msgFlags = MsgDefault
265 FunctionSuccessCallback eachSuccessCallback = FunctionSuccessCallback(),
266 void * param =
nullptr,
267 int msgFlags = MsgDefault
268 ) {
return this->sendWaitUntil( data.size(), data.c_str(), hadSent, sec, rcWait, std::move(eachSuccessCallback), param, msgFlags ); }
275 FunctionSuccessCallback eachSuccessCallback = FunctionSuccessCallback(),
276 void * param =
nullptr,
277 int msgFlags = MsgDefault
278 ) {
return this->sendWaitUntil( data.
getSize(), data.
getBuf(), hadSent, sec, rcWait, std::move(eachSuccessCallback), param, msgFlags ); }
281 template <
typename _PodType,
size_t _N = sizeof(_PodType) >
282 bool sendUntilType( _PodType
const & v,
int msgFlags = MsgDefault ) {
return this->sendUntil( _N, &v, msgFlags ); }
285 int recv(
void * buf,
size_t size,
int msgFlags = MsgDefault );
293 winux::Buffer recv(
size_t size,
int msgFlags = MsgDefault );
309 int recvWaitUntilTarget(
318 FunctionSuccessCallback eachSuccessCallback = FunctionSuccessCallback(),
319 void * param =
nullptr,
320 int msgFlags = MsgDefault
326 bool recvUntilSize(
size_t targetSize,
winux::GrowBuffer * data,
int msgFlags = MsgDefault );
336 int recvWaitUntilSize(
342 FunctionSuccessCallback eachSuccessCallback = FunctionSuccessCallback(),
343 void * param =
nullptr,
344 int msgFlags = MsgDefault
348 template <
typename _PodType,
size_t _N = sizeof(_PodType) >
352 data.
setBuf( v, 0, _N,
true );
353 return this->recvUntilSize( _N, &data, msgFlags );
372 winux::Buffer recvWaitAvail(
double sec,
int * rcWait,
int msgFlags = MsgDefault );
375 int sendTo(
EndPoint const & ep,
void const * data,
size_t size,
int msgFlags = MsgDefault );
384 int recvFrom(
EndPoint * ep,
void * buf,
size_t size,
int msgFlags = MsgDefault );
395 bool connect(
EndPoint const & ep );
401 bool listen(
int backlog );
406 bool accept(
int * sock,
EndPoint * ep = NULL );
418 int getRecvBufSize()
const;
420 bool setRecvBufSize(
int optval );
423 int getSendBufSize()
const;
425 bool setSendBufSize(
int optval );
440 bool getReUseAddr()
const;
442 bool setReUseAddr(
bool optval );
445 bool getBroadcast()
const;
447 bool setBroadcast(
bool optval );
450 int getError()
const;
458 bool isListening()
const;
463 int getAvailable()
const;
466 bool setBlocking(
bool blocking );
474 operator bool()
const {
return this->
get() > -1; }
510 this->extraData.
free();
519 this->targetBytes = 0;
520 this->retryCount = 0;
526 this->data.append(data);
532 template <
typename _IndexType >
538 if ( this->data.
getSize() >= target.size() ) this->startpos = this->data.
getSize() - target.size() + 1;
551 size_t searchedDataSize = this->pos + target.
size();
554 this->extraData.
append( this->data.
getBuf<
char>() + searchedDataSize, this->data.getSize() - searchedDataSize );
555 this->data.
_setSize(searchedDataSize);
560 this->data = std::move(extraData);
574 std::ios_base::openmode mode = std::ios_base::in | std::ios_base::out,
575 size_t inputBufSize = (
size_t)-1,
576 size_t outputBufSize = (
size_t)-1
584 virtual int_type underflow();
589 virtual int_type overflow( int_type c );
630 std::streamsize getAvailable()
const;
636 std::streamsize waitAvail(
double sec );
660 #ifndef MOVE_SEMANTICS_DISABLED 677 virtual void *
get()
const override;
679 template <
typename _Ty >
680 _Ty *
get()
const {
return reinterpret_cast<_Ty *
>( this->
get() ); }
707 EndPointArray::iterator
begin() {
return _epArr.begin(); }
708 EndPointArray::const_iterator
begin()
const {
return _epArr.begin(); }
709 EndPointArray::iterator
end() {
return _epArr.end(); }
710 EndPointArray::const_iterator
end()
const {
return _epArr.end(); }
713 size_t count()
const {
return _epArr.size(); }
719 EndPointArray::value_type
const & operator [] (
int i )
const {
return _epArr[i]; }
720 EndPointArray::value_type & operator [] (
int i ) {
return _epArr[i]; }
722 EndPointArray &
getArr() {
return _epArr; }
723 EndPointArray
const &
getArr()
const {
return _epArr; }
733 EndPointArray _epArr;
748 explicit Socket(
int sock,
bool isNewSock =
false ) : BaseClass( sock, isNewSock ) { }
751 Socket() : BaseClass( BaseClass::afInet, BaseClass::sockStream, BaseClass::protoUnspec ) { }
753 #ifndef MOVE_SEMANTICS_DISABLED 759 BaseClass::operator = ( std::move(other) );
797 explicit Socket(
int sock,
bool isNewSock =
false ) : BaseClass( sock, isNewSock ) { }
800 Socket() : BaseClass( BaseClass::afInet, BaseClass::sockDatagram, BaseClass::protoUnspec ) { }
802 #ifndef MOVE_SEMANTICS_DISABLED 808 BaseClass::operator = ( std::move(other) );
843 int hasReadFd(
int fd )
const;
849 int wait(
double sec = -1 );
873 int hasWriteFd(
int fd )
const;
879 int wait(
double sec = -1 );
903 int hasExceptFd(
int fd )
const;
909 int wait(
double sec = -1 );
941 Select &
clear() { SelectRead::clear(); SelectWrite::clear(); SelectExcept::clear();
return *
this; }
947 int wait(
double sec = -1 );
995 Server(
bool autoReadData,
ip::EndPoint const & ep,
int threadCount = 4,
int backlog = 0,
double serverWait = 0.002,
double verboseInterval = 0.01,
bool verbose =
true );
1008 bool startup(
bool autoReadData,
ip::EndPoint const & ep,
int threadCount = 4,
int backlog = 0,
double serverWait = 0.002,
double verboseInterval = 0.01,
bool verbose =
true );
1011 virtual int run(
void * runParam );
1014 void stop(
bool b =
true );
1017 size_t getClientsCount()
const;
1026 template <
typename _Fx,
typename... _ArgType >
1031 clientCtxPtr->processingEvent =
true;
1032 this->_pool.task( [routine, clientCtxPtr] () {
1035 clientCtxPtr->processingEvent =
false;
1043 std::map< winux::uint64, winux::SharedPointer<ClientCtx> >
_clients;
1060 ( clientCtxPtr, readableSize )
1067 ( clientCtxPtr,
std::move(data) )
1091 clientEpStr(clientEpStr),
1092 clientSockPtr(clientSockPtr)
1113 template <
class _ClientCtxClass >
1126 _cumulativeClientId(0),
1131 _servSock.setReUseAddr(
true);
1132 _stop = !( _servSock.eiennet::Socket::bind( ep,
Socket::sockStream ) && _servSock.listen(backlog) );
1146 int rc = sel.
wait(0.01);
1152 auto clientSockPtr = _servSock.accept(&clientEp);
1153 if ( clientSockPtr )
1155 auto & clientCtxPtr = this->_addClient( clientEp, clientSockPtr );
1158 this->onStartup(clientCtxPtr);
1173 void stop(
bool b =
true ) {
static_cast<volatile bool &
>(_stop) = b; }
1178 return _clients.size();
1183 _startupHandler = handler;
1189 _clients.erase(clientId);
1198 ++_cumulativeClientId;
1199 client = &_clients[_cumulativeClientId];
1201 client->
attachNew(
new _ClientCtxClass( _cumulativeClientId, clientEp.
toString(), clientSockPtr ) );
1210 std::map< winux::uint64, ClientCtxSharedPointer >
_clients;
1215 if ( this->_startupHandler ) this->_startupHandler(clientCtxPtr);
1229 #endif // __SOCKET_HPP__ XString< char > AnsiString
#define EIENNET_FUNC_DECL(ret)
SelectWrite & setWriteSock(Socket const *sock)
RunableT< _Fx, std::tuple< typename std::decay< _ArgType >::type... > > * NewRunable(_Fx fn, _ArgType &&...arg)
创建一个Runable对象
void stop(bool b=true)
是否停止服务运行
void append(void const *data, size_t size)
添加数据:C语言缓冲区
int hasExceptSock(Socket const &sock) const
winux::GrowBuffer extraData
额外收到的数据
SelectRead & setReadSock(Socket const &sock)
Socket(Socket &&other)
移动构造函数
winux::String clientEpStr
SocketStreamIn(SocketStreamBuf *sockBuf)
void * getBuf() const
暴露缓冲区指针
void whenEmptyStopAndWait()
当任务队列为空,任务链为0,就停止线程池运行,并等待线程组线程正常退出
SocketStreamOut(winux::SimplePointer< SocketStreamBuf > &sockBuf)
winux::uint64 _cumulativeClientId
客户唯一标识
Select & setExceptFd(int fd)
int sendTo(EndPoint const &ep, winux::AnsiString const &data, int msgFlags=MsgDefault)
无连接模式发送数据到指定端点。返回已发送大小,出错返回-1。
int wait(double sec=-1)
等待相应的fd就绪。sec<1表示小于1秒的时间,sec<0表示无限等待。eg: sec=1.5表示等待1500ms ...
winux::SharedPointer< ip::tcp::Socket > clientSockPtr
eiennet::Socket BaseClass
Select & clearExceptFds()
SelectExcept & setExceptSock(Socket const *sock)
std::map< winux::uint64, winux::SharedPointer< ClientCtx > > _clients
客户映射表
int sendWaitUntil(winux::Buffer const &data, size_t *hadSent, double sec, int *rcWait, FunctionSuccessCallback eachSuccessCallback=FunctionSuccessCallback(), void *param=nullptr, int msgFlags=MsgDefault)
winux::String const & getHostname() const
获取主机名
void resetData()
重置数据和额外数据为空
Select & setReadSock(Socket const &sock)
Select & setWriteFd(int fd)
EndPointArray::const_iterator end() const
bool processingEvent
是否事件处理中,保证同一个客户连接仅投递一个事件到线程池中
winux::RecursiveMutex _mtxServer
互斥量保护服务器共享数据
static int const MsgDefault
int get() const
Windows:socket句柄,或Linux:socket描述符
void _postTask(winux::SharedPointer< ClientCtx > clientCtxPtr, _Fx fn, _ArgType &&...arg)
往线程池投递任务
size_t count() const
获取解析到的IP端点数
EndPointArray::iterator begin()
Socket * getSocket() const
winux::ushort getPort() const
获取端口号
int sendTo(EndPoint const &ep, winux::Buffer const &data, int msgFlags=MsgDefault)
无连接模式发送数据到指定端点。返回已发送大小,出错返回-1。
SocketStreamIn(SocketStreamBuf &sockBuf)
Socket(int sock, bool isNewSock=false)
构造函数1,包装现有socket描述符
SocketStreamIn(winux::SimplePointer< SocketStreamBuf > &sockBuf)
winux::MembersWrapper< struct Socket_Data > _self
SelectRead & setReadSock(Socket const *sock)
ClientCtx(winux::uint64 clientId, winux::String clientEpStr, winux::SharedPointer< ip::tcp::Socket > clientSockPtr)
int hasReadSock(Socket const &sock) const
winux::String clientEpStr
客户终端字符串
size_t getSize() const
获取数据大小
#define DISABLE_OBJECT_COPY(clsname)
Select & setWriteSock(Socket const &sock)
Select & delWriteFd(int fd)
double _serverWait
服务器IO等待时间间隔(秒)
static int const MsgDontRoute
Select & delExceptFd(int fd)
winux::uint64 _cumulativeClientId
double _verboseInterval
Verbose信息刷新间隔(秒)
winux::SharedPointer< Socket > accept(EndPoint *ep=NULL)
接受一个客户连接
void removeClient(winux::uint64 clientId)
SocketStreamIn(winux::SharedPointer< SocketStreamBuf > &sockBuf)
bool _servSockAIsListening
servSockA是否处于监听中
std::function< void(size_t hadBytes, void *param) > FunctionSuccessCallback
Select & setReadFds(winux::Mixed const &fds)
Select & setExceptSock(Socket const &sock)
ip::tcp::Socket _servSockB
服务器监听套接字B
int ConnectAttempt(Socket *sock, Resolver const &resolver, winux::uint32 perCnnTimeoutMs)
阻塞模式Socket连接尝试,连接成功返回0,超时返回1,失败返回-1
eiennet::Socket BaseClass
int send(winux::Buffer const &data, int msgFlags=MsgDefault)
发送数据。返回已发送大小,出错返回-1。
winux::SharedPointer< Socket > accept(EndPoint *ep=NULL)
接受一个客户连接
static constexpr size_t const npos
非位置,值为-1。
Socket(Socket &&other)
移动构造函数
void onStartupHandler(StartupHandlerFunction handler)
Select & setReadFd(int fd)
缓冲区,表示内存中一块二进制数据(利用malloc/realloc进行内存分配)
Socket(int sock, bool isNewSock=false)
构造函数1,包装现有socket描述符
winux::MembersWrapper< struct SelectRead_Data > _self
virtual winux::String toString() const override
转换成"IP:port"的字符串形式
size_t getClientsCount() const
EndPointArray::iterator end()
#define DEFINE_CUSTOM_EVENT_RETURN_EX(ret, evtname, paramtypes)
static int const MsgPartial
void _setSize(size_t dataSize)
设置数据大小,不能超过容量大小(不建议外部调用)
SelectExcept & setExceptSock(Socket const &sock)
void setBuf(void const *buf, size_t size, size_t capacity, bool isPeek)
设置缓冲区,当isPeek为false时拷贝数据缓冲区
int hasWriteSock(Socket const &sock) const
bool _servSockBIsListening
servSockB是否处于监听中
Select & setWriteFds(winux::Mixed const &fds)
static size_t _Templ_KmpMatchEx(_ChTy const *str, size_t len, _ChTy const *substr, size_t sublen, size_t pos, std::vector< _IndexType > const &next)
KMP匹配算法:传入已经求好的next进行匹配
winux::Buffer adjust(winux::AnsiString const &target)
data里搜到target内容后,调整data大小,把多余的数据放入extraData,然后返回data,并把extraData移到data...
std::map< winux::uint64, ClientCtxSharedPointer > _clients
线程池,创建一组线程等待着从任务队列中获取任务执行
bool recvUntilType(_PodType *v, int msgFlags=MsgDefault)
接收一个Plain of Data类型的变量,若成功返回true,否则返回false。
SocketStreamOut(winux::SharedPointer< SocketStreamBuf > &sockBuf)
void append(winux::Buffer const &data)
添加数据到data
static int const MsgWaitAll
int sendWaitUntil(winux::AnsiString const &data, size_t *hadSent, double sec, int *rcWait, FunctionSuccessCallback eachSuccessCallback=FunctionSuccessCallback(), void *param=nullptr, int msgFlags=MsgDefault)
virtual void onStartup(ClientCtxSharedPointer clientCtxPtr)
Select & delReadFd(int fd)
bool sendUntil(winux::Buffer const &data, int msgFlags=MsgDefault)
winux::ThreadPool _pool
线程池
static int const MsgInterrupt
ip::tcp::Socket _servSockA
服务器监听套接字A
ClientCtxSharedPointer & _addClient(ip::EndPoint const &clientEp, winux::SharedPointer< ip::tcp::Socket > clientSockPtr)
SocketError(int errType, winux::AnsiString const &errStr)
#define DEFINE_CUSTOM_EVENT(evtname, paramtypes, calledparams)
bool find(winux::AnsiString const &target, std::vector< _IndexType > const &targetNextVal)
在data里查找target内容。startpos指定起始位置,pos表示搜索到的位置。
ip::tcp::Socket _servSock
主机名解析器(可以把域名解析为一个或多个IP端点)
virtual winux::uint & size() const =0
取得地址的数据大小,一般为内部地址结构体的大小.
StartupHandlerFunction _startupHandler
std::vector< ip::EndPoint > EndPointArray
winux::MembersWrapper< struct SelectExcept_Data > _self
int send(winux::AnsiString const &data, int msgFlags=MsgDefault)
发送数据。返回已发送大小,出错返回-1。
std::function< void(ClientCtxSharedPointer clientCtxPtr) > StartupHandlerFunction
static int const MsgMaxIovLen
SimplePointer< _Ty > MakeSimple(_Ty *newObj)
EndPointArray::const_iterator begin() const
bool _isAutoReadData
是否自动读取客户到达的数据。当为true时,客户数据达到时调用ClientDataArrived事件,否则调用ClientDataNo...
static int const SdReceive
SelectWrite & setWriteSock(Socket const &sock)
bool sendUntil(winux::AnsiString const &data, int msgFlags=MsgDefault)
Server(ip::EndPoint const &ep, int threadCount=4, int backlog=0)
构造函数1
SocketStreamOut(SocketStreamBuf &sockBuf)
winux::SharedPointer< ip::tcp::Socket > clientSockPtr
客户套接字
SocketStreamOut(SocketStreamBuf *sockBuf)
size_t size() const
获取数据大小
winux::uint64 clientId
客户Id
bool sendUntilType(_PodType const &v, int msgFlags=MsgDefault)
发送一个Plain of Data类型的变量,若成功返回true,否则返回false。
EndPointArray const & getArr() const
Select & setExceptFds(winux::Mixed const &fds)
winux::MembersWrapper< struct SelectWrite_Data > _self