/* dbs_server_read_data * Data came in on a client socket, so read it into the buffer. Returns * false on failure, or when the client closes its half of the * connection. (EAGAIN doesn't count as a failure.) */ BOOL dbs_server_read_data(t_d2dbs_connection* conn) { int nBytes; nBytes = psock_recv(conn->sd, conn->ReadBuf + conn->nCharsInReadBuffer, kBufferSize - conn->nCharsInReadBuffer, 0); if (nBytes == 0) { eventlog(eventlog_level_info,__FUNCTION__,"Socket %d was closed by the client. Shutting down.",conn->sd); return FALSE; } else if (nBytes < 0) { int err; psock_t_socklen errlen; err = 0; errlen = sizeof(err); if (psock_getsockopt(conn->sd, PSOCK_SOL_SOCKET, PSOCK_SO_ERROR, &err, &errlen)<0) return TRUE; if (errlen==0 || err==PSOCK_EAGAIN) { return TRUE; } else { eventlog(eventlog_level_error,__FUNCTION__,"psock_recv() failed : %s",strerror(err)); return FALSE; } } conn->nCharsInReadBuffer += nBytes; return TRUE; }
extern int net_recv_data(int sock, char * buff, int buffsize, int * pos, int * currsize) { int nrecv; ASSERT(buff,-1); ASSERT(pos,-1); if (*pos>buffsize) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] recv buffer overflow pos=%d buffsize=%d",sock,*pos,buffsize); return -1; } if (*currsize>*pos) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] recv buffer error currsize=%d pos=%d",sock,*currsize,*pos); return -1; } if (*pos==buffsize) { std::memmove(buff,buff+*pos,*currsize); *pos=0; } nrecv=psock_recv(sock,buff+*pos,buffsize-*pos,0); if (nrecv==0) { eventlog(eventlog_level_info,__FUNCTION__,"[%d] remote host closed connection",sock); return -1; } if (nrecv<0) { if ( #ifdef PSOCK_EINTR psock_errno()==PSOCK_EINTR || #endif #ifdef PSOCK_EAGAIN psock_errno()==PSOCK_EAGAIN || #endif #ifdef PSOCK_EWOULDBLOCK psock_errno()==PSOCK_EWOULDBLOCK || #endif #ifdef PSOCK_ENOMEM psock_errno()==ENOMEM || #endif 0) return 0; if ( #ifdef PSOCK_ENOTCONN psock_errno()==PSOCK_ENOTCONN || #endif #ifdef PSOCK_ECONNRESET psock_errno()==PSOCK_ECONNRESET || #endif 0) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] remote host closed connection (psock_recv: %s)",sock,pstrerror(psock_errno())); return -1; } eventlog(eventlog_level_error,__FUNCTION__,"[%d] recv error (closing connection) (psock_recv: %s)",sock,pstrerror(psock_errno())); return -1; } * currsize += nrecv; return 1; }
int myp_recv( MYSQL *m, void *buf, int size ) { while( size ) { int len = psock_recv(m->s,(char*)buf,size); if( len <= 0 ) return size == 0 ? 1 : 0; buf = ((char*)buf) + len; size -= len; } return 1; }
extern int net_recv(int sock, void *buff, int len) { int res; res = psock_recv(sock, buff, len, 0); if (res > 0) return res; if (!res) return -1; /* connection closed */ if ( #ifdef PSOCK_EINTR psock_errno()==PSOCK_EINTR || #endif #ifdef PSOCK_EAGAIN psock_errno()==PSOCK_EAGAIN || #endif #ifdef PSOCK_EWOULDBLOCK psock_errno()==PSOCK_EWOULDBLOCK || #endif #ifdef PSOCK_ENOMEM psock_errno()==PSOCK_ENOMEM || #endif 0) /* try later */ return 0; if ( #ifdef PSOCK_ENOTCONN psock_errno()==PSOCK_ENOTCONN || #endif #ifdef PSOCK_ECONNRESET psock_errno()==PSOCK_ECONNRESET || #endif 0) { /* eventlog(eventlog_level_debug,__FUNCTION__,"[%d] remote host closed connection (psock_recv: %s)",sock,std::strerror(psock_errno())); */ return -1; /* common error: close connection, but no message */ } eventlog(eventlog_level_debug,__FUNCTION__,"[%d] receive error (closing connection) (psock_recv: %s)",sock,std::strerror(psock_errno())); return -1; }
extern int handle_file_packet(t_connection * c, t_packet const * const packet) { if (!c) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] got NULL connection",conn_get_socket(c)); return -1; } if (!packet) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] got NULL packet",conn_get_socket(c)); return -1; } /* REMOVED BY UNDYING SOULZZ 4/3/02 */ /* if (packet_get_class(packet)!=packet_class_file) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] got bad packet (class %d)",conn_get_socket(c),(int)packet_get_class(packet)); return -1; } */ switch (conn_get_state(c)) { case conn_state_connected: switch (packet_get_type(packet)) { case CLIENT_FILE_REQ: { char const * rawname; if (!(rawname = packet_get_str_const(packet,sizeof(t_client_file_req),MAX_FILENAME_STR))) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] got bad FILE_REQ (missing or too long filename)",conn_get_socket(c)); return -1; } file_send(c,rawname, bn_int_get(packet->u.client_file_req.adid), bn_int_get(packet->u.client_file_req.extensiontag), bn_int_get(packet->u.client_file_req.startoffset), 1); } break; case CLIENT_FILE_REQ2: { t_packet * rpacket = NULL; if((rpacket = packet_create(packet_class_raw))) { packet_set_size(rpacket,sizeof(t_server_file_unknown1)); bn_int_set( &rpacket->u.server_file_unknown1.unknown, 0xdeadbeef ); conn_push_outqueue(c, rpacket ); packet_del_ref( rpacket ); } conn_set_state(c, conn_state_pending_raw); break; } default: eventlog(eventlog_level_error,__FUNCTION__,"[%d] unknown file packet type 0x%04x, len %u",conn_get_socket(c),packet_get_type(packet),packet_get_size(packet)); break; } break; case conn_state_pending_raw: switch (packet_get_type(packet)) { case CLIENT_FILE_REQ3: { char rawname[MAX_FILENAME_STR]; psock_recv( conn_get_socket(c), rawname, MAX_FILENAME_STR, 0 ); file_send(c, rawname, 0, 0, 0, 1); } break; default: eventlog(eventlog_level_error, __FUNCTION__, "[%d] unknown file packet type 0x%04x, len %u",conn_get_socket(c),packet_get_type(packet),packet_get_size(packet)); break; } break; default: eventlog(eventlog_level_error,__FUNCTION__,"[%d] unknown file connection state %d",conn_get_socket(c),(int)conn_get_state(c)); } return 0; }
static int init_virtconn(t_virtconn * vc, struct sockaddr_in servaddr) { int addlen; char connect_type; /* determine connection type by first character sent by client */ addlen = psock_recv(virtconn_get_client_socket(vc),&connect_type,sizeof(char),0); if (addlen<0 && (psock_errno()==PSOCK_EINTR || psock_errno()==PSOCK_EAGAIN || psock_errno()==PSOCK_EWOULDBLOCK)) return 0; /* error occurred or connection lost */ if (addlen<1) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] could not get virtconn class (closing connection) (psock_recv: %s)",virtconn_get_client_socket(vc),pstrerror(psock_errno())); return -1; } switch (connect_type) { case CLIENT_INITCONN_CLASS_BNET: eventlog(eventlog_level_info,__FUNCTION__,"[%d] client initiated normal connection",virtconn_get_client_socket(vc)); virtconn_set_class(vc,virtconn_class_bnet); break; case CLIENT_INITCONN_CLASS_FILE: eventlog(eventlog_level_info,__FUNCTION__,"[%d] client initiated file download connection",virtconn_get_client_socket(vc)); virtconn_set_class(vc,virtconn_class_file); break; case CLIENT_INITCONN_CLASS_BOT: eventlog(eventlog_level_info,__FUNCTION__,"[%d] client initiated chat bot connection",virtconn_get_client_socket(vc)); virtconn_set_class(vc,virtconn_class_bot); break; default: eventlog(eventlog_level_error,__FUNCTION__,"[%d] client initiated unknown connection type 0x%02hx (length %d) (closing connection)",virtconn_get_client_socket(vc),(unsigned short)connect_type,addlen); return -1; } /* now connect to the real server */ if (psock_connect(virtconn_get_server_socket(vc),(struct sockaddr *)&servaddr,(psock_t_socklen)sizeof(servaddr))<0) { if (psock_errno()!=PSOCK_EINPROGRESS) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] could not connect to server (psock_connect: %s)\n",virtconn_get_client_socket(vc),pstrerror(psock_errno())); return -1; } virtconn_set_state(vc,virtconn_state_connecting); } else virtconn_set_state(vc,virtconn_state_connected); { t_packet * packet; if (!(packet = packet_create(packet_class_raw))) { eventlog(eventlog_level_error,__FUNCTION__,"[%d] could not create packet",virtconn_get_client_socket(vc)); return -1; } packet_append_data(packet,&connect_type,1); queue_push_packet(virtconn_get_serverout_queue(vc),packet); packet_del_ref(packet); } return 0; }
extern int net_recv_packet(int sock, t_packet * packet, unsigned int * currsize) { int addlen; unsigned int header_size; void * temp; if (!packet) { eventlog(eventlog_level_error,"net_recv_packet","[%d] got NULL packet (closing connection)",sock); return -1; } if (!currsize) { eventlog(eventlog_level_error,"net_recv_packet","[%d] got NULL currsize (closing connection)",sock); return -1; } if ((header_size = packet_get_header_size(packet))>=MAX_PACKET_SIZE) { eventlog(eventlog_level_error,"net_recv_packet","[%d] could not determine header size (closing connection)",sock); return -1; } if (!(temp = packet_get_raw_data_build(packet,*currsize))) { eventlog(eventlog_level_error,"net_recv_packet","[%d] could not obtain raw data pointer at offset %u (closing connection)",sock,*currsize); return -1; } if (*currsize<header_size) { addlen = psock_recv(sock, temp, header_size-*currsize, 0); } else { unsigned int total_size=packet_get_size(packet); if (total_size<header_size) { eventlog(eventlog_level_warn,"net_recv_packet","[%d] corrupted packet received (total_size=%u currsize=%u) (closing connection)",sock,total_size,*currsize); return -1; } if (*currsize>=total_size) { eventlog(eventlog_level_warn,"net_recv_packet","[%d] more data requested for already complete packet (total_size=%u currsize=%u) (closing connection)",sock,total_size,*currsize); return -1; } addlen = psock_recv(sock, temp, total_size-*currsize, 0); } if (addlen==0) { eventlog(eventlog_level_debug,"net_recv_packet","[%d] remote host closed connection",sock); return -1; } if (addlen<0) { if ( #ifdef PSOCK_EINTR psock_errno()==PSOCK_EINTR || #endif #ifdef PSOCK_EAGAIN psock_errno()==PSOCK_EAGAIN || #endif #ifdef PSOCK_EWOULDBLOCK psock_errno()==PSOCK_EWOULDBLOCK || #endif #ifdef PSOCK_ENOMEM psock_errno()==PSOCK_ENOMEM || #endif 0) /* try later */ return 0; if ( #ifdef PSOCK_ENOTCONN psock_errno()==PSOCK_ENOTCONN || #endif #ifdef PSOCK_ECONNRESET psock_errno()==PSOCK_ECONNRESET || #endif 0) { /* eventlog(eventlog_level_debug,"net_recv_packet","[%d] remote host closed connection (psock_recv: %s)",sock,strerror(psock_errno())); */ return -1; /* common error: close connection, but no message */ } eventlog(eventlog_level_error,"net_recv_packet","[%d] receive error (closing connection) (psock_recv: %s)",sock,strerror(psock_errno())); return -1; } *currsize += addlen; if (*currsize>=header_size && *currsize==packet_get_size(packet)) return 1; return 0; }
static ssize_t telnetd_read(FAR struct file *filep, FAR char *buffer, size_t len) { FAR struct inode *inode = filep->f_inode; FAR struct telnetd_dev_s *priv = inode->i_private; ssize_t ret; nllvdbg("len: %d\n", len); /* First, handle the case where there are still valid bytes left in the * I/O buffer from the last time that read was called. NOTE: Much of * what we read may be protocol stuff and may not correspond to user * data. Hence we need the loop and we need may need to call psock_recv() * multiple times in order to get data that the client is interested in. */ do { if (priv->td_pending > 0) { /* Process the buffered telnet data */ FAR const char *src = &priv->td_rxbuffer[priv->td_offset]; ret = telnetd_receive(priv, src, priv->td_pending, buffer, len); } /* Read a buffer of data from the telnet client */ else { ret = psock_recv(&priv->td_psock, priv->td_rxbuffer, CONFIG_TELNETD_RXBUFFER_SIZE, 0); /* Did we receive anything? */ if (ret > 0) { /* Yes.. Process the newly received telnet data */ telnetd_dumpbuffer("Received buffer", priv->td_rxbuffer, ret); ret = telnetd_receive(priv, priv->td_rxbuffer, ret, buffer, len); } /* Otherwise the peer closed the connection (ret == 0) or an error * occurred (ret < 0). */ else { break; } } } while (ret == 0); /* Return: * * ret > 0: The number of characters copied into the user buffer by * telnetd_receive(). * ret <= 0: Loss of connection or error events reported by recv(). */ return ret; }