compile netcfg on unix

fixed bug in netcfg created in last revision
netcfg gives error msg when driver is not loaded
zeroconfig now works with latest version of libini
also fixed use of static and link-local ip in zeroconfig
initial IPv4 variables are now 0.0.0.0 instead of 255.255.255.255
created kernel function that shows number of active network devices 
fixed the use of temp mac variable in IPV4.inc (variable is now in stack)
rewrite of ARP code, needs full testing/debugging (new application needed: ARP manager)
port numbers are now in INET byte order, as is in posix standards

git-svn-id: svn://kolibrios.org@1196 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
hidnplayr 2009-10-05 20:47:27 +00:00
parent 00978e27e3
commit 602924a5b5
13 changed files with 2327 additions and 711 deletions

View File

@ -38,8 +38,8 @@ button: ; button
jne @f jne @f
mcall -1 ; close this program mcall -1 ; close this program
@@: @@:
cmp eax,0x0000fe00 cmp eax,0x0000ff00
jg @f jg load_drv
cmp ah, 4 cmp ah, 4
je hook je hook
@ -51,25 +51,17 @@ button: ; button
je unload je unload
jmp still jmp still
@@:
load_drv:
shr eax, 16 shr eax, 16
mov word [selected], ax mov word [selected], ax
call load_drv
call draw_window
jmp still
load_drv:
; mov ax , [selected]
test ax , ax
jz still
mov bl , 6 ; get a dword mov bl , 6 ; get a dword
mov bh , ah ; bus mov bh , ah ; bus
mov ch , al ; dev mov ch , al ; dev
mov cl , 0 ; offset to device/vendor id mov cl , 0 ; offset to device/vendor id
mcall 62 ; get ID's mcall 62 ; get ID's
mov word [PCI_Vendor], ax mov word [PCI_Vendor], ax
shr eax, 16 shr eax, 16
@ -77,11 +69,19 @@ load_drv:
call get_drv_ptr call get_drv_ptr
mov ecx, eax mov ecx, eax
mcall 68, 16 mcall 68, 16
mov [IOCTL.handle], eax mov [IOCTL.handle], eax
ret call draw_window
cmp [IOCTL.handle], 0
jne still
mcall 4, 20 shl 16 + 30, 1 shl 31 + 0x00ff0000 , load_error
jmp still
hook: hook:
mov ax , [selected] mov ax , [selected]
@ -97,30 +97,28 @@ hook:
mov [IOCTL.out_size], 0 mov [IOCTL.out_size], 0
mov [IOCTL.output], 0 mov [IOCTL.output], 0
mcall 68, 17, IOCTL mcall 68, 17, IOCTL
mov byte[drivernumber], al mov byte[drivernumber], al
jmp still
reset: reset:
movzx ebx, byte[drivernumber] movzx ebx, byte[drivernumber]
mcall 73,,2 mcall 73,,2
ret jmp still
unload: unload:
movzx ebx, byte[drivernumber] movzx ebx, byte[drivernumber]
mcall 73,,3 mcall 73,,3
ret jmp still
draw_window: draw_window:
mcall 12, 1 ; start of draw mcall 12, 1 ; start of draw
mcall 0, dword [Form], dword [Form + 4], 0x13ffffff, 0x805080d0, title mcall 0, dword [Form], dword [Form + 4], 0x13ffffff, 0x805080d0, title
; mcall 73, 1,
; mov ecx, eax
; mcall 47, 1 shl 18, , 50 shl 16 + 10, 0x00000000
call Get_PCI_Info ; get pci version and last bus, scan for and draw each pci device call Get_PCI_Info ; get pci version and last bus, scan for and draw each pci device
cmp edx, 20 shl 16 + 110 cmp edx, 20 shl 16 + 110
@ -128,8 +126,9 @@ draw_window:
mcall 4, 20 shl 16 + 100, 1 shl 31 + 0x00000000 , caption mcall 4, 20 shl 16 + 100, 1 shl 31 + 0x00000000 , caption
mov ax , [selected] cmp [selected], 0
test ax, ax jz .done
cmp [IOCTL.handle] ,0
jz .done jz .done
mcall 8, 18 shl 16 + 100, 35 shl 16 + 18, 4, 0x00007f00 mcall 8, 18 shl 16 + 100, 35 shl 16 + 18, 4, 0x00007f00
@ -144,7 +143,7 @@ draw_window:
jmp .done jmp .done
.nonefound : .nonefound:
mcall 4, 20 shl 16 + 30, 1 shl 31 + 0x00ff0000 , nonefound mcall 4, 20 shl 16 + 30, 1 shl 31 + 0x00ff0000 , nonefound
.done: .done:
mcall 12, 2 ; end of draw mcall 12, 2 ; end of draw
@ -379,8 +378,8 @@ get_drv_ptr:
driverfound: driverfound:
ret ret
include 'VENDORS.INC' include 'vendors.inc'
include 'DRIVERS.INC' include 'drivers.inc'
;------------------------------------------------------------------ ;------------------------------------------------------------------
; DATA AREA ; DATA AREA
DATA DATA
@ -404,6 +403,7 @@ btn_stop db 'Stop device',0
lbl_none db 'none',0 lbl_none db 'none',0
;lbl_unknown db 'unknown',0 ;lbl_unknown db 'unknown',0
;lbl_ethernet db 'ethernet',0 ;lbl_ethernet db 'ethernet',0
load_error db 'Could not load driver!',0
devicename db 'test' devicename db 'test'
rb 64 rb 64

View File

@ -42,14 +42,11 @@ RATE_LIMIT_INTERVAL equ 60 ; seconds (delay between successive attempts)
DEFEND_INTERVAL equ 10 ; seconds (min. wait between defensive ARPs) DEFEND_INTERVAL equ 10 ; seconds (min. wait between defensive ARPs)
AF_INET4 equ 2 ;;;;; AF_INET4 equ 2 ;;;;;
IP_PROTO_UDP equ 17 IP_PROTO_UDP equ 17
include '../proc32.inc' include '../proc32.inc'
include '../macros.inc' include '../macros.inc'
include '../debug-fdo.inc' include '../debug-fdo.inc'
@ -197,22 +194,22 @@ START: ; start of execution
invoke ini.get_str, path, str_ipconfig, str_ip, inibuf, 16, 0 invoke ini.get_str, path, str_ipconfig, str_ip, inibuf, 16, 0
mov edx, inibuf mov edx, inibuf
call Ip2dword call Ip2dword
mcall 73, 3, edx mcall 75, 3, edx
invoke ini.get_str, path, str_ipconfig, str_gateway, inibuf, 16, 0 invoke ini.get_str, path, str_ipconfig, str_gateway, inibuf, 16, 0
mov edx, inibuf mov edx, inibuf
call Ip2dword call Ip2dword
mcall 73, 9, edx mcall 75, 9, edx
invoke ini.get_str, path, str_ipconfig, str_dns, inibuf, 16, 0 invoke ini.get_str, path, str_ipconfig, str_dns, inibuf, 16, 0
mov edx, inibuf mov edx, inibuf
call Ip2dword call Ip2dword
mcall 73, 7, edx mcall 75, 7, edx
invoke ini.get_str, path, str_ipconfig, str_subnet, inibuf, 16, 0 invoke ini.get_str, path, str_ipconfig, str_subnet, inibuf, 16, 0
mov edx, inibuf mov edx, inibuf
call Ip2dword call Ip2dword
mcall 73, 5, edx mcall 75, 5, edx
mcall -1 mcall -1
@ -478,11 +475,11 @@ link_local:
call random call random
mov ecx,0xfea9 ; IP 169.254.0.0 link local net, see RFC3927 mov ecx,0xfea9 ; IP 169.254.0.0 link local net, see RFC3927
mov cx,ax mov cx,ax
mcall 73, 3, ecx ; mask is 255.255.0.0 mcall 75, 3, ecx ; mask is 255.255.0.0
DEBUGF 1,"Link Local IP assinged: 169.254.%u.%u\n",[generator+2]:1,[generator+3]:1 DEBUGF 1,"Link Local IP assinged: 169.254.%u.%u\n",[generator+2]:1,[generator+3]:1
mcall 73, 5, 0xffff mcall 75, 5, 0xffff
mcall 73, 9, 0x0 mcall 75, 9, 0x0
mcall 73, 7, 0x0 mcall 75, 7, 0x0
mcall 5, PROBE_WAIT*100 mcall 5, PROBE_WAIT*100
@ -559,7 +556,7 @@ library \
libini,'libini.obj' libini,'libini.obj'
import libini, \ import libini, \
ini.get_str,'ini.get_str' ini.get_str,'ini_get_str'
include_debug_strings include_debug_strings
@ -575,7 +572,7 @@ str_type db 'type',0
sockaddr1: sockaddr1:
dw AF_INET4 dw AF_INET4
dw 68 ; local port dw 68 shl 8 ; local port
dd 0 ; local IP dd 0 ; local IP
rb 10 rb 10
@ -584,7 +581,7 @@ sockaddr1:
sockaddr2: sockaddr2:
dw AF_INET4 dw AF_INET4
dw 67 ; destination port dw 67 shl 8 ; destination port
dd -1 ; destination IP dd -1 ; destination IP
rb 10 rb 10

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved.
;; PROGRAMMING: ;; PROGRAMMING:
;; Ivan Poddubny ;; Ivan Poddubny
;; Marat Zakiyanov (Mario79) ;; Marat Zakiyanov (Mario79)

View File

@ -1,22 +1,21 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; ARP.INC ;; ;; ARP.INC ;;
;; ;; ;; ;;
;; Address Resolution Protocol ;; ;; Part of the tcp/ip network stack for KolibriOS ;;
;; ;; ;; ;;
;; This file contains the following: ;; ;; Based on the work of [Johnny_B] and [smb] ;;
;; arp_table_manager - Manages an ARPTable ;; ;; ;;
;; arp_request - Sends an ARP request on the ethernet ;; ;; Written by hidnplayr@kolibrios.org ;;
;; arp_handler - Called when an ARP packet is received ;; ;; ;;
;; ;; ;; GNU GENERAL PUBLIC LICENSE ;;
;; Changes history: ;; ;; Version 2, June 1991 ;;
;; 22.09.2003 - [Mike Hibbett] : mikeh@oceanfree.net ;; ;; ;;
;; 11.11.2006 - [Johnny_B] and [smb] ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
$Revision: 983 $ $Revision: 983 $
@ -26,6 +25,9 @@ ARP_VALID_MAPPING equ 1
ARP_AWAITING_RESPONSE equ 2 ARP_AWAITING_RESPONSE equ 2
ARP_RESPONSE_TIMEOUT equ 3 ARP_RESPONSE_TIMEOUT equ 3
ARP_REQUEST_TTL = 20 ; in seconds
ARP_ENTRY_TTL = 30 ; in seconds
ETHER_ARP equ 0x0608 ETHER_ARP equ 0x0608
ARP_REQ_OPCODE equ 0x0100 ; request ARP_REQ_OPCODE equ 0x0100 ; request
@ -79,7 +81,18 @@ endg
;-----------------------------------------------------------------
;
; ARP_init
;
; This function resets all ARP variables
;
; IN: /
; OUT: /
;
;-----------------------------------------------------------------
align 4
ARP_init: ARP_init:
xor eax, eax xor eax, eax
@ -93,175 +106,23 @@ ARP_init:
ret ret
;-----------------------------------------------------------------
;***************************************************************************
; Function
; arp_table_manager [by Johnny_B]
; ;
; Description ; ARP_IP_to_MAC
; Does a most required operations with ARP-table
; IN:
; Operation: see Opcode's constants below
; Index: Index of entry in the ARP-table
; Extra: Extra parameter for some Opcodes
; OUT:
; EAX = Returned value depends on opcodes, more detailed see below
; ;
;*************************************************************************** ; This function resets all ARP variables
;Opcode's constants ;
ARP_TABLE_ADD equ 1 ; IN: eax = IPv4 address
ARP_TABLE_IP_TO_MAC equ 5 ; OUT: eax = -1 on error, else eax = first two bytes of mac
; ( high 16 bits are zero)
;Index's constants ; ebx = last four bytes of mac ; TODO: special eax value for 'request send'
EXTRA_IS_ARP_PACKET_PTR equ 0 ;if Extra contain pointer to ARP_Packet ;
EXTRA_IS_ARP_ENTRY_PTR equ -1 ;if Extra contain pointer to ARP_ENTRY ;-----------------------------------------------------------------
align 4 align 4
proc arp_table_manager stdcall uses ebx esi edi ecx edx, Opcode:DWORD,Index:DWORD,Extra:DWORD ARP_IP_to_MAC:
mov ebx, ARPTable ;ARPTable base
mov ecx, dword[NumARP] ;ARP-entries counter
mov eax, dword[Opcode]
DEBUGF 1,"ARP table manager opcode:%u numARP:%u\n",eax,ecx
cmp eax, ARP_TABLE_ADD
je .add
cmp eax, ARP_TABLE_IP_TO_MAC
je .ip_to_mac
jmp .exit ;if unknown opcode
;;BEGIN ADD
;;Description: it adds an entry in the table. If ARP-table already
;; contains same IP, it will be updated.
;;IN: Operation: ARP_TABLE_ADD
;; Index: specifies what contains Extra-parameter
;; Extra: if Index==EXTRA_IS_ARP_Packet_PTR,
;; then Extra contains pointer to ARP_Packet,
;; otherwise Extra contains pointer to ARP_ENTRY
;;OUT:
;; EAX=index of entry, that has been added
;;
.add:
DEBUGF 1,"1"
sub esp, ARP_ENTRY.size ;Allocate ARP_ENTRY_SIZE byte in stack
mov esi, [Extra] ;pointer
mov edi, [Index] ;opcode
cmp edi, EXTRA_IS_ARP_PACKET_PTR
je .ARP_Packet_to_entry ;if Extra contain ptr to ARP_Packet and we have to form arp-entry
;else it contain ptr to arp-entry
DEBUGF 1,"2"
cld
; esi already has been loaded
mov edi, esp ;ebx + eax=ARPTable_base + ARP-entry_base(where we will add)
mov ecx,ARP_ENTRY.size/2 ;ARP_ENTRY_SIZE must be even number!!!
rep movsw ;copy
jmp .search
.ARP_Packet_to_entry:
DEBUGF 1,"3"
mov edx, dword[esi + ARP_Packet.SenderIP] ;esi=base of ARP_Packet
mov [esp + ARP_ENTRY.IP], edx
cld
lea esi, [esi + ARP_Packet.SenderMAC]
lea edi, [esp + ARP_ENTRY.MAC]
movsd
movsw
mov word[esp + ARP_ENTRY.Status], ARP_VALID_MAPPING ; specify the type - a valid entry
mov word[esp + ARP_ENTRY.TTL], 0x0E10 ; = 1 hour
.search:
DEBUGF 1,"4"
mov edx, dword[esp + ARP_ENTRY.IP] ;edx=IP-address, which we'll search
mov ecx, dword[NumARP] ;ecx=ARP-entries counter
jecxz .add_to_end ;if ARP-entries number == 0
imul eax, ecx, ARP_ENTRY.size ;eax=current table size(in bytes)
@@:
sub eax, ARP_ENTRY.size
cmp dword[ebx + eax + ARP_ENTRY.IP], edx
loopnz @b
; jz .replace ; found, replace existing entry, ptr to it is in eax
.add_to_end:
;
; DEBUGF 1,"5\n"
; ;else add to end
; or eax,-1 ;set eax=0xFFFFFFFF if adding is impossible
; mov ecx, dword[NumARP]
; cmp ecx, ARP_TABLE_SIZE
; je .add_exit ;if arp-entries number is equal to arp-table maxsize
; imul eax, dword[NumARP], ARP_ENTRY.size ;eax=ptr to end of ARPTable
; inc dword [NumARP] ;increase ARP-entries counter
; .replace:
DEBUGF 1,"Updating ARP entry: %x-%x-%x-%x-%x-%x = %u.%u.%u.%u to slot:%u\n",\
[esp + ARP_ENTRY.MAC]:2,[esp + ARP_ENTRY.MAC+1]:2,[esp + ARP_ENTRY.MAC+2]:2,[esp + ARP_ENTRY.MAC+3]:2,[esp + ARP_ENTRY.MAC+4]:2,[esp + ARP_ENTRY.MAC+5]:2,\
[esp + ARP_ENTRY.IP]:1,[esp + ARP_ENTRY.IP+1]:1,[esp + ARP_ENTRY.IP+2]:1,[esp + ARP_ENTRY.IP+3]:1,eax
cld
mov esi, esp ;esp=base of ARP-entry, that will be added
lea edi, [ebx + eax] ;ebx + eax=ARPTable_base + ARP-entry_base(where we will add)
mov ecx,ARP_ENTRY.size/2 ;ARP_ENTRY_SIZE must be even number!!!
rep movsw
mov ecx, ARP_ENTRY.size
xor edx, edx ;"div" takes operand from EDX:EAX
div ecx ;eax=index of entry, which has been added
.add_exit:
add esp, ARP_ENTRY.size ;free stack
jmp .exit
;;END ADD
;;BEGIN IP_TO_MAC
;;Description: it gets an IP from Index, scans each entry in the table and writes
;; MAC, that relates to specified IP, into buffer specified in Extra.
;; And if it cannot find an IP-address in the table, it does an ARP-request of that.
;;IN: Operation: ARP_TABLE_IP_TO_MAC
;; Index: IP that should be transformed into MAC
;; Extra: pointer to buffer where will be written the MAC-address.
;;OUT:
;; EAX=ARP table entry status code.
;; If EAX==ARP_NO_ENTRY, IP isn't found in the table and we have sent the request.
;; If EAX==ARP_AWAITING_RESPONSE, we wait the response from remote system.
;; If EAX==ARP_RESPONSE_TIMEOUT, remote system not responds too long.
;; If EAX==ARP_VALID_MAPPING, all is ok, we've got a true MAC.
;;
;; If MAC will equal to a zero, in the buffer. It means, that IP-address was not yet
;; resolved, or that doesn't exist. I recommend you, to do at most 3-5 calls of this
;; function with 1sec delay. sure, only if it not return a valid MAC after a first call.
;;
.ip_to_mac:
DEBUGF 1,"Trying to find MAC for %u.%u.%u.%u\n",[Index]:1,[Index+1]:1,[Index+2]:1,[Index+3]:1
xor eax, eax
mov edi, dword[Extra]
cld
stosd
stosw
DEBUGF 1,"ARP_IP_to_MAC\n"
; first, check destination IP to see if it is on 'this' network. ; first, check destination IP to see if it is on 'this' network.
; The test is: ; The test is:
@ -270,184 +131,130 @@ proc arp_table_manager stdcall uses ebx esi edi ecx edx, Opcode:DWORD,Index:DWOR
; else ; else
; destination is remote, so pass to gateway ; destination is remote, so pass to gateway
xor edx, edx ; TODO: find device num in edx
;;; TODO: get device number ! (in edx) mov ebx, [IP_LIST+edx]
xor edx, edx and ebx, [SUBNET_LIST+edx]
mov ecx, eax
and ecx, [SUBNET_LIST+edx]
cmp ecx, ebx
je .local
mov eax, [Index] ;eax=required IP mov eax, [GATEWAY_LIST+edx]
mov esi, eax DEBUGF 1,"requested IP is not on subnet, using gateway\n"
and esi, [SUBNET_LIST+edx]
mov ecx, [IP_LIST+edx]
and ecx, [SUBNET_LIST+edx]
cmp esi, ecx
je @f ;if we and target IP are located in the same network
mov eax, [GATEWAY_LIST+edx]
mov [Index], eax
DEBUGF 1,"IP is not on subnet, using %u.%u.%u.%u instead\n",[Index]:1,[Index+1]:1,[Index+2]:1,[Index+3]:1
@@:
cmp dword[NumARP], 0 .local:
je .ip_to_mac_send_request ;if ARP-table not contain an entries, we have to request IP. ; try to find it on the list
;EAX will be containing a zero, it's equal to ARP_NO_ENTRY mov ecx, [NumARP]
jz .not_in_list
mov esi, ARPTable + ARP_ENTRY.IP
.scan_loop:
scasd
jz .found_it
add esi, ARP_ENTRY.size - 4
loop .scan_loop
.not_in_list:
mov ecx, dword[NumARP] DEBUGF 1,"IP not found on list, preparing for ARP request\n"
imul esi, ecx, ARP_ENTRY.size ;esi=current ARP-table size
@@: ; if not, reserve an entry in list and send an ARP request packet
sub esi, ARP_ENTRY.size
cmp [ebx + esi + ARP_ENTRY.IP], eax ; ebx=ARPTable base
loopnz @b ; Return back if non match
jnz .ip_to_mac_send_request ; and request IP->MAC if none found in the table
; Return the entry status in eax push eax
movzx eax, word[ebx + esi + ARP_ENTRY.Status]
DEBUGF 1,"MAC found: %x-%x-%x-%x-%x-%x status:%x in slot:%u\n",\ push word ARP_REQUEST_TTL
[ebx + esi + ARP_ENTRY.MAC]:2,[ebx + esi + ARP_ENTRY.MAC+1]:2,[ebx + esi + ARP_ENTRY.MAC+2]:2,[ebx + esi + ARP_ENTRY.MAC+3]:2,[ebx + esi + ARP_ENTRY.MAC+4]:2,[ebx + esi + ARP_ENTRY.MAC+5]:2, ax, esi push word ARP_AWAITING_RESPONSE
push dword 0
push word 0
push eax
call ARP_add_entry
; esi holds index cmp eax, -1
cld je .full
lea esi, [ebx + esi + ARP_ENTRY.MAC]
mov edi, [Extra] ;edi=ptr to buffer for write MAC
movsd
movsw
jmp .exit
.ip_to_mac_send_request: pop eax
;;; TODO: get device number ! (in edx) call ARP_create_request
xor edx, edx
mov edx, [ETH_DRV_LIST + 4*edx]
lea ecx, [edx + ETH_DEVICE.mac]
stdcall arp_request,[Index],[IP_LIST+edx],ecx ;TargetIP,SenderIP_ptr,SenderMAC_ptr ret
mov eax, ARP_NO_ENTRY
jmp .exit
;;END IP_TO_MAC .found_it:
DEBUGF 1,"Found MAC! (%u-%u-%u-%u-%u-%u)\n",[esi+0]:2,[esi+1]:2,[esi+2]:2,[esi+3]:2,[esi+4]:2,[esi+5]:2
movzx eax, word [esi]
mov ebx, [esi+2]
.exit: ret
ret
endp .full:
add esp, 4
mov eax, -1
ret
;*************************************************************************** ;---------------------------------------------------------------------------
; Function
; arp_request [by Johnny_B]
; ;
; Description ; ARP_create_packet
; Sends an ARP request on the ethernet
; IN:
; TargetIP : requested IP address
; SenderIP_ptr : POINTER to sender's IP address(our system's address)
; SenderMAC_ptr : POINTER to sender's MAC address(our system's address)
; OUT:
; EAX=0 (if all is ok), otherwise EAX is not defined
; ;
; EBX,ESI,EDI will be saved ; IN: ip in eax
; ;
;*************************************************************************** ; OUT: /
proc arp_request stdcall uses ebx esi edi,\ ;
TargetIP:DWORD, SenderIP_ptr:DWORD, SenderMAC_ptr:DWORD ;---------------------------------------------------------------------------
DEBUGF 1,"Create ARP request\n"
stdcall kernel_alloc, 60 ; minimum eth packet size align 4
test eax, eax ARP_create_request:
jz .exit
mov ebx, eax DEBUGF 1,"Create ARP Packet\n"
mov word [ebx + ETH_FRAME.Data + ARP_Packet.HardwareType], 0x0100 ;Ethernet call IPv4_dest_to_dev
mov word [ebx + ETH_FRAME.Data + ARP_Packet.ProtocolType], 0x0008 ;IP
mov byte [ebx + ETH_FRAME.Data + ARP_Packet.HardwareSize], 0x06 ;MAC-addr length
mov byte [ebx + ETH_FRAME.Data + ARP_Packet.ProtocolSize], 0x04 ;IP-addr length
mov word [ebx + ETH_FRAME.Data + ARP_Packet.Opcode], 0x0100 ;Request
DEBUGF 1,"1" push eax ; DestIP
mov eax, [IP_LIST+4*edi] ; senderIP
push eax
cld mov edi, [ETH_DRV_LIST + 4*edi]
mov esi, [SenderMAC_ptr] lea eax, [edi + ETH_DEVICE.mac]
lea edi, [ebx + ETH_FRAME.Data + ARP_Packet.SenderMAC] ;Our MAC-addr mov ebx, ETH_BROADCAST
movsd mov ecx, 60 ; minimum packet size
movsw mov edx, edi ;;;
mov di , ETHER_ARP
call ETH_create_Packet
cmp edi, -1
je .exit
DEBUGF 1,"2" mov word [edi + ARP_Packet.HardwareType], 0x0100 ;Ethernet
mov word [edi + ARP_Packet.ProtocolType], 0x0008 ;IP
mov byte [edi + ARP_Packet.HardwareSize], 6 ;MAC-addr length
mov byte [edi + ARP_Packet.ProtocolSize], 4 ;IP-addr length
mov word [edi + ARP_Packet.Opcode], ARP_REQ_OPCODE ;Request
mov esi, [SenderIP_ptr] add edi, ARP_Packet.SenderMAC ; sendermac
mov [ebx + ETH_FRAME.Data + ARP_Packet.SenderIP], esi ;Our IP-addr lea esi, [edx + ETH_DEVICE.mac] ;
; movsd movsw ;
movsd ;
DEBUGF 1,"3" pop eax
stosd ;
lea edi, [ebx + ETH_FRAME.Data + ARP_Packet.TargetMAC] ; Required MAC-addr xor eax, eax ; destmac
xor eax, eax movsw ;
stosd movsw ;
stosw
DEBUGF 1,"4" pop eax
movsd ;
lea edi, [ebx + ETH_FRAME.DstMAC] DEBUGF 1,"ARP Packet for device %x created successfully\n", edx
stosd
stosw
DEBUGF 1,"5" call esi
mov esi, [TargetIP] inc [ARP_PACKETS_TX+4*edi]
mov dword [ebx + ETH_FRAME.Data + ARP_Packet.TargetIP], esi ;Required IP-addr(we get it as function parameter)
DEBUGF 1,"6"
mov esi, [SenderMAC_ptr]
lea edi, [ebx + ETH_FRAME.SrcMAC]
movsd
movsw
DEBUGF 1,"7"
mov ax , ETHER_ARP
stosw
DEBUGF 1,"8"
;;; TODO: get device number in edx !!
xor edx, edx
shl edx, 2
inc [ARP_PACKETS_TX+edx]
push dword .returnaddr
push dword 60
push ebx
mov ebx, [ETH_DRV_LIST + edx]
jmp [ebx + ETH_DEVICE.transmit]
.returnaddr:
; Add an entry in the ARP table, awaiting response
sub esp, ARP_ENTRY.size ;allocate memory for ARP-entry
mov esi, dword[TargetIP]
mov dword[esp + ARP_ENTRY.IP],esi
lea edi, [esp + ARP_ENTRY.MAC]
xor eax, eax
stosd
stosw
mov word[esp + ARP_ENTRY.Status], ARP_AWAITING_RESPONSE
mov word[esp + ARP_ENTRY.TTL], 10 ; 10 seconds
stdcall arp_table_manager,ARP_TABLE_ADD,EXTRA_IS_ARP_ENTRY_PTR,esp
add esp, ARP_ENTRY.size ; free memory
.exit:
DEBUGF 1,"ARP request - end\n"
ret
endp
ret
.exit:
add esp, 8
DEBUGF 1,"Create ARP Packet - failed\n"
mov eax, -1
ret
@ -512,6 +319,81 @@ ARP_decrease_entry_ttls:
ret ret
;---------------------------------------------------------------------------
;
; ARP_add_entry (or update)
;
; IN: arp entry in stack: esp .IP
; esp+4 .MAC
; esp+10 .Status
; esp+12 .TTL
; esp+14
;
; OUT: eax = entry #, -1 on error
;
;---------------------------------------------------------------------------
; TODO: use a mutex
align 4
ARP_add_entry:
mov ecx, [NumARP]
test ecx, ecx
jz .add
mov eax, dword[esp + ARP_ENTRY.MAC]
mov bx , word[esp + ARP_ENTRY.MAC + 4]
mov esi, ARPTable
.loop:
cmp dword [esi + ARP_ENTRY.MAC], eax
jne .maybe_next
cmp word [esi + ARP_ENTRY.MAC + 4], bx
jne .maybe_next
cmp dword[esi + ARP_ENTRY.TTL], 0xFFFF ; static entry
jne .notstatic
cmp dword[esp + ARP_ENTRY.TTL], 0xFFFF
jne .exit
.notstatic:
mov ebx, [NumARP]
xchg ebx, ecx
sub ecx, ebx
jmp .add
.maybe_next:
add esi, ARP_ENTRY.size
loop .loop
mov ecx, [NumARP]
cmp ecx, ARP_TABLE_SIZE
jge .full
.add:
push ecx
imul ecx, ARP_ENTRY.size
lea edi, [ecx + ARPTable]
lea esi, [esp + 4]
mov ecx, ARP_ENTRY.size/2
repz movsw
inc [NumARP]
pop eax
.exit:
add esp, 14
ret
.full:
mov eax, -1
jmp .exit
;--------------------------------------------------------------------------- ;---------------------------------------------------------------------------
; ;
@ -537,13 +419,12 @@ ARP_del_entry:
cld cld
rep movsw rep movsw
dec dword[NumARP] ;decrease arp-entries counter dec [NumARP] ;decrease arp-entries counter
ret ret
;----------------------------------------------------- ;-----------------------------------------------------
; ;
; ARP_Handler: ; ARP_Handler:
@ -557,22 +438,53 @@ ARP_del_entry:
; OUT: / ; OUT: /
; ;
;----------------------------------------------------- ;-----------------------------------------------------
align 4 align 4
ARP_Handler: ARP_handler:
DEBUGF 1,"ARP_Handler - start\n" DEBUGF 1,"ARP_Handler - start\n"
cmp ecx, 28 cmp ecx, 28
jl .exit jl .exit
; Is this a REQUEST? cmp word [edx + ARP_Packet.Opcode], ARP_REP_OPCODE ; Is this a reply packet?
; Is this a request for My Host IP jne .maybe_request
; Yes - So construct a response message.
; Send this message to the ethernet card for transmission
; push ebx edx mov ecx, [NumARP]
stdcall arp_table_manager, ARP_TABLE_ADD, EXTRA_IS_ARP_PACKET_PTR, edx test ecx, ecx
; pop edx ebx jz .exit
mov eax, [esp]
mov eax, [eax + ARP_Packet.SenderIP]
mov esi, ARPTable+ARP_ENTRY.IP
.loop:
scasd
jz .gotit
add esi, ARP_ENTRY.size-4
loop .loop
jmp .exit
.gotit:
cmp [esi-4+ARP_ENTRY.Status], 0x0300 ;if it is a static entry, dont touch it
je .exit
mov [esi-4+ARP_ENTRY.Status], ARP_VALID_MAPPING
mov [esi+ARP_ENTRY.TTL-4], ARP_ENTRY_TTL
mov ebx, [esp]
mov eax, dword [ebx + ARP_Packet.SenderMAC]
mov dword [esi+ARP_ENTRY.MAC-4], eax
mov ax , word [ebx + ARP_Packet.SenderMAC + 4]
mov word [esi+ARP_ENTRY.MAC-4+4], ax
jmp .exit
;------
.maybe_request:
cmp word [edx + ARP_Packet.Opcode], ARP_REQ_OPCODE ; Is this a request packet? cmp word [edx + ARP_Packet.Opcode], ARP_REQ_OPCODE ; Is this a request packet?
jne .exit jne .exit
@ -591,10 +503,8 @@ ARP_Handler:
push eax push eax
push edi push edi
; DEBUGF 1,"ETH_ARP_Handler - request for %u.%u.%u.%u\n",[edi+0]:1,[edi+1]:1,[edi+2]:1,[edi+3]:1
; OK, it is a request for one of our MAC addresses. Build the frame and send it ; OK, it is a request for one of our MAC addresses. Build the frame and send it
; We can reuse the buffer. ; We can reuse the buffer. (faster then using ARP_create_packet)
cld cld
lea esi, [edx + ARP_Packet.SenderMAC] lea esi, [edx + ARP_Packet.SenderMAC]
@ -623,12 +533,12 @@ ARP_Handler:
lea esi, [edx + ARP_Packet.SenderMAC] lea esi, [edx + ARP_Packet.SenderMAC]
movsd movsd
movsw movsw
mov ax , ETHER_ARP ; mov ax , ETHER_ARP
stosw ; stosw
jmp ETH_Sender ; And send it! jmp ETH_Sender ; And send it!
.exit: .exit:
call kernel_free call kernel_free
add esp, 4 ; pop (balance stack) add esp, 4 ; pop (balance stack)
@ -672,7 +582,6 @@ ARP_API:
jz .remove ; 5 jz .remove ; 5
dec bl dec bl
.error: .error:
mov eax, -1 mov eax, -1
ret ret
@ -697,9 +606,11 @@ ARP_API:
.write: .write:
; TODO: write code ; TODO: write code
; call ARP_write_entry
ret ret
.remove: .remove:
; TODO: write code mov esi, eax
call ARP_del_entry
ret ret

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; IP.INC ;; ;; IP.INC ;;
@ -85,7 +85,9 @@ IPv4_init:
or eax, -1 or eax, -1
mov edi, BROADCAST mov edi, BROADCAST
mov ecx, 1+4*MAX_IP stosd
xor eax, eax
mov ecx, 4*MAX_IP
rep stosd rep stosd
xor eax, eax xor eax, eax
@ -116,7 +118,7 @@ IPv4_init:
;----------------------------------------------------------------- ;-----------------------------------------------------------------
align 4 align 4
IPv4_Handler: IPv4_handler:
DEBUGF 1,"IP_Handler - start\n" DEBUGF 1,"IP_Handler - start\n"
mov cx , [edx + IPv4_Packet.HeaderChecksum] mov cx , [edx + IPv4_Packet.HeaderChecksum]
@ -186,13 +188,13 @@ IPv4_Handler:
pop edx ; Offset to data (tcp/udp/icmp/.. Packet) pop edx ; Offset to data (tcp/udp/icmp/.. Packet)
cmp al , IP_PROTO_TCP cmp al , IP_PROTO_TCP
; je TCP_Handler ; je TCP_handler
cmp al , IP_PROTO_UDP cmp al , IP_PROTO_UDP
je UDP_Handler je UDP_handler
cmp al , IP_PROTO_ICMP cmp al , IP_PROTO_ICMP
je ICMP_Handler je ICMP_handler
DEBUGF 1,"IP_Handler - unknown protocol:%u\n",al DEBUGF 1,"IP_Handler - unknown protocol:%u\n",al
@ -391,14 +393,14 @@ IPv4_Handler:
mov al , [edx + IPv4_Packet.Protocol] mov al , [edx + IPv4_Packet.Protocol]
pop edx ; Offset to data (tcp/udp/icmp/.. Packet) pop edx ; Offset to data (tcp/udp/icmp/.. Packet)
; cmp al , IP_PROTO_TCP cmp al , IP_PROTO_TCP
; je TCP_Handler ; je TCP_handler
cmp al , IP_PROTO_UDP cmp al , IP_PROTO_UDP
je UDP_Handler je UDP_handler
cmp al , IP_PROTO_ICMP cmp al , IP_PROTO_ICMP
je ICMP_Handler_fragments je ICMP_handler_fragments
DEBUGF 1,"IP_Handler - unknown protocol:%u\n",al DEBUGF 1,"IP_Handler - unknown protocol:%u\n",al
@ -505,7 +507,7 @@ IPv4_decrease_fragment_ttls:
;;; TODO: create fragmented packets ;;; TODO: create fragmented packets
align 4 align 4
IPv4_create_Packet: IPv4_create_packet:
DEBUGF 1,"Create IPv4 Packet\n" DEBUGF 1,"Create IPv4 Packet\n"
@ -515,11 +517,10 @@ IPv4_create_Packet:
cmp eax, -1 cmp eax, -1
je .broadcast ; If it is broadcast, just send je .broadcast ; If it is broadcast, just send
push eax call ARP_IP_to_MAC
stdcall arp_table_manager, ARP_TABLE_IP_TO_MAC, eax, temp_dstmac ;opcode,IP,MAC_ptr - Get the MAC address.
cmp eax, ARP_NO_ENTRY cmp eax, -1
pop eax jne .found
jne .send
DEBUGF 1,"Create IPv4 Packet - ARP entry not found!\n" DEBUGF 1,"Create IPv4 Packet - ARP entry not found!\n"
@ -528,9 +529,15 @@ IPv4_create_Packet:
ret ret
.found:
push ax
push ebx
jmp .send
.broadcast: .broadcast:
mov dword [temp_dstmac], -1 push word -1
mov word [temp_dstmac+4], -1 push dword -1
.send: .send:
@ -539,9 +546,10 @@ IPv4_create_Packet:
inc [IP_PACKETS_TX+4*edi] inc [IP_PACKETS_TX+4*edi]
mov edi, [ETH_DRV_LIST + 4*edi] mov edi, [ETH_DRV_LIST + 4*edi]
lea eax, [edi + ETH_DEVICE.mac] lea eax, [edi + ETH_DEVICE.mac]
mov ebx, temp_dstmac lea ebx, [esp+16]
mov ecx, [esp+12] mov ecx, [esp+12]
add ecx, IPv4_Packet.DataOrOptional add ecx, IPv4_Packet.DataOrOptional
mov edx, edi ;;;
mov di , ETHER_IPv4 mov di , ETHER_IPv4
call ETH_create_Packet ; TODO: figure out a way to make this work with other protocols too call ETH_create_Packet ; TODO: figure out a way to make this work with other protocols too
cmp edi, -1 cmp edi, -1
@ -572,20 +580,18 @@ IPv4_create_Packet:
DEBUGF 1,"IPv4 Packet for device %x created successfully\n", edx DEBUGF 1,"IPv4 Packet for device %x created successfully\n", edx
add esp, 6
ret ret
.exit: .exit:
add esp, 16 add esp, 16+6
.exit_: .exit_:
DEBUGF 1,"Create IPv4 Packet - failed\n" DEBUGF 1,"Create IPv4 Packet - failed\n"
or edi, -1 or edi, -1
ret ret
uglobal
temp_dstmac dp ? ; TODO: place this in stack instead!
endg
;--------------------------------------------------------------------------- ;---------------------------------------------------------------------------
; ;

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; ETHERNET.INC ;; ;; ETHERNET.INC ;;
@ -45,6 +45,12 @@ struct ETH_DEVICE
ends ; the rest of the device struct depends on the type of device ends ; the rest of the device struct depends on the type of device
align 4
iglobal
ETH_BROADCAST dp 0xffffffffffff
endg
align 4 align 4
uglobal uglobal
@ -230,7 +236,7 @@ ETH_Receiver:
;------------------------------------------------------------- ;-------------------------------------------------------------
align 4 align 4
ETH_Handler: ETH_handler:
get_from_queue ETH_IN_QUEUE, ETH_QUEUE_SIZE, .gohome get_from_queue ETH_IN_QUEUE, ETH_QUEUE_SIZE, .gohome
@ -243,10 +249,10 @@ ETH_Handler:
mov ax , [eax + ETH_FRAME.Type] mov ax , [eax + ETH_FRAME.Type]
cmp ax, ETHER_IPv4 cmp ax, ETHER_IPv4
je IPv4_Handler je IPv4_handler
cmp ax, ETHER_ARP cmp ax, ETHER_ARP
je ARP_Handler je ARP_handler
DEBUGF 1,"Unknown ethernet packet type %x\n", ax DEBUGF 1,"Unknown ethernet packet type %x\n", ax
@ -377,26 +383,22 @@ ETH_create_Packet:
pop ecx pop ecx
pop edx pop edx
DEBUGF 1,"1"
mov edi, eax mov edi, eax
pop esi pop esi
movsd movsd
movsw movsw
DEBUGF 1,"2"
pop esi pop esi
movsd movsd
movsw movsw
DEBUGF 1,"3"
pop ax pop ax
stosw stosw
DEBUGF 1,"4"
lea eax, [edi - ETH_FRAME.Data] ; Set eax to buffer start lea eax, [edi - ETH_FRAME.Data] ; Set eax to buffer start
mov ebx, ecx ; Set ebx to complete buffer size mov ebx, ecx ; Set ebx to complete buffer size
pop ecx pop ecx
mov esi, ETH_Sender mov esi, ETH_Sender
xor edx, edx ;;;; TODO: Fixme xor edx, edx ;;;; TODO: Fixme
mov edx, [ETH_DRV_LIST + edx] mov edx, [ETH_DRV_LIST + edx]
DEBUGF 1,"done: %x size:%u device:%x\n", eax, ebx, edx DEBUGF 1,"done: %x size:%u device:%x\n", eax, ebx, edx

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; ICMP.INC ;; ;; ICMP.INC ;;
@ -146,7 +146,7 @@ ICMP_init:
;-------------------------------- ;--------------------------------
align 4 align 4
ICMP_Handler: ;TODO: works only on pure ethernet right now ! ICMP_handler: ;TODO: works only on pure ethernet right now !
DEBUGF 1,"ICMP_Handler - start\n" DEBUGF 1,"ICMP_Handler - start\n"
cmp byte [edx + ICMP_Packet.Type], ICMP_ECHO ; Is this an echo request? cmp byte [edx + ICMP_Packet.Type], ICMP_ECHO ; Is this an echo request?
@ -318,7 +318,7 @@ ICMP_Handler: ;TODO: works only on pure ethernet right now !
;-------------------------------- ;--------------------------------
align 4 align 4
ICMP_Handler_fragments: ; works only on pure ethernet right now ! ICMP_handler_fragments: ; works only on pure ethernet right now !
DEBUGF 1,"ICMP_Handler_fragments - start\n" DEBUGF 1,"ICMP_Handler_fragments - start\n"
@ -345,7 +345,7 @@ ICMP_Handler_fragments: ; works only on pure ethernet right now !
shl edx, 16 shl edx, 16
mov dx , ICMP_ECHOREPLY shl 8 + 0 ; Type + Code mov dx , ICMP_ECHOREPLY shl 8 + 0 ; Type + Code
call ICMP_create_Packet call ICMP_create_packet
.dump: .dump:
DEBUGF 1,"ICMP_Handler_fragments - end\n" DEBUGF 1,"ICMP_Handler_fragments - end\n"
@ -372,7 +372,7 @@ ICMP_Handler_fragments: ; works only on pure ethernet right now !
;----------------------------------------------------------------- ;-----------------------------------------------------------------
align 4 align 4
ICMP_create_Packet: ICMP_create_packet:
DEBUGF 1,"Create ICMP Packet\n" DEBUGF 1,"Create ICMP Packet\n"
@ -382,7 +382,7 @@ ICMP_create_Packet:
mov di , IP_PROTO_ICMP mov di , IP_PROTO_ICMP
shr edx, 16 shr edx, 16
call IPv4_create_Packet call IPv4_create_packet
cmp edi, -1 cmp edi, -1
je .exit je .exit

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; queue.inc ;; ;; queue.inc ;;

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; SOCKET.INC ;; ;; SOCKET.INC ;;
@ -24,24 +24,25 @@ struct SOCKET
.PID dd ? ; application process id .PID dd ? ; application process id
.Domain dd ? ; INET/UNIX/.. .Domain dd ? ; INET/UNIX/..
.Type dd ? ; RAW/UDP/TCP/... .Type dd ? ; RAW/UDP/TCP/...
.Protocol dd ? ; ICMP/IPv4/ARP/
.LocalIP dd ? ; local IP address .LocalIP dd ? ; local IP address
.RemoteIP dd ? ; remote IP address .RemoteIP dd ? ; remote IP address
.LocalPort dw ? ; local port .LocalPort dw ? ; local port
.RemotePort dw ? ; remote port .RemotePort dw ? ; remote port
; .OrigRemoteIP dd ? ; original remote IP address (used to reset to LISTEN state) .OrigRemoteIP dd ? ; original remote IP address (used to reset to LISTEN state)
; .OrigRemotePort dw ? ; original remote port (used to reset to LISTEN state) .OrigRemotePort dw ? ; original remote port (used to reset to LISTEN state)
.rxDataCount dd ? ; rx data count .rxDataCount dd ? ; rx data count
; .TCBState dd ? ; TCB state .TCBState dd ? ; TCB state
; .TCBTimer dd ? ; TCB timer (seconds) .TCBTimer dd ? ; TCB timer (seconds)
; .ISS dd ? ; initial send sequence .ISS dd ? ; initial send sequence
; .IRS dd ? ; initial receive sequence .IRS dd ? ; initial receive sequence
; .SND_UNA dd ? ; sequence number of unack'ed sent Packets .SND_UNA dd ? ; sequence number of unack'ed sent Packets
; .SND_NXT dd ? ; bext send sequence number to use .SND_NXT dd ? ; bext send sequence number to use
; .SND_WND dd ? ; send window .SND_WND dd ? ; send window
; .RCV_NXT dd ? ; next receive sequence number to use .RCV_NXT dd ? ; next receive sequence number to use
; .RCV_WND dd ? ; receive window .RCV_WND dd ? ; receive window
; .SEG_LEN dd ? ; segment length .SEG_LEN dd ? ; segment length
; .SEG_WND dd ? ; segment window .SEG_WND dd ? ; segment window
.wndsizeTimer dd ? ; window size timer .wndsizeTimer dd ? ; window size timer
.lock dd ? ; lock mutex .lock dd ? ; lock mutex
.backlog dw ? ; Backlog .backlog dw ? ; Backlog
@ -125,7 +126,7 @@ s_error:
; ;
; IN: domain in ecx ; IN: domain in ecx
; type in edx ; type in edx
; set esi to zero, it is reserved for future use ; protocol in esi
; OUT: eax is socket num, -1 on error ; OUT: eax is socket num, -1 on error
; ;
;----------------------------------------------- ;-----------------------------------------------
@ -139,6 +140,7 @@ socket_open:
mov [eax + SOCKET.Domain], ecx mov [eax + SOCKET.Domain], ecx
mov [eax + SOCKET.Type], edx mov [eax + SOCKET.Type], edx
mov [eax + SOCKET.Protocol], esi
stdcall net_socket_addr_to_num, eax stdcall net_socket_addr_to_num, eax
DEBUGF 1,", socketnumber: %u\n", eax DEBUGF 1,", socketnumber: %u\n", eax
@ -154,7 +156,6 @@ socket_open:
; ;
; SOCKET_bind ; SOCKET_bind
; ;
;
; IN: socket number in ecx ; IN: socket number in ecx
; pointer to sockaddr struct in edx ; pointer to sockaddr struct in edx
; length of that struct in esi ; length of that struct in esi
@ -184,6 +185,7 @@ socket_bind:
jl s_error jl s_error
mov bx, word [edx + 2] mov bx, word [edx + 2]
rol bx,8 ;;;
DEBUGF 1,"local port: %u ",bx DEBUGF 1,"local port: %u ",bx
test bx, bx test bx, bx
jnz .check_only jnz .check_only
@ -280,6 +282,7 @@ socket_connect:
.udp: .udp:
mov bx , word [edx + 2] mov bx , word [edx + 2]
rol bx, 8
mov word [eax + SOCKET.RemotePort], bx mov word [eax + SOCKET.RemotePort], bx
DEBUGF 1,"remote port: %u ",bx DEBUGF 1,"remote port: %u ",bx
@ -735,12 +738,13 @@ socket_send:
mov ecx, esi mov ecx, esi
mov esi, edx mov esi, edx
mov edx, dword [eax + SOCKET.LocalPort] ; load local port and remote port at once mov edx, dword [eax + SOCKET.LocalPort] ; load local port and remote port at once
DEBUGF 1,"local port: %u, remote port:%u\n",[eax + SOCKET.LocalPort]:2, [eax + SOCKET.RemotePort]:2 DEBUGF 1,"local port: %u, remote port:%u\n",[eax + SOCKET.LocalPort]:2, [eax + SOCKET.RemotePort]:2
bswap edx ;;;
rol edx, 16 ;;;
mov ebx, [eax + SOCKET.LocalIP] mov ebx, [eax + SOCKET.LocalIP]
mov eax, [eax + SOCKET.RemoteIP] mov eax, [eax + SOCKET.RemoteIP]
call UDP_create_Packet call UDP_create_packet
mov [esp+32], eax mov [esp+32], eax
ret ret
@ -765,7 +769,7 @@ socket_send:
add esi, ICMP_Packet.Data add esi, ICMP_Packet.Data
mov ebx, [eax + SOCKET.LocalIP] mov ebx, [eax + SOCKET.LocalIP]
mov eax, [eax + SOCKET.RemoteIP] mov eax, [eax + SOCKET.RemoteIP]
call ICMP_create_Packet call ICMP_create_packet
mov [esp+32], eax mov [esp+32], eax
ret ret

View File

@ -110,7 +110,7 @@ stack_handler:
cmp [ETH_RUNNING], 0 cmp [ETH_RUNNING], 0
je .exit je .exit
call ETH_Handler ; handle all queued ethernet packets call ETH_handler ; handle all queued ethernet packets
call ETH_send_queued call ETH_send_queued
; Test for 10ms tick, call tcp timer ; Test for 10ms tick, call tcp timer
@ -188,6 +188,13 @@ endp
align 4 align 4
sys_network: sys_network:
cmp ebx, -1
jne @f
mov eax, [ETH_RUNNING]
jmp .return
@@:
cmp bh, MAX_NET_DEVICES ; Check if device number exists cmp bh, MAX_NET_DEVICES ; Check if device number exists
jge .doesnt_exist jge .doesnt_exist
@ -200,7 +207,7 @@ sys_network:
test bl, bl ; 0 = Get device type (ethernet/token ring/...) test bl, bl ; 0 = Get device type (ethernet/token ring/...)
jnz @f jnz @f
; todo
xor eax, eax xor eax, eax
jmp .return jmp .return

View File

@ -1,20 +1,19 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; TCP.INC ;; ;; TCP.INC ;;
;; ;; ;; ;;
;; TCP Processes for Menuet OS TCP/IP stack ;; ;; Part of the tcp/ip network stack for KolibriOS ;;
;; ;; ;; ;;
;; Copyright 2002 Mike Hibbett, mikeh@oceanfree.net ;; ;; Written by hidnplayr@kolibrios.org ;;
;; ;; ;; ;;
;; See file COPYING for details ;; ;; GNU GENERAL PUBLIC LICENSE ;;
;; v0.6 : Added reset handling in the established state ;; ;; Version 2, June 1991 ;;
;; Added a timer per socket to allow delays when ;; ;; ;;
;; rx window gets below 1KB ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
$Revision: 1019 $ $Revision: 1019 $
@ -39,18 +38,20 @@ TH_PUSH equ 0x08
TH_ACK equ 0x10 TH_ACK equ 0x10
TH_URG equ 0x20 TH_URG equ 0x20
TWOMSL equ 10 ; # of secs to wait before closing socket TWOMSL equ 10 ; # of secs to wait before closing socket
TCP_RETRIES equ 5 ; Number of times to resend a Packet TCP_RETRIES equ 5 ; Number of times to resend a Packet
TCP_TIMEOUT equ 10 ; resend if not replied to in x hs TCP_TIMEOUT equ 10 ; resend if not replied to in x hs
TCP_QUEUE_SIZE equ 16
struct TCP_Packet struct TCP_Packet
.SourcePort dw ? .SourcePort dw ?
.DestinationPort dw ? .DestinationPort dw ?
.SequenceNumber dd ? .SequenceNumber dd ?
.AckNumber dd ? .AckNumber dd ?
.DataOffset db ? ; DataOffset[0-3 bits] and Reserved[4-7] .DataOffset db ? ; DataOffset[0-3 bits] and Reserved[4-7]
.Flags db ? ; Reserved[0-1 bits]|URG|ACK|PSH|RST|SYN|FIN .Flags db ? ; Reserved[0-1 bits]|URG|ACK|PSH|RST|SYN|FIN
.Window dw ? .Window dw ?
.Checksum dw ? .Checksum dw ?
.UrgentPointer dw ? .UrgentPointer dw ?
@ -59,17 +60,59 @@ struct TCP_Packet
.Data: .Data:
ends ends
align 4
uglobal
TCP_PACKETS_TX rd MAX_IP
TCP_PACKETS_RX rd MAX_IP
;*************************************************************************** TCP_IN_QUEUE rd 3*TCP_QUEUE_SIZE+3
; Function TCP_OUT_QUEUE rd 3*TCP_QUEUE_SIZE+3
endg
;-----------------------------------------------------------------
;
; TCP_init
;
; This function resets all TCP variables
;
; IN: /
; OUT: /
;
;-----------------------------------------------------------------
align 4
TCP_init:
xor eax, eax
mov edi, TCP_PACKETS_TX
mov ecx, 2*MAX_IP
rep stosd
mov dword [TCP_IN_QUEUE], TCP_QUEUE_SIZE
mov dword [TCP_IN_QUEUE+4], TCP_IN_QUEUE + queue.data
mov dword [TCP_IN_QUEUE+8], TCP_IN_QUEUE + queue.data
mov dword [TCP_OUT_QUEUE], TCP_QUEUE_SIZE
mov dword [TCP_OUT_QUEUE+4], TCP_OUT_QUEUE + queue.data
mov dword [TCP_OUT_QUEUE+8], TCP_OUT_QUEUE + queue.data
ret
;-----------------------------------------------------------------
;
; tcp_tcb_handler ; tcp_tcb_handler
; ;
; Description
; Handles sockets in the timewait state, closing them ; Handles sockets in the timewait state, closing them
; when the TCB timer expires ; when the TCB timer expires
; ;
;*************************************************************************** ;-----------------------------------------------------------------
align 4
tcp_tcb_handler: tcp_tcb_handler:
; scan through all the sockets, decrementing active timers ; scan through all the sockets, decrementing active timers
@ -84,7 +127,7 @@ tcp_tcb_handler:
or ebx, ebx or ebx, ebx
jz .exit jz .exit
DEBUGF 1, "K : %x-%x: %x-%x-%x-%u\n", [ebx + SOCKET.PID]:2, [ebx + SOCKET.Number]:2, [ebx + SOCKET.LocalPort]:4, [ebx + SOCKET.RemoteIP], [ebx + SOCKET.RemotePort]:4, [ebx + SOCKET.TCBState] ; DEBUGF 1, "K : %x-%x: %x-%x-%x-%u\n", [ebx + SOCKET.PID]:2, [ebx + SOCKET.Number]:2, [ebx + SOCKET.LocalPort]:4, [ebx + SOCKET.RemoteIP], [ebx + SOCKET.RemotePort]:4, [ebx + SOCKET.TCBState]
cmp [ebx + SOCKET.TCBTimer], 0 cmp [ebx + SOCKET.TCBTimer], 0
jne .decrement_tcb jne .decrement_tcb
@ -124,7 +167,8 @@ tcp_tcb_handler:
; ;
;*************************************************************************** ;***************************************************************************
proc tcp_tx_handler stdcall align 4
tcp_tx_handler:
; decrement all resend buffers timers. If they ; decrement all resend buffers timers. If they
; expire, queue them for sending, and restart the timer. ; expire, queue them for sending, and restart the timer.
; If the retries counter reach 0, delete the entry ; If the retries counter reach 0, delete the entry
@ -133,7 +177,7 @@ proc tcp_tx_handler stdcall
mov ecx, 0 mov ecx, 0
.next_resendq: .next_resendq:
cmp ecx, NUMRESENDENTRIES ; cmp ecx, NUMRESENDENTRIES
je .exit ; None left je .exit ; None left
cmp dword[esi + 4], 0 cmp dword[esi + 4], 0
jne @f ; found one jne @f ; found one
@ -162,9 +206,9 @@ proc tcp_tx_handler stdcall
@@: ; resend Packet @@: ; resend Packet
pushad pushad
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
jne .tth004z jne .tth004z
; TODO - try again in 10ms. ; TODO - try again in 10ms.
@ -179,21 +223,21 @@ proc tcp_tx_handler stdcall
.tth004z: .tth004z:
; we have a buffer # in ax ; we have a buffer # in ax
push eax ecx ; push eax ecx
mov ecx, IPBUFFSIZE ; mov ecx, IPBUFFSIZE
mul ecx ; mul ecx
add eax, IPbuffs ; add eax, IPbuffs
; we have the buffer address in eax ; we have the buffer address in eax
mov edi, eax mov edi, eax
pop ecx pop ecx
; Now get buffer location, and copy buffer across. argh! more copying,, ; Now get buffer location, and copy buffer across. argh! more copying,,
mov esi, resendBuffer ; mov esi, resendBuffer
@@: add esi, IPBUFFSIZE ; @@: add esi, IPBUFFSIZE
loop @b loop @b
; we have resend buffer location in esi ; we have resend buffer location in esi
mov ecx, IPBUFFSIZE ; mov ecx, IPBUFFSIZE
; copy data across ; copy data across
push edi push edi
@ -202,15 +246,15 @@ proc tcp_tx_handler stdcall
pop edi pop edi
; queue Packet ; queue Packet
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
mov edx, [IP_LIST] ; mov edx, [IP_LIST]
cmp edx, [edi + IP_Packet.DestinationAddress] ; cmp edx, [edi + IP_Packet.DestinationAddress]
jne .not_local ; jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
pop ebx pop ebx
call queue ; call queue
.tth005: .tth005:
popad popad
@ -221,35 +265,32 @@ proc tcp_tx_handler stdcall
.exit: .exit:
ret ret
endp
;***************************************************************************
; Function ;-----------------------------------------------------------------
; tcp_rx
; ;
; Description ; TCP_Handler:
; TCP protocol handler
; This is a kernel function, called by ip_rx
; IP buffer address given in edx
; IP buffer number in eax
; Free up (or re-use) IP buffer when finished
; ;
;*************************************************************************** ; Called by IPv4_handler,
; this procedure will inject the tcp data diagrams in the application sockets.
;
; IN: Pointer to buffer in [esp]
; size of buffer in [esp+4]
; pointer to device struct in ebx
; TCP Packet size in ecx
; pointer to TCP Packet data in edx
; SourceAddres in esi
; OUT: /
;
;-----------------------------------------------------------------
proc tcp_rx stdcall uses ebx TCP_Handler :
; The process is as follows.
; Look for a socket with matching remote IP, remote port, local port
; if not found, then
; look for remote IP + local port match ( where sockets remote port = 0)
; if not found, then
; look for a socket where local socket port == IP Packets remote port
; where sockets remote port, remote IP = 0
; discard if not found
; Call sockets tcbStateMachine, with pointer to Packet.
; the state machine will not delete the Packet, so do that here.
push eax
DEBUGF 1,"TCP_Handler\n"
jmp .exit ;;;;
; Look for a socket where ; Look for a socket where
; IP Packet TCP Destination Port = local Port ; IP Packet TCP Destination Port = local Port
@ -265,19 +306,19 @@ proc tcp_rx stdcall uses ebx
; DEBUGF 1, "K : tcp_rx - 1.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4 ; DEBUGF 1, "K : tcp_rx - 1.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4
mov ax, [edx + 20 + TCP_Packet.DestinationPort] ; get the dest. port from the TCP hdr mov ax, [edx + TCP_Packet.DestinationPort] ; get the dest. port from the TCP hdr
cmp [ebx + SOCKET.LocalPort], ax ; get the dest. port from the TCP hdr cmp [ebx + SOCKET.LocalPort], ax ; get the dest. port from the TCP hdr
jne .next_socket.1 ; different - try next socket jne .next_socket.1 ; different - try next socket
; DEBUGF 1, "K : tcp_rx - 1.addr: %x - %x\n", [edx + IP_Packet.SourceAddress], [ebx + SOCKET.RemoteIP] ; DEBUGF 1, "K : tcp_rx - 1.addr: %x - %x\n", [edx + IP_Packet.SourceAddress], [ebx + SOCKET.RemoteIP]
mov eax, [edx + IP_Packet.SourceAddress] ; get the source IP Addr from the IP hdr mov eax, esi ;[edx + IP_Packet.SourceAddress] ; get the source IP Addr from the IP hdr
cmp [ebx + SOCKET.RemoteIP], eax ; compare with socket's remote IP cmp [ebx + SOCKET.RemoteIP], eax ; compare with socket's remote IP
jne .next_socket.1 ; different - try next socket jne .next_socket.1 ; different - try next socket
; DEBUGF 1, "K : tcp_rx - 1.sport: %x - %x\n", [edx + 20 + TCP_Packet.SourcePort]:4, [ebx + SOCKET.RemotePort]:4 ; DEBUGF 1, "K : tcp_rx - 1.sport: %x - %x\n", [edx + 20 + TCP_Packet.SourcePort]:4, [ebx + SOCKET.RemotePort]:4
mov ax, [edx + 20 + TCP_Packet.SourcePort] ; get the source port from the TCP hdr mov ax, [edx + TCP_Packet.SourcePort] ; get the source port from the TCP hdr
cmp [ebx + SOCKET.RemotePort], ax ; compare with socket's remote port cmp [ebx + SOCKET.RemotePort], ax ; compare with socket's remote port
jne .next_socket.1 ; different - try next socket jne .next_socket.1 ; different - try next socket
@ -301,14 +342,14 @@ proc tcp_rx stdcall uses ebx
; DEBUGF 1, "K : tcp_rx - 2.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4 ; DEBUGF 1, "K : tcp_rx - 2.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4
mov ax, [edx + 20 + TCP_Packet.DestinationPort] ; get the dest. port from the TCP hdr mov ax, [edx + TCP_Packet.DestinationPort] ; get the dest. port from the TCP hdr
cmp [ebx + SOCKET.LocalPort], ax ; compare with socket's local port cmp [ebx + SOCKET.LocalPort], ax ; compare with socket's local port
jne .next_socket.2 ; different - try next socket jne .next_socket.2 ; different - try next socket
; DEBUGF 1, "K : tcp_rx - 2.addr: %x - %x\n", [edx + IP_Packet.SourceAddress], [ebx + SOCKET.RemoteIP] ; DEBUGF 1, "K : tcp_rx - 2.addr: %x - %x\n", [edx + IP_Packet.SourceAddress], [ebx + SOCKET.RemoteIP]
mov eax, [edx + IP_Packet.SourceAddress] ; get the source IP Addr from the IP hdr ; mov eax, esi ;[edx + IP_Packet.SourceAddress] ; get the source IP Addr from the IP hdr
cmp [ebx + SOCKET.RemoteIP], eax ; compare with socket's remote IP cmp [ebx + SOCKET.RemoteIP], esi ; compare with socket's remote IP
jne .next_socket.2 ; different - try next socket jne .next_socket.2 ; different - try next socket
; DEBUGF 1, "K : tcp_rx - 2.sport: 0000 - %x\n", [ebx + SOCKET.RemotePort]:4 ; DEBUGF 1, "K : tcp_rx - 2.sport: 0000 - %x\n", [ebx + SOCKET.RemotePort]:4
@ -336,7 +377,7 @@ proc tcp_rx stdcall uses ebx
; DEBUGF 1, "K : tcp_rx - 3.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4 ; DEBUGF 1, "K : tcp_rx - 3.dport: %x - %x\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [ebx + SOCKET.LocalPort]:4
mov ax, [edx + 20 + TCP_Packet.DestinationPort] ; get destination port from the TCP hdr mov ax, [edx + TCP_Packet.DestinationPort] ; get destination port from the TCP hdr
cmp [ebx + SOCKET.LocalPort], ax ; compare with socket's local port cmp [ebx + SOCKET.LocalPort], ax ; compare with socket's local port
jne .next_socket.3 ; different - try next socket jne .next_socket.3 ; different - try next socket
@ -358,9 +399,9 @@ proc tcp_rx stdcall uses ebx
; If we got here, we need to reject the Packet ; If we got here, we need to reject the Packet
DEBUGF 1, "K : tcp_rx - dumped\n" DEBUGF 1, "K : tcp_rx - dumped\n"
DEBUGF 1, "K : --------: %x-%x-%x (flags: %x)\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [edx + IP_Packet.SourceAddress], [edx + 20 + TCP_Packet.SourcePort]:4, [edx + 20 + TCP_Packet.Flags]:2 ; DEBUGF 1, "K : --------: %x-%x-%x (flags: %x)\n", [edx + 20 + TCP_Packet.DestinationPort]:4, [edx + IP_Packet.SourceAddress], [edx + 20 + TCP_Packet.SourcePort]:4, [edx + 20 + TCP_Packet.Flags]:2
inc [dumped_rx_count] ; inc [dumped_rx_count]
jmp .exit jmp .exit
.change_state: .change_state:
@ -373,12 +414,27 @@ proc tcp_rx stdcall uses ebx
stdcall tcpStateMachine, ebx stdcall tcpStateMachine, ebx
.exit: .exit:
pop eax
call freeBuff call kernel_free
ret add esp, 4 ; pop (balance stack)
endp
ret
;-----------------------------------------------------------------
;
; IN: eax = dest ip
; ebx = source ip
; ecx = data length
; edx = remote port shl 16 + local port
; esi = data offset
;
;-----------------------------------------------------------------
TCP_create_Packet:
DEBUGF 1,"Create TCP Packet\n"
;*************************************************************************** ;***************************************************************************
; Function ; Function
; buildTCPPacket ; buildTCPPacket
@ -394,44 +450,45 @@ endp
; ;
;*************************************************************************** ;***************************************************************************
proc build_tcp_Packet stdcall, sockAddr:DWORD
push ecx ; Save data length push ecx ; Save data length
; convert buffer pointer eax to the absolute address add ecx, UDP_Packet.Data
mov ecx, IPBUFFSIZE mov di , IP_PROTO_UDP
mul ecx
add eax, IPbuffs
mov edx, eax ; dx = fragment id
mov [edx + 20 + TCP_Packet.Flags], bl ; TCP flags call IPv4_create_Packet ; TODO: figure out a way to choose between IPv4 and IPv6
cmp edi, -1
je .exit
mov ebx, [sockAddr] mov [edi + TCP_Packet.Flags], bl ; TCP flags
; mov ebx, [sockAddr];---------------------------------------------------------- eof
; So, ebx holds the socket ptr, edx holds the IPbuffer ptr ; So, ebx holds the socket ptr, edx holds the IPbuffer ptr
; Fill in the IP header ( some data is in the socket descriptor) ; Fill in the IP header ( some data is in the socket descriptor)
mov eax, [ebx + SOCKET.LocalIP] mov eax, [ebx + SOCKET.LocalIP]
mov [edx + IP_Packet.SourceAddress], eax ; mov [edx + IP_Packet.SourceAddress], eax
mov eax, [ebx + SOCKET.RemoteIP] mov eax, [ebx + SOCKET.RemoteIP]
mov [edx + IP_Packet.DestinationAddress], eax ; mov [edx + IP_Packet.DestinationAddress], eax
mov [edx + IP_Packet.VersionAndIHL], 0x45 ; mov [edx + IP_Packet.VersionAndIHL], 0x45
mov [edx + IP_Packet.TypeOfService], 0 ; mov [edx + IP_Packet.TypeOfService], 0
pop eax ; Get the TCP data length pop eax ; Get the TCP data length
push eax push eax
add eax, 20 + 20 ; add IP header and TCP header lengths add eax, 20 + 20 ; add IP header and TCP header lengths
rol ax, 8 rol ax, 8
mov [edx + IP_Packet.TotalLength], ax ; mov [edx + IP_Packet.TotalLength], ax
mov [edx + IP_Packet.Identification], 0 ; mov [edx + IP_Packet.Identification], 0
mov [edx + IP_Packet.FlagsAndFragmentOffset], 0x0040 ; mov [edx + IP_Packet.FlagsAndFragmentOffset], 0x0040
mov [edx + IP_Packet.TimeToLive], 0x20 ; mov [edx + IP_Packet.TimeToLive], 0x20
mov [edx + IP_Packet.Protocol], PROTOCOL_TCP ; mov [edx + IP_Packet.Protocol], PROTOCOL_TCP
; Checksum left unfilled ; Checksum left unfilled
mov [edx + IP_Packet.HeaderChecksum], 0 ; mov [edx + IP_Packet.HeaderChecksum], 0
; Fill in the TCP header (some data is in the socket descriptor) ; Fill in the TCP header (some data is in the socket descriptor)
mov ax, [ebx + SOCKET.LocalPort] mov ax, [ebx + SOCKET.LocalPort]
@ -475,54 +532,64 @@ proc build_tcp_Packet stdcall, sockAddr:DWORD
@@: ; we have edx as IPbuffer ptr. @@: ; we have edx as IPbuffer ptr.
; Fill in the TCP checksum ; Fill in the TCP checksum
; First, fill in pseudoheader ; First, fill in pseudoheader
mov eax, [edx + IP_Packet.SourceAddress] ; mov eax, [edx + IP_Packet.SourceAddress]
mov [pseudoHeader], eax ; mov [pseudoHeader], eax
mov eax, [edx + IP_Packet.DestinationAddress] ; mov eax, [edx + IP_Packet.DestinationAddress]
mov [pseudoHeader + 4], eax ; mov [pseudoHeader + 4], eax
mov word[pseudoHeader + 8], PROTOCOL_TCP shl 8 + 0 ; mov word[pseudoHeader + 8], PROTOCOL_TCP shl 8 + 0
add ebx, 20 ; add ebx, 20
mov [pseudoHeader + 10], bh ; mov [pseudoHeader + 10], bh
mov [pseudoHeader + 11], bl ; mov [pseudoHeader + 11], bl
;
mov eax, pseudoHeader ; mov eax, pseudoHeader
mov [checkAdd1], eax ; mov [checkAdd1], eax
mov word[checkSize1], 12 ; mov word[checkSize1], 12
mov eax, edx ; mov eax, edx
add eax, 20 ; add eax, 20
mov [checkAdd2], eax ; mov [checkAdd2], eax
mov eax, ebx ; mov eax, ebx
mov [checkSize2], ax ; mov [checkSize2], ax
;
call checksum ; call checksum
; store it in the TCP checksum ( in the correct order! ) ; store it in the TCP checksum ( in the correct order! )
mov ax, [checkResult] ; mov ax, [checkResult]
rol ax, 8 ; rol ax, 8
mov [edx + 20 + TCP_Packet.Checksum], ax ; mov [edx + 20 + TCP_Packet.Checksum], ax
; Fill in the IP header checksum ; Fill in the IP header checksum
movzx eax, byte [edx + IP_Packet.VersionAndIHL] ; Calculate Header length by using IHL field ; movzx eax, byte [edx + IP_Packet.VersionAndIHL] ; Calculate Header length by using IHL field
and eax, 0x0000000F ; ; and eax, 0x0000000F ;
shl eax, 2 ; ; shl eax, 2 ;
;
stdcall checksum_jb, edx, eax ; buf_ptr, buf_size stdcall checksum_jb, edx, eax ; buf_ptr, buf_size
rol ax, 8 rol ax, 8
mov [edx + IP_Packet.HeaderChecksum], ax ; mov [edx + IP_Packet.HeaderChecksum], ax
.exit:
call kernel_free
add esp, 4 ; pop (balance stack)
ret ret
endp ;endp
; Increments the 32 bit value pointed to by esi in internet order ; Increments the 32 bit value pointed to by esi in internet order
proc inc_inet_esi stdcall proc inc_inet_esi stdcall
push eax ; push eax
mov eax, [esi] ; mov eax, [esi]
bswap eax ; bswap eax
inc eax ; inc eax
bswap eax ; bswap eax
mov [esi], eax ; mov [esi], eax
pop eax ; pop eax
ret ; ret
inc byte[esi+0]
adc byte[esi+1],0
adc byte[esi+2],0
adc byte[esi+3],0
endp endp
@ -591,7 +658,7 @@ proc tcpStateMachine stdcall, sockAddr:DWORD
xor ecx, ecx xor ecx, ecx
.next_resendq: .next_resendq:
cmp ecx, NUMRESENDENTRIES ; cmp ecx, NUMRESENDENTRIES
je .call_handler ; None left je .call_handler ; None left
cmp [esi + 4], eax cmp [esi + 4], eax
je @f ; found one je @f ; found one
@ -606,8 +673,8 @@ proc tcpStateMachine stdcall, sockAddr:DWORD
push ecx push ecx
; Now get buffer location, and copy buffer across. argh! more copying,, ; Now get buffer location, and copy buffer across. argh! more copying,,
imul edi, ecx, IPBUFFSIZE ; imul edi, ecx, IPBUFFSIZE
add edi, resendBuffer ; add edi, resendBuffer
; we have dest buffer location in edi. incoming Packet in edx. ; we have dest buffer location in edi. incoming Packet in edx.
; Get this Packets sequence number ; Get this Packets sequence number
@ -668,41 +735,41 @@ proc stateTCB_LISTEN stdcall, sockAddr:DWORD
; We have a SYN. update the socket with this IP Packets details, ; We have a SYN. update the socket with this IP Packets details,
; And send a response ; And send a response
mov eax, [edx + IP_Packet.SourceAddress] ; mov eax, [edx + IP_Packet.SourceAddress]
mov [ebx + SOCKET.RemoteIP], eax ; mov [ebx + SOCKET.RemoteIP], eax
mov ax, [edx + 20 + TCP_Packet.SourcePort] ; mov ax, [edx + 20 + TCP_Packet.SourcePort]
mov [ebx + SOCKET.RemotePort], ax ; mov [ebx + SOCKET.RemotePort], ax
mov eax, [edx + 20 + TCP_Packet.SequenceNumber] ; mov eax, [edx + 20 + TCP_Packet.SequenceNumber]
mov [ebx + SOCKET.IRS], eax ; mov [ebx + SOCKET.IRS], eax
mov [ebx + SOCKET.RCV_NXT], eax ; mov [ebx + SOCKET.RCV_NXT], eax
lea esi, [ebx + SOCKET.RCV_NXT] ; lea esi, [ebx + SOCKET.RCV_NXT]
call inc_inet_esi ; RCV.NXT ; call inc_inet_esi ; RCV.NXT
mov eax, [ebx + SOCKET.ISS] ; mov eax, [ebx + SOCKET.ISS]
mov [ebx + SOCKET.SND_NXT], eax ; mov [ebx + SOCKET.SND_NXT], eax
;
; Now construct the response, and queue for sending by IP ; Now construct the response, and queue for sending by IP
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
je .exit ; je .exit
push eax push eax
mov bl, TH_SYN + TH_ACK mov bl, TH_SYN + TH_ACK
xor ecx, ecx xor ecx, ecx
xor esi, esi xor esi, esi
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; mov edx, [stack_ip] ;;; mov edx, [stack_ip]
mov ecx, [sockAddr] mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
; Send it. ; Send it.
pop ebx pop ebx
call queue ;;; call queue
mov esi, [sockAddr] mov esi, [sockAddr]
mov [esi + SOCKET.TCBState], TCB_SYN_RECEIVED mov [esi + SOCKET.TCBState], TCB_SYN_RECEIVED
@ -747,9 +814,9 @@ proc stateTCB_SYN_SENT stdcall, sockAddr:DWORD
; Send an ACK ; Send an ACK
; Now construct the response, and queue for sending by IP ; Now construct the response, and queue for sending by IP
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
pop ebx pop ebx
je .exit je .exit
@ -757,19 +824,19 @@ proc stateTCB_SYN_SENT stdcall, sockAddr:DWORD
xor ecx, ecx xor ecx, ecx
xor esi, esi xor esi, esi
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; mov edx, [stack_ip] ;;; mov edx, [stack_ip]
mov ecx, [sockAddr] ; mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] ; cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local ; jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
; Send it. ; Send it.
pop ebx pop ebx
call queue ;;; call queue
.exit: .exit:
ret ret
@ -822,13 +889,13 @@ proc stateTCB_ESTABLISHED stdcall, sockAddr:DWORD
mov ecx, 0 mov ecx, 0
.next_resendq: .next_resendq:
cmp ecx, NUMRESENDENTRIES ; cmp ecx, NUMRESENDENTRIES
je .last_resendq ; None left ; je .last_resendq ; None left
cmp [esi + 4], eax ; cmp [esi + 4], eax
je @f ; found one ; je @f ; found one
inc ecx ; inc ecx
add esi, 8 ; add esi, 8
jmp .next_resendq ; jmp .next_resendq
@@: mov dword[esi + 4], 0 @@: mov dword[esi + 4], 0
inc ecx inc ecx
@ -881,7 +948,7 @@ proc stateTCB_ESTABLISHED stdcall, sockAddr:DWORD
; Read the data bytes, store in socket buffer ; Read the data bytes, store in socket buffer
movzx ecx, [edx + IP_Packet.TotalLength] ; movzx ecx, [edx + IP_Packet.TotalLength]
xchg cl, ch xchg cl, ch
sub ecx, 40 ; Discard 40 bytes of header sub ecx, 40 ; Discard 40 bytes of header
ja .data ; Read data, if any ja .data ; Read data, if any
@ -943,9 +1010,9 @@ proc stateTCB_ESTABLISHED stdcall, sockAddr:DWORD
.ack: .ack:
; Send an ACK ; Send an ACK
; Now construct the response, and queue for sending by IP ; Now construct the response, and queue for sending by IP
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
je .exit je .exit
push eax push eax
@ -953,20 +1020,20 @@ proc stateTCB_ESTABLISHED stdcall, sockAddr:DWORD
mov bl, TH_ACK mov bl, TH_ACK
xor ecx, ecx xor ecx, ecx
xor esi, esi xor esi, esi
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; mov edx, [stack_ip] ;;; mov edx, [stack_ip]
mov ecx, [sockAddr] ; mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] ; cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local ; jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
; Send it. ; Send it.
pop ebx pop ebx
call queue ;;; call queue
.exit: .exit:
ret ret
@ -1000,9 +1067,9 @@ proc stateTCB_FIN_WAIT_1 stdcall, sockAddr:DWORD
call inc_inet_esi call inc_inet_esi
; Send an ACK ; Send an ACK
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
je .exit je .exit
push eax push eax
@ -1010,19 +1077,19 @@ proc stateTCB_FIN_WAIT_1 stdcall, sockAddr:DWORD
mov bl, TH_ACK mov bl, TH_ACK
xor ecx, ecx xor ecx, ecx
xor esi, esi xor esi, esi
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; mov edx, [stack_ip] ;;; mov edx, [stack_ip]
mov ecx, [sockAddr] ; mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] ; cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local ; jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
; Send it. ; Send it.
pop ebx pop ebx
call queue ;;; call queue
.exit: .exit:
ret ret
@ -1040,29 +1107,29 @@ proc stateTCB_FIN_WAIT_2 stdcall, sockAddr:DWORD
call inc_inet_esi call inc_inet_esi
; Send an ACK ; Send an ACK
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ;; cmp ax, NO_BUFFER
je .exit ; je .exit
push eax push eax
mov bl, TH_ACK mov bl, TH_ACK
xor ecx, ecx xor ecx, ecx
xor esi, esi xor esi, esi
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; mov edx, [stack_ip] ;;; mov edx, [stack_ip]
mov ecx, [sockAddr] mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
; Send it. ; Send it.
pop ebx pop ebx
call queue ;;; call queue
.exit: .exit:
ret ret
@ -1119,8 +1186,8 @@ endp
; @param EDX is pointer to application data buffer ; @param EDX is pointer to application data buffer
; @return 0 (sent successfully) or -1 (error) in EAX ; @return 0 (sent successfully) or -1 (error) in EAX
;; ;;
proc socket_write_tcp stdcall ;proc socket_write_tcp stdcall
local sockAddr dd ? ;local sockAddr dd ?
; DEBUGF 1, "socket_write_tcp(0x%x)\n", ebx ; DEBUGF 1, "socket_write_tcp(0x%x)\n", ebx
stdcall net_socket_num_to_addr, ebx stdcall net_socket_num_to_addr, ebx
@ -1128,16 +1195,16 @@ local sockAddr dd ?
jz .error jz .error
mov ebx, eax mov ebx, eax
mov [sockAddr], ebx ; mov [sockAddr], ebx
; If the sockets window timer is nonzero, do not queue Packet ; If the sockets window timer is nonzero, do not queue Packet
cmp [ebx + SOCKET.wndsizeTimer], 0 cmp [ebx + SOCKET.wndsizeTimer], 0
jne .error jne .error
mov eax, EMPTY_QUEUE ; mov eax, EMPTY_QUEUE
call dequeue ; call dequeue
cmp ax, NO_BUFFER ; cmp ax, NO_BUFFER
je .error ; je .error
push eax push eax
@ -1152,7 +1219,7 @@ local sockAddr dd ?
push ecx push ecx
mov bl, TH_ACK mov bl, TH_ACK
stdcall build_tcp_Packet, [sockAddr] ; stdcall build_tcp_Packet, [sockAddr]
pop ecx pop ecx
; Check destination IP address. ; Check destination IP address.
@ -1161,24 +1228,24 @@ local sockAddr dd ?
pop ebx pop ebx
push ecx push ecx
mov eax, NET1OUT_QUEUE ; mov eax, NET1OUT_QUEUE
;;; TODO: get device id in edx ;;; TODO: get device id in edx
xor edx, edx xor edx, edx
shl edx, 2 shl edx, 2
mov edx, [IP_LIST+edx] mov edx, [IP_LIST+edx]
mov ecx, [sockAddr] ; mov ecx, [sockAddr]
cmp edx, [ecx + SOCKET.RemoteIP] ; cmp edx, [ecx + SOCKET.RemoteIP]
jne .not_local ; jne .not_local
mov eax, IPIN_QUEUE ; mov eax, IPIN_QUEUE
.not_local: .not_local:
pop ecx pop ecx
push ebx ; save ipbuffer number push ebx ; save ipbuffer number
call queue ;;;; call queue
mov esi, [sockAddr] ; mov esi, [sockAddr]
; increament SND.NXT in socket ; increament SND.NXT in socket
; Amount to increment by is in ecx ; Amount to increment by is in ecx
@ -1193,7 +1260,7 @@ local sockAddr dd ?
mov ecx, 0 mov ecx, 0
.next_resendq: .next_resendq:
cmp ecx, NUMRESENDENTRIES ; cmp ecx, NUMRESENDENTRIES
je .exit ; None found je .exit ; None found
cmp dword[esi + 4], 0 cmp dword[esi + 4], 0
je @f ; found one je @f ; found one
@ -1211,28 +1278,28 @@ local sockAddr dd ?
; retry time ; retry time
; fill IP buffer associated with this descriptor ; fill IP buffer associated with this descriptor
stdcall net_socket_addr_to_num, [sockAddr] ; stdcall net_socket_addr_to_num, [sockAddr]
mov [esi + 4], eax mov [esi + 4], eax
mov byte[esi + 1], TCP_RETRIES mov byte[esi + 1], TCP_RETRIES
mov word[esi + 2], TCP_TIMEOUT mov word[esi + 2], TCP_TIMEOUT
inc ecx inc ecx
; Now get buffer location, and copy buffer across. argh! more copying,, ; Now get buffer location, and copy buffer across. argh! more copying,,
mov edi, resendBuffer - IPBUFFSIZE ; mov edi, resendBuffer - IPBUFFSIZE
@@: add edi, IPBUFFSIZE ; @@: add edi, IPBUFFSIZE
loop @b loop @b
; we have dest buffer location in edi ; we have dest buffer location in edi
pop eax pop eax
; convert source buffer pointer eax to the absolute address ; convert source buffer pointer eax to the absolute address
mov ecx, IPBUFFSIZE ; mov ecx, IPBUFFSIZE
mul ecx ; mul ecx
add eax, IPbuffs ; add eax, IPbuffs
mov esi, eax ; mov esi, eax
; do copy ; do copy
mov ecx, IPBUFFSIZE ; mov ecx, IPBUFFSIZE
; cld ; cld
rep movsb rep movsb
@ -1243,7 +1310,7 @@ local sockAddr dd ?
.error: .error:
or eax, -1 or eax, -1
ret ret
endp ;endp
@ -1262,10 +1329,10 @@ endp
checksum: checksum:
pusha pusha
mov eax, [checkAdd1] ; mov eax, [checkAdd1]
xor edx, edx ; edx is the accumulative checksum xor edx, edx ; edx is the accumulative checksum
xor ebx, ebx xor ebx, ebx
mov cx, [checkSize1] ; mov cx, [checkSize1]
shr cx, 1 shr cx, 1
jz cs1_1 jz cs1_1
@ -1279,7 +1346,7 @@ cs1:
loopw cs1 loopw cs1
cs1_1: cs1_1:
and word [checkSize1], 0x01 ; and word [checkSize1], 0x01
jz cs_test2 jz cs_test2
mov bh, [eax] mov bh, [eax]
@ -1288,11 +1355,11 @@ cs1_1:
add edx, ebx add edx, ebx
cs_test2: cs_test2:
mov cx, [checkSize2] ; mov cx, [checkSize2]
cmp cx, 0 cmp cx, 0
jz cs_exit ; Finished if no 2nd buffer jz cs_exit ; Finished if no 2nd buffer
mov eax, [checkAdd2] ; mov eax, [checkAdd2]
shr cx, 1 shr cx, 1
jz cs2_1 jz cs2_1
@ -1307,7 +1374,7 @@ cs2:
loopw cs2 loopw cs2
cs2_1: cs2_1:
and word [checkSize2], 0x01 ; and word [checkSize2], 0x01
jz cs_exit jz cs_exit
mov bh, [eax] mov bh, [eax]
@ -1326,21 +1393,7 @@ cs_exit:
add edx, eax add edx, eax
not dx not dx
mov [checkResult], dx ; mov [checkResult], dx
popa popa
ret ret
TCP_HANDLER:
;;; TODO: write code here
call kernel_free
add esp, 4 ; pop (balance stack)
ret

View File

@ -1,6 +1,6 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; ;; ;; ;;
;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;; ;; Copyright (C) KolibriOS team 2004-2009. All rights reserved. ;;
;; Distributed under terms of the GNU General Public License ;; ;; Distributed under terms of the GNU General Public License ;;
;; ;; ;; ;;
;; UDP.INC ;; ;; UDP.INC ;;
@ -73,7 +73,7 @@ UDP_init:
; ;
;----------------------------------------------------------------- ;-----------------------------------------------------------------
UDP_Handler: UDP_handler:
DEBUGF 1,"UDP_Handler\n" DEBUGF 1,"UDP_Handler\n"
; TODO: First validate the header & checksum. Discard buffer if error ; TODO: First validate the header & checksum. Discard buffer if error
@ -110,7 +110,6 @@ UDP_Handler:
@@: @@:
DEBUGF 1,"Found valid UDP packet for socket %x\n", esi DEBUGF 1,"Found valid UDP packet for socket %x\n", esi
; sub ecx, UDP_Packet.Data ; get # of bytes in ecx ; sub ecx, UDP_Packet.Data ; get # of bytes in ecx
; mov eax, ecx ; mov eax, ecx
@ -199,12 +198,12 @@ UDP_Handler:
; IN: eax = dest ip ; IN: eax = dest ip
; ebx = source ip ; ebx = source ip
; ecx = data length ; ecx = data length
; edx = remote port shl 16 + local port ; edx = remote port shl 16 + local port (both in INET order)
; esi = data offset ; esi = data offset
; ;
;----------------------------------------------------------------- ;-----------------------------------------------------------------
UDP_create_Packet: UDP_create_packet:
DEBUGF 1,"Create UDP Packet\n" DEBUGF 1,"Create UDP Packet\n"
@ -215,13 +214,13 @@ UDP_create_Packet:
; dx = fragment id ; dx = fragment id
call IPv4_create_Packet ; TODO: figure out a way to choose between IPv4 and IPv6 call IPv4_create_packet ; TODO: figure out a way to choose between IPv4 and IPv6
cmp edi, -1 cmp edi, -1
je .exit je .exit
sub ecx , UDP_Packet.Data
mov byte[edi + UDP_Packet.Length], ch mov byte[edi + UDP_Packet.Length], ch
mov byte[edi + UDP_Packet.Length+1], cl mov byte[edi + UDP_Packet.Length+1], cl
sub ecx , UDP_Packet.Data
pop esi pop esi
push edi push edi
@ -235,8 +234,8 @@ UDP_create_Packet:
pop edi pop edi
pop ecx pop ecx
bswap ecx ; convert little endian - big endian ; bswap ecx ; convert little endian - big endian
rol ecx, 16 ; ; rol ecx, 16 ;
mov dword [edi + UDP_Packet.SourcePort], ecx ; notice: we write both port's at once mov dword [edi + UDP_Packet.SourcePort], ecx ; notice: we write both port's at once