Subversion Repositories HelenOS

Compare Revisions

Ignore whitespace Rev 3913 → Rev 3914

/branches/network/uspace/srv/net/structures/packet/packet_server.c
34,9 → 34,10
* Packet server implementation.
*/
 
#include <align.h>
#include <async.h>
#include <align.h>
#include <errno.h>
#include <futex.h>
//#include <stdio.h>
#include <unistd.h>
 
80,6 → 81,9
/** Packet server global data.
*/
static struct{
/** Safety lock.
*/
futex_t lock;
/** Free packet queues.
*/
packet_t free[ FREE_QUEUES_COUNT ];
92,6 → 96,7
*/
unsigned int count;
} ps_globals = {
{ 1 },
{ NULL, NULL, NULL, NULL, NULL, NULL, NULL },
{ PAGE_SIZE, PAGE_SIZE * 2, PAGE_SIZE * 4, PAGE_SIZE * 8, PAGE_SIZE * 16, PAGE_SIZE * 32, PAGE_SIZE * 64 },
0
98,6 → 103,7
};
 
/** Releases the packet and returns it to the appropriate free packet queue.
* Should be used only when the global data are locked.
* @param packet The packet to be released. Input parameter.
*/
void packet_release( packet_t packet );
105,6 → 111,7
/** Returns the packet of dimensions at least as given.
* Tries to reuse free packets first.
* Creates a&nbsp;new packet aligned to the memory page size if none available.
* Locks the global data during its processing.
* @param owner The new owner of the packet. Input parameter.
* @param addr_len The source and destination addresses maximal length in bytes. Input parameter.
* @param max_prefix The maximal prefix length in bytes. Input parameter.
116,6 → 123,7
packet_t packet_get( services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_suffix );
 
/** Creates a&nbsp;new packet of dimensions at least as given.
* Should be used only when the global data are locked.
* @param length The total length of the packet, including the header, the addresses and the data of the packet. Input parameter.
* @param owner The new owner of the packet. Input parameter.
* @param addr_len The source and destination addresses maximal length in bytes. Input parameter.
181,7 → 189,9
case NET_PACKET_RELEASE:
packet = pm_find( IPC_GET_ID( call ));
if( ! packet_is_valid( packet )) return ENOENT;
futex_down( & ps_globals.lock );
pq_destroy( packet, packet_release );
futex_up( & ps_globals.lock );
return EOK;
}
return ENOTSUP;
200,6 → 210,7
size_t length;
 
length = ALIGN_UP( sizeof( struct packet ) + 2 * addr_len + max_prefix + max_content + max_suffix, PAGE_SIZE );
futex_down( & ps_globals.lock );
for( index = 0; index < FREE_QUEUES_COUNT - 1; ++ index ){
if( length <= ps_globals.sizes[ index ] ){
packet = ps_globals.free[ index ];
208,11 → 219,14
}
if( packet ){
packet_init( packet, owner, addr_len, max_prefix, max_content, max_suffix );
futex_up( & ps_globals.lock );
return packet;
}
}
}
return packet_create( length, owner, addr_len, max_prefix, max_content, max_suffix );
packet = packet_create( length, owner, addr_len, max_prefix, max_content, max_suffix );
futex_up( & ps_globals.lock );
return packet;
}
 
packet_t packet_create( size_t length, services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_suffix ){
220,6 → 234,7
 
packet_t packet;
 
// already locked
packet = ( packet_t ) mmap( NULL, length, PROTO_READ | PROTO_WRITE, MAP_SHARED | MAP_ANONYMOUS, 0, 0 );
if( packet == MAP_FAILED ) return NULL;
++ ps_globals.count;