Beispiel #1
0
static int _network_async_free_netbuf_proc(int tid, unsigned int tick, int id, intptr_t data)
{
	// netbuf is in data
	netbuffer_put((netbuf)data);

	return 0;
}//end: _network_async_free_netbuf_proc()
Beispiel #2
0
void network_disconnect(int32 fd)
{
	SESSION *s = &g_Session[fd];
	netbuf b, bn;

	// Prevent recursive calls
	// by wrong implemented on disconnect handlers.. and such..
	if(s->disconnect_in_progress == true)
		return;

	s->disconnect_in_progress = true;


	// Disconnect Todo:
	//  - Call onDisconnect Handler
	//  - Release all Assigned buffers.
	//  - remove from event system (notifications)
	//  - cleanup session structure
	//  - close connection.
	//

	if(s->onDisconnect != NULL &&
	   s->type != NST_LISTENER) {

		s->onDisconnect(fd);
	}

	// Read Buffer
	if(s->read.buf != NULL) {
		netbuffer_put(s->read.buf);
		s->read.buf = NULL;
	}

	// Write Buffer(s)
	b = s->write.buf;
	while(1) {
		if(b == NULL) break;

		bn = b->next;

		netbuffer_put(b);

		b = bn;
	}
	s->write.buf = NULL;
	s->write.buf_last = NULL;

	s->write.n_outstanding = 0;
	s->write.max_outstanding = 0;


	// Remove from event system.
	evdp_remove(fd, &s->evdp_data);

	// Cleanup Session Structure.
	s->type = NST_FREE;
	s->data = NULL; // no application level data assigned
	s->disconnect_in_progress = false;


	// Close connection
	close(fd);

}//end: network_disconnect()
Beispiel #3
0
static bool _onSend(int32 fd){
	register SESSION *s = &g_Session[fd];
	register netbuf buf, buf_next;
	register uint32 szNeeded;
	register int wLen;

	if(s->type == NST_FREE)
		return true; 	// Possible due to multipl non coalsced event notifications 
						// so onSend gets called after disconnect caused by an previous vent. 
						// we can ignore the call to onSend, then. 
	
	buf = s->write.buf;
	while(1){
		if(buf == NULL)
			break;
		
		buf_next = buf->next;
		
		
		szNeeded = (buf->dataLen - s->write.dataPos);	// using th session-local .dataPos member, due to shared write buffer support.
		
		// try to write.
		wLen = write(fd, &buf->buf[s->write.dataPos],  szNeeded);
		if(wLen == 0){
			return false; // eof.
		}else if(wLen == -1){
			if(errno == EAGAIN || errno == EWOULDBLOCK)
				return true; // dont disconnect / try again later.
			
			// all other errors. . 
			return false;
		}
		
		// Wrote data.. =>
		szNeeded -= wLen;
		if(szNeeded > 0){
			// still data left .. 
			// 
			s->write.dataPos += wLen; // fix offset.
			return true;
		}else{
			// this buffer has been written successfully
			// could be returned to pool.
			netbuffer_put(buf);
			s->write.n_outstanding--; // When threadsafe -> Interlocked here.
			s->write.dataPos = 0; 
		}
			
			
		buf = buf_next;
	}

	// okay,
	// reaching this part means:
	// while interrupted by break - 
	// which means all buffers are written, nothing left
	//
	
	s->write.buf_last = NULL;
	s->write.buf = NULL;
	s->write.n_outstanding = 0;
	s->write.dataPos = 0;
	
	// Remove from event dispatcher (write notification)
	//
	evdp_writable_remove(fd, &s->evdp_data);
			
	return true;	
}//end: _onSend()