Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/net/tl/tl_common.c

    r46d4d9f r14f1db0  
    2727 */
    2828
    29 /** @addtogroup libnet
    30  * @{
     29/** @addtogroup net_tl
     30 *  @{
    3131 */
    3232
    3333/** @file
    34  * Transport layer common functions implementation.
    35  * @see tl_common.h
    36  */
    37 
    38 #include <tl_common.h>
    39 #include <packet_client.h>
     34 *  Transport layer common functions implementation.
     35 *  @see tl_common.h
     36 */
     37
     38#include <async.h>
     39#include <ipc/services.h>
     40
     41#include <net_err.h>
     42#include <packet/packet.h>
     43#include <packet/packet_client.h>
    4044#include <packet_remote.h>
     45#include <net_device.h>
    4146#include <icmp_interface.h>
     47#include <in.h>
     48#include <in6.h>
     49#include <inet.h>
     50#include <ip_local.h>
    4251#include <ip_remote.h>
     52#include <socket_codes.h>
     53#include <socket_errno.h>
    4354#include <ip_interface.h>
    4455#include <tl_interface.h>
    45 
    46 #include <net/socket_codes.h>
    47 #include <net/in.h>
    48 #include <net/in6.h>
    49 #include <net/inet.h>
    50 #include <net/device.h>
    51 #include <net/packet.h>
    52 
    53 #include <async.h>
    54 #include <ipc/services.h>
    55 #include <errno.h>
     56#include <tl_common.h>
    5657
    5758DEVICE_MAP_IMPLEMENT(packet_dimensions, packet_dimension_t);
    5859
    59 /** Gets the address port.
    60  *
    61  * Supports AF_INET and AF_INET6 address families.
    62  *
    63  * @param[in,out] addr  The address to be updated.
    64  * @param[in] addrlen   The address length.
    65  * @param[out] port     The set port.
    66  * @return              EOK on success.
    67  * @return              EINVAL if the address length does not match the address
    68  *                      family.
    69  * @return              EAFNOSUPPORT if the address family is not supported.
    70  */
    71 int
    72 tl_get_address_port(const struct sockaddr *addr, int addrlen, uint16_t *port)
    73 {
    74         const struct sockaddr_in *address_in;
    75         const struct sockaddr_in6 *address_in6;
    76 
    77         if ((addrlen <= 0) || ((size_t) addrlen < sizeof(struct sockaddr)))
    78                 return EINVAL;
    79 
    80         switch (addr->sa_family) {
    81         case AF_INET:
    82                 if (addrlen != sizeof(struct sockaddr_in))
    83                         return EINVAL;
    84 
    85                 address_in = (struct sockaddr_in *) addr;
    86                 *port = ntohs(address_in->sin_port);
    87                 break;
    88        
    89         case AF_INET6:
    90                 if (addrlen != sizeof(struct sockaddr_in6))
    91                         return EINVAL;
    92 
    93                 address_in6 = (struct sockaddr_in6 *) addr;
    94                 *port = ntohs(address_in6->sin6_port);
    95                 break;
    96        
    97         default:
    98                 return EAFNOSUPPORT;
    99         }
    100 
     60int tl_get_address_port(const struct sockaddr * addr, int addrlen, uint16_t * port){
     61        const struct sockaddr_in * address_in;
     62        const struct sockaddr_in6 * address_in6;
     63
     64        if((addrlen <= 0) || ((size_t) addrlen < sizeof(struct sockaddr))){
     65                return EINVAL;
     66        }
     67        switch(addr->sa_family){
     68                case AF_INET:
     69                        if(addrlen != sizeof(struct sockaddr_in)){
     70                                return EINVAL;
     71                        }
     72                        address_in = (struct sockaddr_in *) addr;
     73                        *port = ntohs(address_in->sin_port);
     74                        break;
     75                case AF_INET6:
     76                        if(addrlen != sizeof(struct sockaddr_in6)){
     77                                return EINVAL;
     78                        }
     79                        address_in6 = (struct sockaddr_in6 *) addr;
     80                        *port = ntohs(address_in6->sin6_port);
     81                        break;
     82                default:
     83                        return EAFNOSUPPORT;
     84        }
    10185        return EOK;
    10286}
     
    10791 * The reply is cached then.
    10892 *
    109  * @param[in] ip_phone  The IP moduel phone for (semi)remote calls.
    110  * @param[in] packet_dimensions The packet dimensions cache.
    111  * @param[in] device_id The device identifier.
    112  * @param[out] packet_dimension The IP packet dimensions.
    113  * @return              EOK on success.
    114  * @return              EBADMEM if the packet_dimension parameter is NULL.
    115  * @return              ENOMEM if there is not enough memory left.
    116  * @return              EINVAL if the packet_dimensions cache is not valid.
    117  * @return              Other codes as defined for the ip_packet_size_req()
    118  *                      function.
    119  */
    120 int
    121 tl_get_ip_packet_dimension(int ip_phone,
    122     packet_dimensions_t *packet_dimensions, device_id_t device_id,
    123     packet_dimension_t **packet_dimension)
     93 * @param[in]  ip_phone          The IP moduel phone for (semi)remote calls.
     94 * @param[in]  packet_dimensions The packet dimensions cache.
     95 * @param[in]  device_id         The device identifier.
     96 * @param[out] packet_dimension  The IP packet dimensions.
     97 *
     98 * @return EOK on success.
     99 * @return EBADMEM if the packet_dimension parameter is NULL.
     100 * @return ENOMEM if there is not enough memory left.
     101 * @return EINVAL if the packet_dimensions cache is not valid.
     102 * @return Other codes as defined for the ip_packet_size_req() function.
     103 *
     104 */
     105int tl_get_ip_packet_dimension(int ip_phone,
     106    packet_dimensions_ref packet_dimensions, device_id_t device_id,
     107    packet_dimension_ref *packet_dimension)
    124108{
    125         int rc;
     109        ERROR_DECLARE;
    126110       
    127111        if (!packet_dimension)
    128112                return EBADMEM;
    129113       
    130         *packet_dimension = packet_dimensions_find(packet_dimensions,
    131             device_id);
     114        *packet_dimension = packet_dimensions_find(packet_dimensions, device_id);
    132115        if (!*packet_dimension) {
    133116                /* Ask for and remember them if not found */
     
    136119                        return ENOMEM;
    137120               
    138                 rc = ip_packet_size_req(ip_phone, device_id, *packet_dimension);
    139                 if (rc != EOK) {
     121                if (ERROR_OCCURRED(ip_packet_size_req(ip_phone, device_id,
     122                    *packet_dimension))) {
    140123                        free(*packet_dimension);
    141                         return rc;
     124                        return ERROR_CODE;
    142125                }
    143126               
    144                 rc = packet_dimensions_add(packet_dimensions, device_id,
     127                ERROR_CODE = packet_dimensions_add(packet_dimensions, device_id,
    145128                    *packet_dimension);
    146                 if (rc < 0) {
     129                if (ERROR_CODE < 0) {
    147130                        free(*packet_dimension);
    148                         return rc;
     131                        return ERROR_CODE;
    149132                }
    150133        }
     
    153136}
    154137
    155 /** Updates IP device packet dimensions cache.
    156  *
    157  * @param[in,out] packet_dimensions The packet dimensions cache.
    158  * @param[in] device_id The device identifier.
    159  * @param[in] content   The new maximum content size.
    160  * @return              EOK on success.
    161  * @return              ENOENT if the packet dimension is not cached.
    162  */
    163 int
    164 tl_update_ip_packet_dimension(packet_dimensions_t *packet_dimensions,
    165     device_id_t device_id, size_t content)
    166 {
    167         packet_dimension_t *packet_dimension;
     138int tl_update_ip_packet_dimension(packet_dimensions_ref packet_dimensions, device_id_t device_id, size_t content){
     139        packet_dimension_ref packet_dimension;
    168140
    169141        packet_dimension = packet_dimensions_find(packet_dimensions, device_id);
    170         if (!packet_dimension)
     142        if(! packet_dimension){
    171143                return ENOENT;
    172 
     144        }
    173145        packet_dimension->content = content;
    174 
    175         if (device_id != DEVICE_INVALID_ID) {
    176                 packet_dimension = packet_dimensions_find(packet_dimensions,
    177                     DEVICE_INVALID_ID);
    178 
    179                 if (packet_dimension) {
    180                         if (packet_dimension->content >= content)
     146        if(device_id != DEVICE_INVALID_ID){
     147                packet_dimension = packet_dimensions_find(packet_dimensions, DEVICE_INVALID_ID);
     148                if(packet_dimension){
     149                        if(packet_dimension->content >= content){
    181150                                packet_dimension->content = content;
    182                         else
    183                                 packet_dimensions_exclude(packet_dimensions,
    184                                     DEVICE_INVALID_ID);
     151                        }else{
     152                                packet_dimensions_exclude(packet_dimensions, DEVICE_INVALID_ID);
     153                        }
    185154                }
    186155        }
    187 
    188156        return EOK;
    189157}
    190158
    191 /** Sets the address port.
    192  *
    193  * Supports AF_INET and AF_INET6 address families.
    194  *
    195  * @param[in,out] addr  The address to be updated.
    196  * @param[in] addrlen   The address length.
    197  * @param[in] port      The port to be set.
    198  * @return              EOK on success.
    199  * @return              EINVAL if the address length does not match the address
    200  *                      family.
    201  * @return              EAFNOSUPPORT if the address family is not supported.
    202  */
    203 int tl_set_address_port(struct sockaddr * addr, int addrlen, uint16_t port)
    204 {
    205         struct sockaddr_in *address_in;
    206         struct sockaddr_in6 *address_in6;
     159int tl_set_address_port(struct sockaddr * addr, int addrlen, uint16_t port){
     160        struct sockaddr_in * address_in;
     161        struct sockaddr_in6 * address_in6;
    207162        size_t length;
    208163
    209         if (addrlen < 0)
    210                 return EINVAL;
    211        
     164        if(addrlen < 0){
     165                return EINVAL;
     166        }
    212167        length = (size_t) addrlen;
    213         if (length < sizeof(struct sockaddr))
    214                 return EINVAL;
    215 
    216         switch (addr->sa_family) {
    217         case AF_INET:
    218                 if (length != sizeof(struct sockaddr_in))
    219                         return EINVAL;
    220                 address_in = (struct sockaddr_in *) addr;
    221                 address_in->sin_port = htons(port);
    222                 return EOK;
    223        
    224         case AF_INET6:
    225                 if (length != sizeof(struct sockaddr_in6))
    226                                 return EINVAL;
    227                 address_in6 = (struct sockaddr_in6 *) addr;
    228                 address_in6->sin6_port = htons(port);
    229                 return EOK;
    230        
    231         default:
    232                 return EAFNOSUPPORT;
    233         }
    234 }
    235 
    236 /** Prepares the packet for ICMP error notification.
    237  *
    238  * Keeps the first packet and releases all the others.
    239  * Releases all the packets on error.
    240  *
    241  * @param[in] packet_phone The packet server module phone.
    242  * @param[in] icmp_phone The ICMP module phone.
    243  * @param[in] packet    The packet to be send.
    244  * @param[in] error     The packet error reporting service. Prefixes the
    245  *                      received packet.
    246  * @return              EOK on success.
    247  * @return              ENOENT if no packet may be sent.
    248  */
    249 int
    250 tl_prepare_icmp_packet(int packet_phone, int icmp_phone, packet_t *packet,
    251     services_t error)
    252 {
    253         packet_t *next;
    254         uint8_t *src;
     168        if(length < sizeof(struct sockaddr)){
     169                return EINVAL;
     170        }
     171        switch(addr->sa_family){
     172                case AF_INET:
     173                        if(length != sizeof(struct sockaddr_in)){
     174                                return EINVAL;
     175                        }
     176                        address_in = (struct sockaddr_in *) addr;
     177                        address_in->sin_port = htons(port);
     178                        return EOK;
     179                case AF_INET6:
     180                        if(length != sizeof(struct sockaddr_in6)){
     181                                return EINVAL;
     182                        }
     183                        address_in6 = (struct sockaddr_in6 *) addr;
     184                        address_in6->sin6_port = htons(port);
     185                        return EOK;
     186                default:
     187                        return EAFNOSUPPORT;
     188        }
     189}
     190
     191int tl_prepare_icmp_packet(int packet_phone, int icmp_phone, packet_t packet, services_t error){
     192        packet_t next;
     193        uint8_t * src;
    255194        int length;
    256195
     
    261200       
    262201        length = packet_get_addr(packet, &src, NULL);
    263         if ((length > 0) && (!error) && (icmp_phone >= 0) &&
    264             // set both addresses to the source one (avoids the source address
    265             // deletion before setting the destination one)
    266             (packet_set_addr(packet, src, src, (size_t) length) == EOK)) {
     202        if((length > 0)
     203                && (! error)
     204                && (icmp_phone >= 0)
     205        // set both addresses to the source one (avoids the source address deletion before setting the destination one)
     206                && (packet_set_addr(packet, src, src, (size_t) length) == EOK)){
    267207                return EOK;
    268         } else
     208        }else{
    269209                pq_release_remote(packet_phone, packet_get_id(packet));
    270 
     210        }
    271211        return ENOENT;
    272212}
    273213
    274 /** Receives data from the socket into a packet.
    275  *
    276  * @param[in] packet_phone The packet server module phone.
    277  * @param[out] packet   The new created packet.
    278  * @param[in] prefix    Reserved packet data prefix length.
    279  * @param[in] dimension The packet dimension.
    280  * @param[in] addr      The destination address.
    281  * @param[in] addrlen   The address length.
    282  * @return              Number of bytes received.
    283  * @return              EINVAL if the client does not send data.
    284  * @return              ENOMEM if there is not enough memory left.
    285  * @return              Other error codes as defined for the
    286  *                      async_data_read_finalize() function.
    287  */
    288 int
    289 tl_socket_read_packet_data(int packet_phone, packet_t **packet, size_t prefix,
    290     const packet_dimension_t *dimension, const struct sockaddr *addr,
    291     socklen_t addrlen)
    292 {
     214int tl_socket_read_packet_data(int packet_phone, packet_ref packet, size_t prefix, const packet_dimension_ref dimension, const struct sockaddr * addr, socklen_t addrlen){
     215        ERROR_DECLARE;
     216
    293217        ipc_callid_t callid;
    294218        size_t length;
    295         void *data;
    296         int rc;
    297 
    298         if (!dimension)
    299                 return EINVAL;
    300 
     219        void * data;
     220
     221        if(! dimension){
     222                return EINVAL;
     223        }
    301224        // get the data length
    302         if (!async_data_write_receive(&callid, &length))
    303                 return EINVAL;
    304 
     225        if(! async_data_write_receive(&callid, &length)){
     226                return EINVAL;
     227        }
    305228        // get a new packet
    306         *packet = packet_get_4_remote(packet_phone, length, dimension->addr_len,
    307             prefix + dimension->prefix, dimension->suffix);
    308         if (!packet)
     229        *packet = packet_get_4_remote(packet_phone, length, dimension->addr_len, prefix + dimension->prefix, dimension->suffix);
     230        if(! packet){
    309231                return ENOMEM;
    310 
     232        }
    311233        // allocate space in the packet
    312234        data = packet_suffix(*packet, length);
    313         if (!data) {
     235        if(! data){
    314236                pq_release_remote(packet_phone, packet_get_id(*packet));
    315237                return ENOMEM;
    316238        }
    317 
    318239        // read the data into the packet
    319         rc = async_data_write_finalize(callid, data, length);
    320         if (rc != EOK) {
     240        if(ERROR_OCCURRED(async_data_write_finalize(callid, data, length))
     241        // set the packet destination address
     242                || ERROR_OCCURRED(packet_set_addr(*packet, NULL, (uint8_t *) addr, addrlen))){
    321243                pq_release_remote(packet_phone, packet_get_id(*packet));
    322                 return rc;
    323         }
    324        
    325         // set the packet destination address
    326         rc = packet_set_addr(*packet, NULL, (uint8_t *) addr, addrlen);
    327         if (rc != EOK) {
    328                 pq_release_remote(packet_phone, packet_get_id(*packet));
    329                 return rc;
    330         }
    331 
     244                return ERROR_CODE;
     245        }
    332246        return (int) length;
    333247}
Note: See TracChangeset for help on using the changeset viewer.