1,5 → 1,5 |
/* |
* Copyright (c) 2008 Lukas Mejdrech |
* Copyright (c) 2009 Lukas Mejdrech |
* All rights reserved. |
* |
* Redistribution and use in source and binary forms, with or without |
26,11 → 26,12 |
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
*/ |
|
/** @addtogroup net |
/** @addtogroup packet |
* @{ |
*/ |
|
/** @file |
* Packet server implementation. |
*/ |
|
#include <async.h> |
50,18 → 51,45 |
#include "packet_header.h" |
#include "packet_server.h" |
|
/** Returns the packet identifier message parameter. |
*/ |
#define IPC_GET_ID( call ) ( packet_id_t ) IPC_GET_ARG1( * call ) |
|
/** Returns the owner message parameter. |
*/ |
#define IPC_GET_OWNER( call ) ( services_t ) IPC_GET_ARG1( * call ) |
|
/** Returns the maximal content length message parameter. |
*/ |
#define IPC_GET_CONTENT( call ) ( size_t ) IPC_GET_ARG2( * call ) |
|
/** Returns the maximal address length message parameter. |
*/ |
#define IPC_GET_ADDR_LEN( call ) ( size_t ) IPC_GET_ARG3( * call ) |
|
/** Returns the maximal prefix length message parameter. |
*/ |
#define IPC_GET_PREFIX( call ) ( size_t ) IPC_GET_ARG4( * call ) |
|
/** Returns the maximal suffix length message parameter. |
*/ |
#define IPC_GET_SUFIX( call ) ( size_t ) IPC_GET_ARG5( * call ) |
|
#define FREE_QUEUES_COUNT 7 |
|
/** Packet server global data. |
*/ |
static struct{ |
/** Free packet queues. |
*/ |
packet_t free[ FREE_QUEUES_COUNT ]; |
/** Packet length upper bounds of the free packet queues. |
* The maximal lengths of packets in each queue in the ascending order. |
* The last queue is not limited. |
*/ |
int sizes[ FREE_QUEUES_COUNT ]; |
/** Total packets allocated. |
*/ |
unsigned int count; |
} ps_globals = { |
{ NULL, NULL, NULL, NULL, NULL, NULL, NULL }, |
69,10 → 97,54 |
0 |
}; |
|
/** Releases the packet and returns it to the appropriate free packet queue. |
* @param packet The packet to be released. Input parameter. |
*/ |
void packet_release( packet_t packet ); |
packet_t packet_get( services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_sufix ); |
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_sufix ); |
void packet_init( packet_t packet, services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_sufix ); |
|
/** Returns the packet of dimensions at least as given. |
* Tries to reuse free packets first. |
* Creates a new packet aligned to the memory page size if none available. |
* @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. |
* @param max_content The maximal content length in bytes. Input parameter. |
* @param max_suffix The maximal suffix length in bytes. Input parameter. |
* @returns The packet of dimensions at least as given. |
* @returns NULL if there is not enough memory left. |
*/ |
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 new packet of dimensions at least as given. |
* @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. |
* @param max_prefix The maximal prefix length in bytes. Input parameter. |
* @param max_content The maximal content length in bytes. Input parameter. |
* @param max_suffix The maximal suffix length in bytes. Input parameter. |
* @returns The packet of dimensions at least as given. |
* @returns NULL if there is not enough memory left. |
*/ |
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 ); |
|
/** Initializes the packet according to the given dimensions. |
* @param packet The packet to be initialized. 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. |
* @param max_prefix The maximal prefix length in bytes. Input parameter. |
* @param max_content The maximal content length in bytes. Input parameter. |
* @param max_suffix The maximal suffix length in bytes. Input parameter. |
*/ |
void packet_init( packet_t packet, services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_suffix ); |
|
/** Shares the packet memory block. |
* @param packet The packet to be shared. |
* @returns EOK on success. |
* @returns EINVAL if the packet is not valid. |
* @returns EINVAL if the calling module does not accept the memory. |
* @returns ENOMEM if the desired and actual sizes differ. |
* @returns Other error codes as defined for the ipc_share_in_finalize() function. |
*/ |
int packet_reply( const packet_t packet ); |
|
int packet_server_message( ipc_callid_t callid, ipc_call_t * call, ipc_call_t * answer, int * answer_count ){ |
122,12 → 194,12 |
ps_globals.free[ index ] = pq_add( ps_globals.free[ index ], packet, packet->length, packet->length ); |
} |
|
packet_t packet_get( services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_sufix ){ |
packet_t packet_get( services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_suffix ){ |
int index; |
packet_t packet; |
size_t length; |
|
length = ALIGN_UP( sizeof( struct packet ) + 2 * addr_len + max_prefix + max_content + max_sufix, PAGE_SIZE ); |
length = ALIGN_UP( sizeof( struct packet ) + 2 * addr_len + max_prefix + max_content + max_suffix, PAGE_SIZE ); |
for( index = 0; index < FREE_QUEUES_COUNT - 1; ++ index ){ |
if( length <= ps_globals.sizes[ index ] ){ |
packet = ps_globals.free[ index ]; |
135,15 → 207,15 |
packet = pm_find( packet->next ); |
} |
if( packet ){ |
packet_init( packet, owner, addr_len, max_prefix, max_content, max_sufix ); |
packet_init( packet, owner, addr_len, max_prefix, max_content, max_suffix ); |
return packet; |
} |
} |
} |
return packet_create( length, owner, addr_len, max_prefix, max_content, max_sufix ); |
return packet_create( length, owner, addr_len, max_prefix, max_content, max_suffix ); |
} |
|
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_sufix ){ |
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 ){ |
ERROR_DECLARE; |
|
packet_t packet; |
152,11 → 224,11 |
if( packet == MAP_FAILED ) return NULL; |
++ ps_globals.count; |
packet->packet_id = ps_globals.count; |
packet->mode = PM_ONEWAY; |
packet->mode = PM_ONE_WAY; |
packet->length = length; |
packet_init( packet, owner, addr_len, max_prefix, max_content, max_sufix ); |
packet_init( packet, owner, addr_len, max_prefix, max_content, max_suffix ); |
packet->magic_value = PACKET_MAGIC_VALUE; |
if( ERROR_OCCURED( pm_add( packet ))){ |
if( ERROR_OCCURRED( pm_add( packet ))){ |
munmap( packet, packet->length ); |
return NULL; |
} |
164,7 → 236,7 |
return packet; |
} |
|
void packet_init( packet_t packet, services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_sufix ){ |
void packet_init( packet_t packet, services_t owner, size_t addr_len, size_t max_prefix, size_t max_content, size_t max_suffix ){ |
packet->owner = owner; |
packet->order = 0; |
packet->metric = 0; |