Compare commits
4
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
36854f1382 | ||
|
|
f990a48b98 | ||
|
|
fb2906bc1d | ||
|
|
9c58dc1f04 |
No files matched your search
@@ -463,7 +463,7 @@ proc kernel_alloc stdcall, size:dword
|
||||
and eax, -PAGE_SIZE;
|
||||
mov [size], eax
|
||||
and eax, eax
|
||||
jz .err
|
||||
jz .err0
|
||||
mov ebx, eax
|
||||
shr ebx, 12
|
||||
mov [pages_count], ebx
|
||||
@@ -509,6 +509,13 @@ proc kernel_alloc stdcall, size:dword
|
||||
pop ebx
|
||||
ret
|
||||
.err:
|
||||
mov eax, [lin_addr]
|
||||
test eax, eax
|
||||
jz .err0
|
||||
mov ecx, [pages_count]
|
||||
call release_pages
|
||||
stdcall free_kernel_space, [lin_addr]
|
||||
.err0:
|
||||
xor eax, eax
|
||||
pop edi
|
||||
pop ebx
|
||||
|
||||
@@ -1397,7 +1397,9 @@ proc create_ring_buffer stdcall, size:dword, flags:dword
|
||||
mov [page_tabs + edi], eax
|
||||
mov [page_tabs + edi + edx], eax
|
||||
invlpg [ebx]
|
||||
invlpg [ebx+0x10000]
|
||||
add ebx, [size]
|
||||
invlpg [ebx] ; the mirror half
|
||||
sub ebx, [size]
|
||||
add eax, 0x1000
|
||||
add ebx, 0x1000
|
||||
add edi, 4
|
||||
@@ -1416,6 +1418,62 @@ proc create_ring_buffer stdcall, size:dword, flags:dword
|
||||
ret
|
||||
endp
|
||||
|
||||
; Same as create_ring_buffer, but from non-contiguous pages.
|
||||
; Not for DMA. Free with kernel_free.
|
||||
align 4
|
||||
proc create_ring_buffer_sparse stdcall, size:dword, flags:dword
|
||||
locals
|
||||
buf_ptr dd ?
|
||||
endl
|
||||
|
||||
mov eax, [size]
|
||||
test eax, eax
|
||||
jz .fail
|
||||
|
||||
add eax, eax
|
||||
stdcall alloc_kernel_space, eax
|
||||
test eax, eax
|
||||
jz .fail
|
||||
mov [buf_ptr], eax
|
||||
|
||||
push ebx esi edi
|
||||
mov ebx, eax ; page being mapped
|
||||
mov esi, [size] ; distance to its mirror
|
||||
mov edi, esi
|
||||
shr edi, 12 ; pages left
|
||||
.page:
|
||||
call alloc_page
|
||||
test eax, eax
|
||||
jz .mm_fail
|
||||
or eax, [flags]
|
||||
mov edx, ebx
|
||||
shr edx, 12
|
||||
mov [page_tabs + edx*4], eax
|
||||
invlpg [ebx]
|
||||
lea edx, [ebx + esi]
|
||||
shr edx, 12
|
||||
mov [page_tabs + edx*4], eax
|
||||
invlpg [ebx + esi]
|
||||
add ebx, PAGE_SIZE
|
||||
dec edi
|
||||
jnz .page
|
||||
|
||||
mov eax, [buf_ptr]
|
||||
pop edi esi ebx
|
||||
ret
|
||||
|
||||
.mm_fail:
|
||||
mov eax, [buf_ptr]
|
||||
mov ecx, [size]
|
||||
shr ecx, 11 ; both halves, in pages
|
||||
call release_pages
|
||||
stdcall free_kernel_space, [buf_ptr]
|
||||
pop edi esi ebx
|
||||
xor eax, eax
|
||||
.fail:
|
||||
ret
|
||||
endp
|
||||
|
||||
|
||||
align 4
|
||||
proc print_mem
|
||||
|
||||
@@ -198,6 +198,10 @@ ends
|
||||
|
||||
SOCKET_STRUCT_SIZE = 4096 ; in bytes
|
||||
|
||||
if sizeof.STREAM_SOCKET > SOCKET_STRUCT_SIZE
|
||||
err "STREAM_SOCKET does not fit in SOCKET_STRUCT_SIZE"
|
||||
end if
|
||||
|
||||
SOCKET_QUEUE_SIZE = 10 ; maximum number of incoming packets queued for 1 socket
|
||||
; the incoming packet queue for sockets is placed in the socket struct itself, at this location from start
|
||||
SOCKET_QUEUE_LOCATION = (SOCKET_STRUCT_SIZE - SOCKET_QUEUE_SIZE*sizeof.socket_queue_entry - sizeof.queue)
|
||||
@@ -1647,7 +1651,7 @@ socket_ring_create:
|
||||
mov esi, eax
|
||||
|
||||
push edx
|
||||
stdcall create_ring_buffer, SOCKET_BUFFER_SIZE, PG_SWR
|
||||
stdcall create_ring_buffer_sparse, SOCKET_BUFFER_SIZE, PG_SWR
|
||||
pop edx
|
||||
test eax, eax
|
||||
jz .fail
|
||||
|
||||
@@ -63,7 +63,7 @@ TCP_OPT_TIMESTAMP = 8
|
||||
TCP_time_MSL = 47 ; max segment lifetime (30s)
|
||||
TCP_time_re_min = 2 ; min retransmission (1,28s)
|
||||
TCP_time_re_max = 100 ; max retransmission (64s)
|
||||
TCP_time_pers_min = 2 ; min persist (1,28s)
|
||||
TCP_time_pers_min = 8 ; min persist (5,12s)
|
||||
TCP_time_pers_max = 94 ; max persist (60,16s)
|
||||
TCP_time_keep_init = 118 ; connection establishment (75,52s)
|
||||
TCP_time_keep_idle = 4608 ; idle time before 1st probe (2h)
|
||||
|
||||
@@ -525,11 +525,8 @@ endl
|
||||
|
||||
test [temp_bits], TCP_BIT_TIMESTAMP
|
||||
jz .no_timestamp_rtt
|
||||
cmp [ebx + TCP_SOCKET.ts_ecr], 0 ; nothing echoed
|
||||
je .no_timestamp_rtt
|
||||
mov eax, [timestamp]
|
||||
sub eax, [ebx + TCP_SOCKET.ts_ecr]
|
||||
shr eax, 6 ; 1/100 s -> 640 ms ticks
|
||||
inc eax
|
||||
call tcp_xmit_timer
|
||||
jmp .rtt_done
|
||||
@@ -1117,11 +1114,8 @@ endl
|
||||
|
||||
test [temp_bits], TCP_BIT_TIMESTAMP
|
||||
jz .timestamp_not_present
|
||||
cmp [ebx + TCP_SOCKET.ts_ecr], 0 ; nothing echoed
|
||||
je .timestamp_not_present
|
||||
mov eax, [timestamp]
|
||||
sub eax, [ebx + TCP_SOCKET.ts_ecr]
|
||||
shr eax, 6 ; 1/100 s -> 640 ms ticks
|
||||
inc eax
|
||||
call tcp_xmit_timer
|
||||
jmp .rtt_done_
|
||||
|
||||
@@ -626,7 +626,7 @@ endl
|
||||
mov [eax + TCP_SOCKET.SND_MAX], edx ; [eax + TCP_SOCKET.SND_NXT] from before we updated it
|
||||
|
||||
cmp [eax + TCP_SOCKET.t_rtt], 0 ; are we currently timing anything?
|
||||
jne @f
|
||||
je @f
|
||||
mov [eax + TCP_SOCKET.t_rtt], 1 ; nope, start transmission timer
|
||||
mov [eax + TCP_SOCKET.t_rtseq], edi
|
||||
inc [TCPS_segstimed]
|
||||
|
||||
@@ -96,7 +96,7 @@ macro tcp_init_socket socket {
|
||||
mov [socket + TCP_SOCKET.t_srtt], TCP_time_srtt_default
|
||||
mov [socket + TCP_SOCKET.t_rttvar], TCP_time_rtt_default * 4
|
||||
mov [socket + TCP_SOCKET.t_rttmin], TCP_time_re_min
|
||||
mov [socket + TCP_SOCKET.t_rxtcur], TCP_time_rtt_default
|
||||
;;; TODO: TCP_time_rangeset
|
||||
|
||||
mov [socket + TCP_SOCKET.SND_CWND], TCP_max_win shl TCP_max_winshift
|
||||
mov [socket + TCP_SOCKET.SND_SSTHRESH], TCP_max_win shl TCP_max_winshift
|
||||
@@ -518,7 +518,7 @@ tcp_xmit_timer:
|
||||
|
||||
inc [TCPS_rttupdated]
|
||||
|
||||
cmp [ebx + TCP_SOCKET.t_srtt], 0 ; first sample?
|
||||
cmp [ebx + TCP_SOCKET.t_rtt], 0
|
||||
je .no_rtt_yet
|
||||
|
||||
; srtt is stored as a fixed point with 3 bits after the binary point.
|
||||
@@ -534,7 +534,7 @@ tcp_xmit_timer:
|
||||
pop ecx
|
||||
|
||||
add [ebx + TCP_SOCKET.t_srtt], eax
|
||||
jg @f ; signed: delta may be negative
|
||||
ja @f
|
||||
mov [ebx + TCP_SOCKET.t_srtt], 1
|
||||
@@:
|
||||
|
||||
@@ -556,10 +556,10 @@ tcp_xmit_timer:
|
||||
pop edx
|
||||
|
||||
add [ebx + TCP_SOCKET.t_rttvar], eax
|
||||
jg @f
|
||||
ja @f
|
||||
mov [ebx + TCP_SOCKET.t_rttvar], 1
|
||||
@@:
|
||||
jmp .rto
|
||||
ret
|
||||
|
||||
|
||||
.no_rtt_yet:
|
||||
@@ -572,16 +572,6 @@ tcp_xmit_timer:
|
||||
mov [ebx + TCP_SOCKET.t_rttvar], eax
|
||||
pop ecx
|
||||
|
||||
.rto:
|
||||
; Retransmit timeout = srtt + 4*rttvar, reset the backoff
|
||||
push ecx
|
||||
mov ecx, [ebx + TCP_SOCKET.t_srtt]
|
||||
shr ecx, TCP_RTT_SHIFT
|
||||
add ecx, [ebx + TCP_SOCKET.t_rttvar]
|
||||
tcpt_rangeset [ebx + TCP_SOCKET.t_rxtcur], ecx, TCP_time_re_min, TCP_time_re_max
|
||||
pop ecx
|
||||
mov [ebx + TCP_SOCKET.t_rxtshift], 0
|
||||
mov [ebx + TCP_SOCKET.t_rtt], 0 ; the timed segment is done
|
||||
ret
|
||||
|
||||
|
||||
|
||||
@@ -91,10 +91,6 @@ proc tcp_timer_640ms
|
||||
jne .loop
|
||||
|
||||
inc [eax + TCP_SOCKET.t_idle]
|
||||
cmp [eax + TCP_SOCKET.t_rtt], 0 ; timing a segment?
|
||||
je @f
|
||||
inc [eax + TCP_SOCKET.t_rtt]
|
||||
@@:
|
||||
|
||||
test [eax + TCP_SOCKET.timer_flags], timer_flag_retransmission
|
||||
jz .check_more2
|
||||
@@ -103,95 +99,6 @@ proc tcp_timer_640ms
|
||||
|
||||
DEBUGF DEBUG_NETWORK_VERBOSE, "socket %x: Retransmission timer expired\n", eax
|
||||
|
||||
; Lock socket, an ACK may have stopped or restarted the timer meanwhile
|
||||
pusha
|
||||
lea ecx, [eax + SOCKET.mutex]
|
||||
call mutex_lock
|
||||
popa
|
||||
test [eax + TCP_SOCKET.timer_flags], timer_flag_retransmission
|
||||
jz .rexmt_cancelled
|
||||
cmp [eax + TCP_SOCKET.timer_retransmission], 0
|
||||
jne .rexmt_cancelled
|
||||
|
||||
; Too many retransmissions? Drop the connection
|
||||
inc [eax + TCP_SOCKET.t_rxtshift]
|
||||
cmp [eax + TCP_SOCKET.t_rxtshift], TCP_max_rxtshift
|
||||
jbe .rexmt
|
||||
|
||||
pusha
|
||||
lea ecx, [eax + SOCKET.mutex]
|
||||
call mutex_unlock
|
||||
popa
|
||||
|
||||
DEBUGF DEBUG_NETWORK_VERBOSE, "socket %x: too many retransmissions, dropping\n", eax
|
||||
|
||||
push [eax + SOCKET.NextPtr]
|
||||
mov ebx, ETIMEDOUT
|
||||
call tcp_drop
|
||||
pop eax
|
||||
jmp .check_only
|
||||
|
||||
.rexmt_cancelled:
|
||||
pusha
|
||||
lea ecx, [eax + SOCKET.mutex]
|
||||
call mutex_unlock
|
||||
popa
|
||||
jmp .check_more2
|
||||
|
||||
.rexmt:
|
||||
push ebx ecx edx
|
||||
|
||||
; Restart timer with backoff: t_rxtcur << min(t_rxtshift, 6)
|
||||
mov ebx, [eax + TCP_SOCKET.t_rxtcur]
|
||||
mov cl, [eax + TCP_SOCKET.t_rxtshift]
|
||||
cmp cl, 6
|
||||
jbe @f
|
||||
mov cl, 6
|
||||
@@:
|
||||
shl ebx, cl
|
||||
cmp ebx, TCP_time_re_min
|
||||
jae @f
|
||||
mov ebx, TCP_time_re_min
|
||||
@@:
|
||||
cmp ebx, TCP_time_re_max
|
||||
jbe @f
|
||||
mov ebx, TCP_time_re_max
|
||||
@@:
|
||||
mov [eax + TCP_SOCKET.timer_retransmission], ebx
|
||||
|
||||
; Resend from the last acknowledged byte, don't time it
|
||||
push [eax + TCP_SOCKET.SND_UNA]
|
||||
pop [eax + TCP_SOCKET.SND_NXT]
|
||||
mov [eax + TCP_SOCKET.t_rtt], 0
|
||||
mov [eax + TCP_SOCKET.t_dupacks], 0
|
||||
|
||||
; Slow start: ssthresh = max(2, min(wnd, cwnd) / 2 / mss) * mss, cwnd = mss
|
||||
mov ecx, [eax + TCP_SOCKET.t_maxseg]
|
||||
mov edx, [eax + TCP_SOCKET.SND_WND]
|
||||
cmp edx, [eax + TCP_SOCKET.SND_CWND]
|
||||
jbe @f
|
||||
mov edx, [eax + TCP_SOCKET.SND_CWND]
|
||||
@@:
|
||||
mov ebx, eax ; socket ptr
|
||||
mov eax, edx
|
||||
shr eax, 1
|
||||
xor edx, edx
|
||||
div ecx
|
||||
cmp eax, 2
|
||||
jae @f
|
||||
mov eax, 2
|
||||
@@:
|
||||
mul ecx
|
||||
mov [ebx + TCP_SOCKET.SND_SSTHRESH], eax
|
||||
mov [ebx + TCP_SOCKET.SND_CWND], ecx
|
||||
mov eax, ebx
|
||||
pop edx ecx ebx
|
||||
|
||||
pusha
|
||||
lea ecx, [eax + SOCKET.mutex]
|
||||
call mutex_unlock
|
||||
popa
|
||||
|
||||
push eax
|
||||
call tcp_output
|
||||
pop eax
|
||||
|
||||
Reference in new issue
Block a user