Subversion Repositories Kolibri OS

Compare Revisions

Ignore whitespace Rev 2730 → Rev 2731

/kernel/branches/net/network/IPv4.inc
1,6 → 1,6
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;;
;; Copyright (C) KolibriOS team 2004-2011. All rights reserved. ;;
;; Copyright (C) KolibriOS team 2004-2012. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;;
;; ;;
;; IPv4.INC ;;
18,42 → 18,42
 
$Revision$
 
MAX_FRAGMENTS = 64
MAX_IP = MAX_NET_DEVICES
IP_MAX_INTERFACES = MAX_IP
MAX_FRAGMENTS = 64
MAX_IP = MAX_NET_DEVICES
IP_MAX_INTERFACES = MAX_IP
 
struct IPv4_header
 
VersionAndIHL db ? ; Version[0-3 bits] and IHL(header length)[4-7 bits]
TypeOfService db ? ; precedence [7-5] minimize delay [4], maximize throughput [3], maximize riliability [2] minimize momentary cost [1] and zero [0]
TotalLength dw ?
Identification dw ?
FlagsAndFragmentOffset dw ? ; Flags[0-2] and FragmentOffset[3-15]
TimeToLive db ? ;
Protocol db ?
HeaderChecksum dw ?
SourceAddress dd ?
DestinationAddress dd ?
VersionAndIHL db ? ; Version[0-3 bits] and IHL(header length)[4-7 bits]
TypeOfService db ? ; precedence [7-5] minimize delay [4], maximize throughput [3], maximize riliability [2] minimize momentary cost [1] and zero [0]
TotalLength dw ?
Identification dw ?
FlagsAndFragmentOffset dw ? ; Flags[0-2] and FragmentOffset[3-15]
TimeToLive db ? ;
Protocol db ?
HeaderChecksum dw ?
SourceAddress dd ?
DestinationAddress dd ?
 
ends
 
struct FRAGMENT_slot
 
ttl dw ? ; Time to live for this entry, 0 for empty slot's
id dw ? ; Identification field from IP header
SrcIP dd ? ; .. from IP header
DstIP dd ? ; .. from IP header
ptr dd ? ; Pointer to first packet
ttl dw ? ; Time to live for this entry, 0 for empty slot's
id dw ? ; Identification field from IP header
SrcIP dd ? ; .. from IP header
DstIP dd ? ; .. from IP header
ptr dd ? ; Pointer to first packet
 
ends
 
struct FRAGMENT_entry ; This structure will replace the ethernet header in fragmented ip packets
struct FRAGMENT_entry ; This structure will replace the ethernet header in fragmented ip packets
 
PrevPtr dd ? ; Pointer to previous fragment entry (-1 for first packet)
NextPtr dd ? ; Pointer to next fragment entry (-1 for last packet)
Owner dd ? ; Pointer to structure of driver
rb 2 ; to match ethernet header size ; TODO: fix this hack
; Ip header begins here (we will need the IP header to re-construct the complete packet)
PrevPtr dd ? ; Pointer to previous fragment entry (-1 for first packet)
NextPtr dd ? ; Pointer to next fragment entry (-1 for last packet)
Owner dd ? ; Pointer to structure of driver
rb 2 ; to match ethernet header size ;;; FIXME
; Ip header begins here (we will need the IP header to re-construct the complete packet)
ends
 
 
60,15 → 60,16
align 4
uglobal
 
IP_LIST rd MAX_IP
SUBNET_LIST rd MAX_IP
DNS_LIST rd MAX_IP
GATEWAY_LIST rd MAX_IP
IP_LIST rd MAX_IP
SUBNET_LIST rd MAX_IP
DNS_LIST rd MAX_IP
GATEWAY_LIST rd MAX_IP
BROADCAST_LIST rd MAX_IP
 
IP_PACKETS_TX rd MAX_IP
IP_PACKETS_RX rd MAX_IP
IP_PACKETS_TX rd MAX_IP
IP_PACKETS_RX rd MAX_IP
 
FRAGMENT_LIST rb MAX_FRAGMENTS * sizeof.FRAGMENT_slot
FRAGMENT_LIST rb MAX_FRAGMENTS * sizeof.FRAGMENT_slot
endg
 
 
83,13 → 84,9
 
xor eax, eax
mov edi, IP_LIST
mov ecx, 4*MAX_IP
mov ecx, 7*MAX_IP + (sizeof.FRAGMENT_slot*MAX_FRAGMENTS)/4
rep stosd
 
mov edi, FRAGMENT_LIST
mov ecx, sizeof.FRAGMENT_slot*MAX_FRAGMENTS/4 + 2*MAX_IP
rep stosd
 
}
 
 
100,20 → 97,27
;-----------------------------------------------------------------
macro IPv4_decrease_fragment_ttls {
 
local .loop
local .loop, .next
 
mov esi, FRAGMENT_LIST
mov ecx, MAX_FRAGMENTS
.loop:
cmp [esi + FRAGMENT_slot.ttl], 0
je .try_next
je .next
dec [esi + FRAGMENT_slot.ttl]
jnz .try_next
jz .died
.next:
add esi, sizeof.FRAGMENT_slot
dec ecx
jnz .loop
jmp .done
 
.died:
DEBUGF 1,"Fragment slot timed-out!\n"
;;; TODO: clear all entry's of timed-out slot
.try_next:
add esi, 4
loop .loop
jmp .next
 
.done:
}
 
 
186,7 → 190,7
;
; IPv4_input:
;
; Will check if IP Packet isnt damaged
; Will check if IPv4 Packet isnt damaged
; and call appropriate handler. (TCP/UDP/ICMP/..)
;
; It will also re-construct fragmented packets
194,27 → 198,23
; IN: Pointer to buffer in [esp]
; size of buffer in [esp+4]
; pointer to device struct in ebx
; pointer to IP header in edx
; size of IP packet in ecx
; pointer to IPv4 header in edx
; size of IPv4 packet in ecx
; OUT: /
;
;-----------------------------------------------------------------
align 4
IPv4_input: ; TODO: add code for raw sockets
IPv4_input: ; TODO: add IPv4 raw sockets support
 
DEBUGF 1,"IPv4_input, packet from: %u.%u.%u.%u ",\
[edx + IPv4_header.SourceAddress]:1,[edx + IPv4_header.SourceAddress + 1]:1,[edx + IPv4_header.SourceAddress + 2]:1,[edx + IPv4_header.SourceAddress + 3]:1
[edx + IPv4_header.SourceAddress + 0]:1,[edx + IPv4_header.SourceAddress + 1]:1,\
[edx + IPv4_header.SourceAddress + 2]:1,[edx + IPv4_header.SourceAddress + 3]:1
DEBUGF 1,"to: %u.%u.%u.%u\n",\
[edx + IPv4_header.DestinationAddress]:1,[edx + IPv4_header.DestinationAddress + 1]:1,[edx + IPv4_header.DestinationAddress + 2]:1,[edx + IPv4_header.DestinationAddress + 3]:1
[edx + IPv4_header.DestinationAddress + 0]:1,[edx + IPv4_header.DestinationAddress + 1]:1,\
[edx + IPv4_header.DestinationAddress + 2]:1,[edx + IPv4_header.DestinationAddress + 3]:1
 
;-------------------------------------------
; Check if the packet still has time to live
 
cmp byte [edx + IPv4_header.TimeToLive], 0
je .dump
 
;-------------------------------
; Now, re-calculate the checksum
; re-calculate the checksum
 
IPv4_checksum edx
jnz .dump ; if checksum isn't valid then dump packet
229,38 → 229,35
 
; check if it matches local ip
 
mov eax, [IP_LIST+edi]
cmp [edx + IPv4_header.DestinationAddress], eax
mov eax, [edx + IPv4_header.DestinationAddress]
cmp eax, [IP_LIST+edi]
je .ip_ok
 
; check for broadcast
; check for broadcast (IP or (not SUBNET))
 
mov eax, [SUBNET_LIST+edi]
not eax
or eax, [IP_LIST+edi]
cmp [edx + IPv4_header.DestinationAddress], eax
cmp eax, [BROADCAST_LIST+edi]
je .ip_ok
 
; or a special broadcast
; or a special broadcast (255.255.255.255)
 
cmp [edx + IPv4_header.DestinationAddress], -1
cmp eax, 0xffffffff
je .ip_ok
 
; maybe it's a multicast then
; maybe it's a multicast (224.0.0.0/4)
 
mov eax, [edx + IPv4_header.DestinationAddress]
and eax, 0xff000000
; cmp eax, 224 shl 24
; je .ip_ok
and eax, 0x0fffffff
cmp eax, 224
je .ip_ok
 
; or a loopback address
; or a loopback address (127.0.0.0/8)
 
cmp eax, 127 shl 24
and eax, 0x00ffffff
cmp eax, 127
je .ip_ok
 
; or it's not meant for us..
; or it's just not meant for us.. :(
 
DEBUGF 2,"Destination address does not match!\n"
DEBUGF 2,"IPv4_input - Destination address does not match!\n"
jmp .dump
 
;------------------------
288,11 → 285,11
shl esi, 2 ;
 
movzx ecx, [edx + IPv4_header.TotalLength] ; Calculate length of encapsulated Packet
xchg cl , ch ;
xchg cl, ch ;
sub ecx, esi ;
 
lea edi, [edx + IPv4_header.SourceAddress] ; make edi ptr to source and dest IPv4 address
mov al , [edx + IPv4_header.Protocol]
mov al, [edx + IPv4_header.Protocol]
add esi, edx ; make esi ptr to data
 
cmp al, IP_PROTO_TCP
304,10 → 301,10
cmp al, IP_PROTO_ICMP
je ICMP_input
 
DEBUGF 2,"unknown Internet protocol: %u\n", al
DEBUGF 2,"IPv4_input - unknown protocol: %u\n", al
 
.dump:
DEBUGF 2,"IP_Handler - dumping\n"
DEBUGF 2,"IPv4_input - dumping\n"
; inc [dumped_rx_count]
call kernel_free
add esp, 4 ; pop (balance stack)
499,16 → 496,10
mov edx, eax
mov [edx + IPv4_header.TotalLength], cx
add esp, 8
xchg cl, ch
push ecx
 
xchg cl, ch ;
 
push ecx ;;;;
push eax ;;;;
 
; mov esi, edx ; This prints the IP packet to the debug board (usefull when using serial output debug..)
; ;
; packet_to_debug
 
push eax
jmp .handle_it ; edx = buf ptr, ecx = size, [esp] buf ptr, [esp+4], total size, ebx=device ptr
 
.destroy_slot_pop:
527,7 → 518,7
; find fragment slot
;
; IN: pointer to fragmented packet in edx
; OUT: pointer to slot in edi, -1 on error
; OUT: pointer to slot in esi, -1 on error
;
;-----------------------------------------------------------------
align 4
885,7 → 876,8
je .found_it
.next:
add edi, 4
loop .loop
dec ecx
jnz .loop
 
.invalid:
xor edi, edi ; if none found, use device 0 as default device
967,6 → 959,13
 
.write_ip:
mov [IP_LIST + eax], ecx
 
; pre-calculate the local broadcast address
mov ebx, [SUBNET_LIST + eax]
not ebx
or ecx, ebx
mov [BROADCAST_LIST + eax], ecx
 
xor eax, eax
ret
 
985,6 → 984,13
 
.write_subnet:
mov [SUBNET_LIST + eax], ecx
 
; pre-calculate the local broadcast address
mov ebx, [IP_LIST + eax]
not ecx
or ecx, ebx
mov [BROADCAST_LIST + eax], ecx
 
xor eax, eax
ret