Subversion Repositories Kolibri OS

Rev

Rev 6474 | Rev 6909 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 6474 Rev 6476
Line 12... Line 12...
12
;;          GNU GENERAL PUBLIC LICENSE                             ;;
12
;;          GNU GENERAL PUBLIC LICENSE                             ;;
13
;;             Version 2, June 1991                                ;;
13
;;             Version 2, June 1991                                ;;
14
;;                                                                 ;;
14
;;                                                                 ;;
15
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
15
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
Line 16... Line 16...
16
 
16
 
-
 
17
$Revision: 6476 $
-
 
18
 
Line 17... Line 19...
17
$Revision: 6474 $
19
TCP_BIT_SENDALOT        = 1 shl 0
18
 
20
 
19
;-----------------------------------------------------------------;
21
;-----------------------------------------------------------------;
20
;                                                                 ;
22
;                                                                 ;
Line 62... Line 64...
62
 
64
 
63
  .not_idle:
65
  .not_idle:
64
  .again:
66
  .again:
Line -... Line 67...
-
 
67
        mov     [temp_bits], 0
-
 
68
 
65
        mov     [temp_bits], 0
69
; Calculate offset
66
 
70
 
-
 
71
        mov     ebx, [eax + TCP_SOCKET.SND_NXT]
-
 
72
        sub     ebx, [eax + TCP_SOCKET.SND_UNA]
Line 67... Line 73...
67
        mov     ebx, [eax + TCP_SOCKET.SND_NXT]         ; calculate offset (71)
73
 
68
        sub     ebx, [eax + TCP_SOCKET.SND_UNA]         ;
74
; Determine window
69
 
75
 
70
        mov     ecx, [eax + TCP_SOCKET.SND_WND]         ; determine window
76
        mov     ecx, [eax + TCP_SOCKET.SND_WND]
71
        cmp     ecx, [eax + TCP_SOCKET.SND_CWND]        ;
77
        cmp     ecx, [eax + TCP_SOCKET.SND_CWND]
Line -... Line 78...
-
 
78
        jb      @f
-
 
79
        mov     ecx, [eax + TCP_SOCKET.SND_CWND]
72
        jb      @f                                      ;
80
       @@:
Line 73... Line 81...
73
        mov     ecx, [eax + TCP_SOCKET.SND_CWND]        ;
81
 
74
       @@:                                              ;
82
; get flags in dl
Line 75... Line 83...
75
 
83
 
Line 103... Line 111...
103
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
111
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
Line 104... Line 112...
104
 
112
 
Line 105... Line 113...
105
  .no_force:
113
  .no_force:
106
 
114
 
Line 107... Line 115...
107
;--------------------------------
115
;--------------------------------
108
; Calculate how much data to send (106)
116
; Calculate how much data to send
109
 
117
 
110
        mov     esi, [eax + STREAM_SOCKET.snd.size]
118
        mov     esi, [eax + STREAM_SOCKET.snd.size]
111
        cmp     esi, ecx
119
        cmp     esi, ecx
112
        jb      @f
120
        jb      @f
Line 113... Line 121...
113
        mov     esi, ecx
121
        mov     esi, ecx
114
       @@:
122
       @@:
Line 115... Line 123...
115
        sub     esi, ebx
123
        sub     esi, ebx
116
 
124
 
Line 117... Line 125...
117
;------------------------
125
;------------------------
Line 118... Line 126...
118
; check for window shrink (107)
126
; check for window shrink
-
 
127
 
119
 
128
; If FIN has been sent, but not ACKed, but we havent been called to retransmit, esi will be -1
Line 120... Line 129...
120
; If FIN has been set, but not ACKed, but we havent been called to retransmit, esi will be -1
129
; Otherwise, window shrank after we sent into it.
-
 
130
 
121
; Otherwise, window shrank after we sent into it.
131
        jae     .not_persist
122
 
132
 
Line 123... Line 133...
123
        jae     .not_persist
133
; enter persist state
-
 
134
 
124
 
135
        xor     esi, esi
Line 125... Line 136...
125
; enter persist state
136
 
-
 
137
; If window shrank to 0
126
        xor     esi, esi
138
 
127
 
139
        test    ecx, ecx
128
; If window shrank to 0
140
        jnz     @f
Line 129... Line 141...
129
        test    ecx, ecx
141
 
Line 130... Line 142...
130
        jnz     @f
142
; cancel pending retransmit
Line 131... Line 143...
131
 
143
 
132
; cancel pending retransmit
144
        and     [eax + TCP_SOCKET.timer_flags], not timer_flag_retransmission
Line 133... Line 145...
133
        and     [eax + TCP_SOCKET.timer_flags], not timer_flag_retransmission
145
 
134
 
146
; pull SND_NXT back to (closed) window, We will enter persist state below.
135
; pull SND_NXT back to (closed) window, We will enter persist state below.
147
 
136
        push    [eax + TCP_SOCKET.SND_UNA]
148
        push    [eax + TCP_SOCKET.SND_UNA]
137
        pop     [eax + TCP_SOCKET.SND_NXT]
149
        pop     [eax + TCP_SOCKET.SND_NXT]
Line 138... Line 150...
138
       @@:
150
       @@:
139
 
151
 
Line 140... Line 152...
140
; If window didn't close completely, just wait for an ACK
152
; If window didn't close completely, just wait for an ACK
141
 
153
 
142
  .not_persist:
154
  .not_persist:
143
 
155
 
144
;---------------------------
156
;---------------------------
145
; Send one segment at a time (124)
157
; Send one segment at a time
146
 
158
 
Line 147... Line 159...
147
        cmp     esi, [eax + TCP_SOCKET.t_maxseg]
159
        cmp     esi, [eax + TCP_SOCKET.t_maxseg]
148
        jbe     @f
160
        jbe     @f
Line 149... Line 161...
149
        mov     esi, [eax + TCP_SOCKET.t_maxseg]
161
        mov     esi, [eax + TCP_SOCKET.t_maxseg]
150
        or      [temp_bits], TCP_BIT_SENDALOT
162
        or      [temp_bits], TCP_BIT_SENDALOT
Line 151... Line 163...
151
       @@:
163
       @@:
152
 
164
 
Line 153... Line 165...
153
;--------------------------------------------
165
;--------------------------------------------
154
; Turn of FIN flag if send buffer not emptied (128)
166
; Turn of FIN flag if send buffer not emptied
Line 155... Line 167...
155
 
167
 
Line 201... Line 213...
201
        jb      .send
213
        jb      .send
Line 202... Line 214...
202
 
214
 
Line 203... Line 215...
203
  .len_zero:
215
  .len_zero:
204
 
216
 
Line 205... Line 217...
205
;----------------------------------------
217
;----------------------------------------
Line 206... Line 218...
206
; Check if a window update should be sent (154)
218
; Check if a window update should be sent
207
 
219
 
Line 225... Line 237...
225
        mov     ebx, ecx
237
        mov     ebx, ecx
226
       @@:
238
       @@:
227
        sub     ebx, [eax + TCP_SOCKET.RCV_ADV]
239
        sub     ebx, [eax + TCP_SOCKET.RCV_ADV]
228
        add     ebx, [eax + TCP_SOCKET.RCV_NXT]
240
        add     ebx, [eax + TCP_SOCKET.RCV_NXT]
Line -... Line 241...
-
 
241
 
-
 
242
        DEBUGF  DEBUG_NETWORK_VERBOSE, "TCP_output: we can increase window by %d bytes\n", ebx
229
 
243
 
230
        mov     edi, [eax + TCP_SOCKET.t_maxseg]
244
        mov     edi, [eax + TCP_SOCKET.t_maxseg]
231
        shl     edi, 1
-
 
232
 
245
        shl     edi, 1
233
        cmp     ebx, edi
246
        cmp     ebx, edi
Line 234... Line 247...
234
        jae     .send
247
        jae     .send
235
 
248
 
236
        shl     ebx, 1
249
        shl     ebx, 1
Line 237... Line 250...
237
;        cmp     ebx, [eax + TCP_SOCKET.]    ;;; TODO: check with receive buffer high water mark
250
;        cmp     ebx, [eax + TCP_SOCKET.]    ;;; TODO: check with receive buffer high water mark
Line 238... Line 251...
238
;        jae     TCP_send
251
;        jae     TCP_send
239
 
252
 
-
 
253
  .no_window:
-
 
254
 
Line 240... Line 255...
240
  .no_window:
255
;--------------------------
241
 
256
; Should a segment be sent?
Line 242... Line 257...
242
;--------------------------
257
 
Line 250... Line 265...
250
 
265
 
251
        mov     ebx, [eax + TCP_SOCKET.SND_UP]          ; when urgent pointer is beyond start of send bufer
266
        mov     ebx, [eax + TCP_SOCKET.SND_UP]          ; when urgent pointer is beyond start of send bufer
252
        cmp     ebx, [eax + TCP_SOCKET.SND_UNA]
267
        cmp     ebx, [eax + TCP_SOCKET.SND_UNA]
Line -... Line 268...
-
 
268
        ja      .send
-
 
269
 
253
        ja      .send
270
; Do we need to send a FIN according to our state?
254
 
271
 
Line 255... Line 272...
255
        test    dl, TH_FIN
272
        test    dl, TH_FIN
Line 256... Line 273...
256
        jz      .enter_persist  ; no reason to send, enter persist state
273
        jz      .enter_persist                          ; no reason to send, enter persist state
257
 
274
 
Line -... Line 275...
-
 
275
; Do so if we didnt do it already
-
 
276
 
258
; FIN was set, only send if not already sent, or on retransmit
277
        test    [eax + TCP_SOCKET.t_flags], TF_SENTFIN
259
 
278
        jz      .send
260
        test    [eax + TCP_SOCKET.t_flags], TF_SENTFIN
279
 
Line 261... Line 280...
261
        jz      .send
280
; Or when we need to retransmit the FIN
262
 
281
 
Line 263... Line 282...
263
        mov     ebx, [eax + TCP_SOCKET.SND_NXT]
282
        mov     ebx, [eax + TCP_SOCKET.SND_NXT]
Line 264... Line 283...
264
        cmp     ebx, [eax + TCP_SOCKET.SND_UNA]
283
        cmp     ebx, [eax + TCP_SOCKET.SND_UNA]
265
        je      .send
284
        je      .send
Line 282... Line 301...
282
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
301
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
283
        call    tcp_set_persist
302
        call    tcp_set_persist
284
       @@:
303
       @@:
Line 285... Line 304...
285
 
304
 
286
;----------------------------
305
;----------------------------
Line 287... Line 306...
287
; No reason to send a segment (219)
306
; No reason to send a segment
Line 288... Line 307...
288
 
307
 
289
        DEBUGF  DEBUG_NETWORK_VERBOSE, "TCP_output: No reason to send a segment\n"
308
        DEBUGF  DEBUG_NETWORK_VERBOSE, "TCP_output: No reason to send a segment\n"
Line 298... Line 317...
298
        ret
317
        ret
Line 299... Line 318...
299
 
318
 
300
 
319
 
301
;-----------------------------------------------
320
;-----------------------------------------------
302
;
321
;
303
; Send a segment (222)
322
; Send a segment
304
;
323
;
305
; eax = socket pointer
324
; eax = socket pointer
306
; esi = data len
325
; esi = data len
Line 389... Line 408...
389
; edx = flags
408
; edx = flags
390
; edi = header size
409
; edi = header size
391
; esi = data len
410
; esi = data len
Line 392... Line 411...
392
 
411
 
393
;---------------------------------------------
412
;---------------------------------------------
Line 394... Line 413...
394
; check if we dont exceed the max segment size (270)
413
; check if we dont exceed the max segment size
395
 
414
 
396
        add     esi, edi                        ; total TCP segment size
415
        add     esi, edi                        ; total TCP segment size
Line 397... Line 416...
397
        cmp     esi, [eax + TCP_SOCKET.t_maxseg]
416
        cmp     esi, [eax + TCP_SOCKET.t_maxseg]
398
        jbe     .no_overflow
417
        jbe     .no_overflow
399
 
418
 
Line 400... Line 419...
400
        mov     esi, [eax + TCP_SOCKET.t_maxseg]
419
        mov     esi, [eax + TCP_SOCKET.t_maxseg]
-
 
420
        or      [temp_bits], TCP_BIT_SENDALOT
401
        or      [temp_bits], TCP_BIT_SENDALOT
421
  .no_overflow:
402
  .no_overflow:
422
 
Line 403... Line 423...
403
 
423
; Update stats
404
; Update stats
424
 
Line 480... Line 500...
480
 
500
 
481
;-----------------------------------------------------------------
501
;-----------------------------------------------------------------
482
; Start by pushing all TCP header values in reverse order on stack
502
; Start by pushing all TCP header values in reverse order on stack
Line 483... Line 503...
483
; (essentially, creating the tcp header on the stack!)
503
; (essentially, creating the tcp header on the stack!)
484
 
504
 
485
        pushw   0       ;        .UrgentPointer          dw ?
505
        pushw   0                               ; UrgentPointer
486
        pushw   0       ;        .Checksum               dw ?
506
        pushw   0                               ; Checksum
487
        pushw   bx      ;        .Window                 dw ?
507
        pushw   bx                              ; Window
488
        shl     edi, 2  ;        .DataOffset             db ?  only 4 left-most bits
508
        shl     edi, 2                          ; DataOffset
489
        shl     dx, 8
509
        shl     dx, 8
490
        or      dx, di  ;        .Flags                  db ?
510
        or      dx, di                          ; Flags
Line 491... Line 511...
491
        pushw   dx
511
        pushw   dx
492
        shr     edi, 2  ;        .DataOffset             db ?
512
        shr     edi, 2                          ; DataOffset
Line 493... Line 513...
493
 
513
 
494
        push    [eax + TCP_SOCKET.RCV_NXT]      ;        .AckNumber              dd ?
514
        push    [eax + TCP_SOCKET.RCV_NXT]      ; AckNumber
Line 495... Line 515...
495
        ntohd   [esp]
515
        ntohd   [esp]
496
 
516
 
Line 497... Line 517...
497
        push    [eax + TCP_SOCKET.SND_NXT]      ;        .SequenceNumber         dd ?
517
        push    [eax + TCP_SOCKET.SND_NXT]      ; SequenceNumber
Line 498... Line 518...
498
        ntohd   [esp]
518
        ntohd   [esp]
499
 
519
 
Line 556... Line 576...
556
        pop     edi
576
        pop     edi
557
        pop     esi                             ; begin of data
577
        pop     esi                             ; begin of data
558
        pop     ecx                             ; full packet size
578
        pop     ecx                             ; full packet size
559
        mov     eax, [esp + 8]                  ; socket ptr
579
        mov     eax, [esp + 8]                  ; socket ptr
Line 560... Line 580...
560
 
580
 
561
;----------------------------------
581
;----------------------------
Line 562... Line 582...
562
; initialize retransmit timer (400)
582
; initialize retransmit timer
Line 563... Line 583...
563
 
583
 
564
;TODO: check t_force and persist
584
;TODO: check t_force and persist
Line 582... Line 602...
582
        mov     [eax + TCP_SOCKET.t_rtseq], edi
602
        mov     [eax + TCP_SOCKET.t_rtseq], edi
583
        inc     [TCPS_segstimed]
603
        inc     [TCPS_segstimed]
584
       @@:
604
       @@:
Line 585... Line 605...
585
 
605
 
-
 
606
; set retransmission timer if not already set, and not doing an ACK or keepalive probe
586
; set retransmission timer if not already set, and not doing an ACK or keepalive probe
607
 
587
        test    [eax + TCP_SOCKET.timer_flags], timer_flag_retransmission
608
        test    [eax + TCP_SOCKET.timer_flags], timer_flag_retransmission
Line 588... Line 609...
588
        jnz     .retransmit_set
609
        jnz     .retransmit_set
589
 
610
 
Line 596... Line 617...
596
 
617
 
597
        test    [eax + TCP_SOCKET.timer_flags], timer_flag_persist
618
        test    [eax + TCP_SOCKET.timer_flags], timer_flag_persist
598
        jz      .retransmit_set
619
        jz      .retransmit_set
599
        and     [eax + TCP_SOCKET.timer_flags], not timer_flag_persist
620
        and     [eax + TCP_SOCKET.timer_flags], not timer_flag_persist
600
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
-
 
601
 
621
        mov     [eax + TCP_SOCKET.t_rxtshift], 0
Line 602... Line 622...
602
  .retransmit_set:
622
  .retransmit_set:
603
 
623
 
Line 640... Line 660...
640
        jbe     @f
660
        jbe     @f
641
        mov     [eax + TCP_SOCKET.RCV_ADV], ecx
661
        mov     [eax + TCP_SOCKET.RCV_ADV], ecx
642
       @@:
662
       @@:
Line 643... Line 663...
643
 
663
 
-
 
664
; update last ack sent
644
; update last ack sent
665
 
645
        push    [eax + TCP_SOCKET.RCV_NXT]
666
        push    [eax + TCP_SOCKET.RCV_NXT]
Line 646... Line 667...
646
        pop     [eax + TCP_SOCKET.last_ack_sent]
667
        pop     [eax + TCP_SOCKET.last_ack_sent]
-
 
668
 
647
 
669
; clear the ACK flags
Line 648... Line 670...
648
; clear the ACK flags
670
 
649
        and     [eax + TCP_SOCKET.t_flags], not (TF_ACKNOW + TF_DELACK)
671
        and     [eax + TCP_SOCKET.t_flags], not (TF_ACKNOW + TF_DELACK)