Rev 4695 | Rev 4707 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 4695 | Rev 4702 | ||
---|---|---|---|
Line 29... | Line 29... | ||
29 | /** @addtogroup ip |
29 | /** @addtogroup ip |
30 | * @{ |
30 | * @{ |
31 | */ |
31 | */ |
32 | 32 | ||
33 | /** @file |
33 | /** @file |
- | 34 | * IP module implementation. |
|
- | 35 | * @see arp.h |
|
- | 36 | * \todo |
|
34 | */ |
37 | */ |
35 | 38 | ||
36 | #include <async.h> |
39 | #include <async.h> |
37 | #include <errno.h> |
40 | #include <errno.h> |
38 | #include <fibril_sync.h> |
41 | #include <fibril_sync.h> |
Line 71... | Line 74... | ||
71 | #include "ip.h" |
74 | #include "ip.h" |
72 | #include "ip_header.h" |
75 | #include "ip_header.h" |
73 | #include "ip_messages.h" |
76 | #include "ip_messages.h" |
74 | #include "ip_module.h" |
77 | #include "ip_module.h" |
75 | 78 | ||
- | 79 | /** Default IP version. |
|
- | 80 | */ |
|
76 | #define DEFAULT_IPV 4 |
81 | #define DEFAULT_IPV 4 |
- | 82 | ||
- | 83 | /** Minimum IP packet content. |
|
- | 84 | */ |
|
77 | #define IP_MIN_CONTENT 576 |
85 | #define IP_MIN_CONTENT 576 |
78 | 86 | ||
- | 87 | /** ARP module name. |
|
- | 88 | */ |
|
79 | #define ARP_NAME "arp" |
89 | #define ARP_NAME "arp" |
- | 90 | ||
- | 91 | /** ARP module filename. |
|
- | 92 | */ |
|
80 | #define ARP_FILENAME "/srv/arp" |
93 | #define ARP_FILENAME "/srv/arp" |
81 | 94 | ||
- | 95 | /** IP packet address length. |
|
- | 96 | */ |
|
82 | #define IP_ADDR sizeof( in_addr_t ) |
97 | #define IP_ADDR sizeof( in_addr_t ) |
- | 98 | ||
- | 99 | /** IP packet prefix length. |
|
- | 100 | */ |
|
83 | #define IP_PREFIX sizeof( ip_header_t ) |
101 | #define IP_PREFIX sizeof( ip_header_t ) |
- | 102 | ||
- | 103 | /** IP packet suffix length. |
|
- | 104 | */ |
|
84 | #define IP_SUFFIX 0 |
105 | #define IP_SUFFIX 0 |
- | 106 | ||
- | 107 | /** IP packet maximum content length. |
|
- | 108 | */ |
|
85 | #define IP_MAX_CONTENT 65535 |
109 | #define IP_MAX_CONTENT 65535 |
- | 110 | ||
- | 111 | /** Returns the actual IP header length. |
|
- | 112 | * @param header The IP packet header. Input parameter. |
|
- | 113 | */ |
|
86 | #define IP_HEADER_LENGTH( header ) (( header )->ihl * 4u ) |
114 | #define IP_HEADER_LENGTH( header ) (( header )->ihl * 4u ) |
- | 115 | ||
- | 116 | /** Returns the actual IP packet total length. |
|
- | 117 | * @param header The IP packet header. Input parameter. |
|
- | 118 | */ |
|
87 | #define IP_TOTAL_LENGTH( header ) ntohs(( header )->total_length ) |
119 | #define IP_TOTAL_LENGTH( header ) ntohs(( header )->total_length ) |
- | 120 | ||
- | 121 | /** Returns the actual IP packet data length. |
|
- | 122 | * @param header The IP packet header. Input parameter. |
|
- | 123 | */ |
|
88 | #define IP_HEADER_DATA_LENGTH( header ) ( IP_TOTAL_LENGTH( header ) - IP_HEADER_LENGTH( header )) |
124 | #define IP_HEADER_DATA_LENGTH( header ) ( IP_TOTAL_LENGTH( header ) - IP_HEADER_LENGTH( header )) |
- | 125 | ||
- | 126 | /** Returns the IP packet header checksum. |
|
- | 127 | * @param header The IP packet header. Input parameter. |
|
- | 128 | */ |
|
89 | #define IP_HEADER_CHECKSUM( header ) ( htons( ip_checksum(( uint8_t * )( header ), IP_HEADER_LENGTH( header )))) |
129 | #define IP_HEADER_CHECKSUM( header ) ( htons( ip_checksum(( uint8_t * )( header ), IP_HEADER_LENGTH( header )))) |
90 | 130 | ||
- | 131 | /** IP header checksum value for computed zero checksum. |
|
91 | //zero is returned as 0xFFFF (not flipped) |
132 | * Zero is returned as 0xFFFF (not flipped) |
- | 133 | */ |
|
92 | #define IP_HEADER_CHECKSUM_ZERO 0xFFFFu |
134 | #define IP_HEADER_CHECKSUM_ZERO 0xFFFFu |
93 | 135 | ||
- | 136 | /** IP global data. |
|
- | 137 | */ |
|
94 | ip_globals_t ip_globals; |
138 | ip_globals_t ip_globals; |
95 | 139 | ||
96 | DEVICE_MAP_IMPLEMENT( ip_netifs, ip_netif_t ) |
140 | DEVICE_MAP_IMPLEMENT( ip_netifs, ip_netif_t ) |
97 | 141 | ||
98 | INT_MAP_IMPLEMENT( ip_protos, ip_proto_t ) |
142 | INT_MAP_IMPLEMENT( ip_protos, ip_proto_t ) |
99 | 143 | ||
100 | GENERIC_FIELD_IMPLEMENT( ip_routes, ip_route_t ) |
144 | GENERIC_FIELD_IMPLEMENT( ip_routes, ip_route_t ) |
101 | 145 | ||
- | 146 | /** Updates the device content length according to the new MTU value. |
|
- | 147 | * @param device_id The device identifier. Input parameter. |
|
- | 148 | * @param mtu The new mtu value. Input parameter. |
|
- | 149 | * @returns EOK on success. |
|
- | 150 | * @returns ENOENT if device is not found. |
|
- | 151 | */ |
|
102 | int ip_mtu_changed_msg( device_id_t device_id, size_t mtu ); |
152 | int ip_mtu_changed_message( device_id_t device_id, size_t mtu ); |
- | 153 | ||
- | 154 | /** Updates the device state. |
|
- | 155 | * @param device_id The device identifier. Input parameter. |
|
- | 156 | * @param state The new state value. Input parameter. |
|
- | 157 | * @returns EOK on success. |
|
- | 158 | * @returns ENOENT if device is not found. |
|
- | 159 | */ |
|
103 | int ip_device_state_msg( int il_phone, device_id_t device_id, device_state_t state ); |
160 | int ip_device_state_message( device_id_t device_id, device_state_t state ); |
- | 161 | ||
104 | int ip_register( int protocol, services_t service, int phone, tl_received_msg_t tl_received_msg ); |
162 | int ip_register( int protocol, services_t service, int phone, tl_received_msg_t tl_received_msg ); |
- | 163 | ||
- | 164 | /** Initializes a new network interface specific data. |
|
- | 165 | * Connects to the network interface layer module, reads the netif configuration, starts an ARP module if needed and sets the netif routing table. |
|
- | 166 | * The device identifier and the nil service has to be set. |
|
- | 167 | * @param ip_netif Network interface specific data. Input/output parameter. |
|
- | 168 | * @returns EOK on success. |
|
- | 169 | * @returns ENOTSUP if DHCP is configured. |
|
- | 170 | * @returns ENOTSUP if IPv6 is configured. |
|
- | 171 | * @returns EINVAL if any of the addresses is invalid. |
|
- | 172 | * @returns EINVAL if the used ARP module is not known. |
|
- | 173 | * @returns ENOMEM if there is not enough memory left. |
|
- | 174 | * @returns Other error codes as defined for the net_get_device_conf_req() function. |
|
- | 175 | * @returns Other error codes as defined for the bind_service() function. |
|
- | 176 | * @returns Other error codes as defined for the specific arp_device_req() function. |
|
- | 177 | * @returns Other error codes as defined for the nil_packet_size_req() function. |
|
- | 178 | */ |
|
105 | int ip_netif_initialize( ip_netif_ref ip_netif ); |
179 | int ip_netif_initialize( ip_netif_ref ip_netif ); |
106 | 180 | ||
107 | int ip_send_route( packet_t packet, ip_netif_ref netif, ip_route_ref route, in_addr_t * src, in_addr_t dest ); |
181 | int ip_send_route( packet_t packet, ip_netif_ref netif, ip_route_ref route, in_addr_t * src, in_addr_t dest ); |
108 | int ip_prepare_packet( in_addr_t * source, in_addr_t dest, packet_t packet, measured_string_ref destination ); |
182 | int ip_prepare_packet( in_addr_t * source, in_addr_t dest, packet_t packet, measured_string_ref destination ); |
109 | 183 | ||
Line 115... | Line 189... | ||
115 | 189 | ||
116 | in_addr_t * ip_netif_addr( ip_netif_ref netif ); |
190 | in_addr_t * ip_netif_addr( ip_netif_ref netif ); |
117 | ip_route_ref ip_find_route( in_addr_t destination ); |
191 | ip_route_ref ip_find_route( in_addr_t destination ); |
118 | ip_route_ref ip_netif_find_route( ip_netif_ref netif, in_addr_t destination ); |
192 | ip_route_ref ip_netif_find_route( ip_netif_ref netif, in_addr_t destination ); |
119 | 193 | ||
- | 194 | /** Processes the received IP packet. |
|
- | 195 | * @param device_id The source device identifier. Input parameter. |
|
- | 196 | * @param packet The received packet. Input/output parameter. |
|
- | 197 | * @returns EOK on success and the packet is no longer needed. |
|
- | 198 | * @returns EINVAL if the packet is too small to carry the IP packet. |
|
- | 199 | * @returns EINVAL if the received address lengths differs from the registered values. |
|
- | 200 | * @returns ENOENT if the device is not found in the cache. |
|
- | 201 | * @returns ENOENT if the protocol for the device is not found in the cache. |
|
- | 202 | * @returns ENOMEM if there is not enough memory left. |
|
- | 203 | */ |
|
120 | int ip_received_msg( device_id_t device_id, packet_t packet ); |
204 | int ip_receive_message( device_id_t device_id, packet_t packet ); |
- | 205 | ||
121 | int ip_process_packet( device_id_t device_id, packet_t packet ); |
206 | int ip_process_packet( device_id_t device_id, packet_t packet ); |
122 | in_addr_t ip_get_destination( ip_header_ref header ); |
207 | in_addr_t ip_get_destination( ip_header_ref header ); |
123 | int ip_deliver_local( device_id_t device_id, packet_t packet, ip_header_ref header ); |
208 | int ip_deliver_local( device_id_t device_id, packet_t packet, ip_header_ref header ); |
124 | 209 | ||
125 | /** Computes the ip header checksum. |
210 | /** Computes the ip header checksum. |
Line 140... | Line 225... | ||
140 | 225 | ||
141 | // flip, zero is returned as 0xFFFF (not flipped) |
226 | // flip, zero is returned as 0xFFFF (not flipped) |
142 | return ( ~ checksum ) ? ~ checksum : IP_HEADER_CHECKSUM_ZERO; |
227 | return ( ~ checksum ) ? ~ checksum : IP_HEADER_CHECKSUM_ZERO; |
143 | } |
228 | } |
144 | 229 | ||
145 | /** Initializes the module. |
- | |
146 | */ |
- | |
147 | int ip_initialize( async_client_conn_t client_connection ){ |
230 | int ip_initialize( async_client_conn_t client_connection ){ |
148 | ERROR_DECLARE; |
231 | ERROR_DECLARE; |
149 | 232 | ||
150 | fibril_rwlock_initialize( & ip_globals.lock ); |
233 | fibril_rwlock_initialize( & ip_globals.lock ); |
151 | fibril_rwlock_write_lock( & ip_globals.lock ); |
234 | fibril_rwlock_write_lock( & ip_globals.lock ); |
Line 229... | Line 312... | ||
229 | char * data; |
312 | char * data; |
230 | int index; |
313 | int index; |
231 | ip_route_ref route; |
314 | ip_route_ref route; |
232 | in_addr_t gateway; |
315 | in_addr_t gateway; |
233 | 316 | ||
234 | ip_netif->arp = 0; |
317 | ip_netif->arp = NULL; |
235 | route = NULL; |
318 | route = NULL; |
236 | configuration = & names[ 0 ]; |
319 | configuration = & names[ 0 ]; |
237 | // get configuration |
320 | // get configuration |
238 | ERROR_PROPAGATE( net_get_device_conf_req( ip_globals.net_phone, ip_netif->device_id, & configuration, count, & data )); |
321 | ERROR_PROPAGATE( net_get_device_conf_req( ip_globals.net_phone, ip_netif->device_id, & configuration, count, & data )); |
239 | if( configuration ){ |
322 | if( configuration ){ |
Line 321... | Line 404... | ||
321 | ip_globals.gateway.netif = ip_netif; |
404 | ip_globals.gateway.netif = ip_netif; |
322 | } |
405 | } |
323 | return EOK; |
406 | return EOK; |
324 | } |
407 | } |
325 | 408 | ||
326 | int ip_mtu_changed_msg( device_id_t device_id, size_t mtu ){ |
409 | int ip_mtu_changed_message( device_id_t device_id, size_t mtu ){ |
327 | ip_netif_ref netif; |
410 | ip_netif_ref netif; |
328 | 411 | ||
329 | fibril_rwlock_write_lock( & ip_globals.netifs_lock ); |
412 | fibril_rwlock_write_lock( & ip_globals.netifs_lock ); |
330 | netif = ip_netifs_find( & ip_globals.netifs, device_id ); |
413 | netif = ip_netifs_find( & ip_globals.netifs, device_id ); |
331 | if( ! netif ){ |
414 | if( ! netif ){ |
Line 336... | Line 419... | ||
336 | printf( "ip - device %d changed mtu to %d\n\n", device_id, mtu ); |
419 | printf( "ip - device %d changed mtu to %d\n\n", device_id, mtu ); |
337 | fibril_rwlock_write_unlock( & ip_globals.netifs_lock ); |
420 | fibril_rwlock_write_unlock( & ip_globals.netifs_lock ); |
338 | return EOK; |
421 | return EOK; |
339 | } |
422 | } |
340 | 423 | ||
341 | int ip_device_state_msg( int il_phone, device_id_t device_id, device_state_t state ){ |
424 | int ip_device_state_message( device_id_t device_id, device_state_t state ){ |
342 | // ERROR_DECLARE; |
425 | // ERROR_DECLARE; |
343 | 426 | ||
344 | /* measured_string_t address; |
427 | /* measured_string_t address; |
345 | measured_string_ref translation; |
428 | measured_string_ref translation; |
346 | char * data; |
429 | char * data; |
Line 616... | Line 699... | ||
616 | return ip_register( IL_GET_PROTO( call ), IL_GET_SERVICE( call ), IPC_GET_PHONE( call ), NULL ); |
699 | return ip_register( IL_GET_PROTO( call ), IL_GET_SERVICE( call ), IPC_GET_PHONE( call ), NULL ); |
617 | case NET_IL_SEND: |
700 | case NET_IL_SEND: |
618 | ERROR_PROPAGATE( packet_translate( ip_globals.net_phone, & packet, IPC_GET_PACKET( call ))); |
701 | ERROR_PROPAGATE( packet_translate( ip_globals.net_phone, & packet, IPC_GET_PACKET( call ))); |
619 | return ip_send_msg( 0, IPC_GET_DEVICE( call ), packet, 0 ); |
702 | return ip_send_msg( 0, IPC_GET_DEVICE( call ), packet, 0 ); |
620 | case NET_IL_DEVICE_STATE: |
703 | case NET_IL_DEVICE_STATE: |
621 | return ip_device_state_msg( 0, IPC_GET_DEVICE( call ), IPC_GET_STATE( call )); |
704 | return ip_device_state_message( IPC_GET_DEVICE( call ), IPC_GET_STATE( call )); |
622 | case NET_IL_RECEIVED: |
705 | case NET_IL_RECEIVED: |
623 | ERROR_PROPAGATE( packet_translate( ip_globals.net_phone, & packet, IPC_GET_PACKET( call ))); |
706 | ERROR_PROPAGATE( packet_translate( ip_globals.net_phone, & packet, IPC_GET_PACKET( call ))); |
624 | return ip_received_msg( IPC_GET_DEVICE( call ), packet ); |
707 | return ip_receive_message( IPC_GET_DEVICE( call ), packet ); |
625 | case NET_IP_ADD_ROUTE: |
708 | case NET_IP_ADD_ROUTE: |
626 | return ip_add_route_req( 0, IPC_GET_DEVICE( call ), IP_GET_ADDRESS( call ), IP_GET_NETMASK( call ), IP_GET_GATEWAY( call )); |
709 | return ip_add_route_req( 0, IPC_GET_DEVICE( call ), IP_GET_ADDRESS( call ), IP_GET_NETMASK( call ), IP_GET_GATEWAY( call )); |
627 | case NET_IP_SET_GATEWAY: |
710 | case NET_IP_SET_GATEWAY: |
628 | return ip_set_gateway_req( 0, IPC_GET_DEVICE( call ), IP_GET_GATEWAY( call )); |
711 | return ip_set_gateway_req( 0, IPC_GET_DEVICE( call ), IP_GET_GATEWAY( call )); |
629 | case NET_IL_PACKET_SPACE: |
712 | case NET_IL_PACKET_SPACE: |
630 | ERROR_PROPAGATE( ip_packet_size_req( 0, IPC_GET_DEVICE( call ), IPC_SET_ADDR( answer ), IPC_SET_PREFIX( answer ), IPC_SET_CONTENT( answer ), IPC_SET_SUFFIX( answer ))); |
713 | ERROR_PROPAGATE( ip_packet_size_req( 0, IPC_GET_DEVICE( call ), IPC_SET_ADDR( answer ), IPC_SET_PREFIX( answer ), IPC_SET_CONTENT( answer ), IPC_SET_SUFFIX( answer ))); |
631 | * answer_count = 3; |
714 | * answer_count = 3; |
632 | return EOK; |
715 | return EOK; |
633 | case NET_IL_MTU_CHANGED: |
716 | case NET_IL_MTU_CHANGED: |
634 | return ip_mtu_changed_msg( IPC_GET_DEVICE( call ), IPC_GET_MTU( call )); |
717 | return ip_mtu_changed_message( IPC_GET_DEVICE( call ), IPC_GET_MTU( call )); |
635 | } |
718 | } |
636 | return ENOTSUP; |
719 | return ENOTSUP; |
637 | } |
720 | } |
638 | 721 | ||
639 | int ip_packet_size_req( int ip_phone, device_id_t device_id, size_t * addr_len, size_t * prefix, size_t * content, size_t * suffix ){ |
722 | int ip_packet_size_req( int ip_phone, device_id_t device_id, size_t * addr_len, size_t * prefix, size_t * content, size_t * suffix ){ |
Line 900... | Line 983... | ||
900 | last->ihl = length / 4; |
983 | last->ihl = length / 4; |
901 | } |
984 | } |
902 | last->header_checksum = 0; |
985 | last->header_checksum = 0; |
903 | } |
986 | } |
904 | 987 | ||
905 | int ip_received_msg( device_id_t device_id, packet_t packet ){ |
988 | int ip_receive_message( device_id_t device_id, packet_t packet ){ |
906 | packet_t next; |
989 | packet_t next; |
907 | 990 | ||
908 | do{ |
991 | do{ |
909 | next = pq_detach( packet ); |
992 | next = pq_detach( packet ); |
910 | if( ip_process_packet( device_id, packet ) != EOK ){ |
993 | if( ip_process_packet( device_id, packet ) != EOK ){ |