int32_t _send( struct session * self, char * buf, uint32_t nbytes ) { int32_t rc = 0; if ( self->status&SESSION_EXITING ) { // 等待关闭的连接 return -1; } // 判断session是否繁忙 if ( !(self->status&SESSION_WRITING) && session_sendqueue_count(self) == 0 ) { // 直接发送 rc = channel_send( self, buf, nbytes ); if ( rc == nbytes ) { // 全部发送出去 return rc; } // 为什么发送错误没有直接终止会话呢? // 该接口有可能在ioservice_t中调用, 直接终止会话后, 会引发后续对会话的操作崩溃 } // 创建message, 添加到发送队列中 struct message * message = message_create(); if ( message == NULL ) { return -2; } message_add_buffer( message, buf+rc, nbytes-rc ); message_add_receiver( message, self->id ); QUEUE_PUSH(sendqueue)(&self->sendqueue, &message); session_add_event( self, EV_WRITE ); return rc; }
int32_t iolayer_broadcast( iolayer_t self, sid_t * ids, uint32_t count, const char * buf, uint32_t nbytes ) { uint8_t i = 0; int32_t rc = 0; pthread_t threadid = pthread_self(); struct iolayer * layer = (struct iolayer *)self; for ( i = 0; i < layer->nthreads; ++i ) { struct message * msg = message_create(); if ( unlikely(msg == NULL) ) { continue; } message_add_receivers( msg, ids, count ); message_add_buffer( msg, (char *)buf, nbytes ); if ( threadid == iothreads_get_id( layer->group, i ) ) { // 本线程内直接广播 _broadcast_direct( layer, i, _get_manager(layer, i), msg ); } else { // 跨线程提交广播任务 int32_t result = iothreads_post( layer->group, i, eIOTaskType_Broadcast, msg, 0 ); if ( unlikely(result != 0) ) { message_destroy( msg ); continue; } } rc += count; } return rc; }