Subversion Repositories Kolibri OS

Rev

Rev 2403 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
1159 hidnplayr 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                                 ;;
2362 hidnplayr 3
;; Copyright (C) KolibriOS team 2004-2012. All rights reserved.    ;;
1159 hidnplayr 4
;; Distributed under terms of the GNU General Public License       ;;
5
;;                                                                 ;;
1529 hidnplayr 6
;;    Written by hidnplayr@kolibrios.org,                          ;;
7
;;     and Clevermouse.                                            ;;
1159 hidnplayr 8
;;                                                                 ;;
1529 hidnplayr 9
;;       Based on code by mike.dld                                 ;;
1159 hidnplayr 10
;;                                                                 ;;
1529 hidnplayr 11
;;         GNU GENERAL PUBLIC LICENSE                              ;;
12
;;          Version 2, June 1991                                   ;;
13
;;                                                                 ;;
1159 hidnplayr 14
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
15
 
1206 hidnplayr 16
$Revision: 2404 $
1159 hidnplayr 17
 
1773 hidnplayr 18
 
2402 hidnplayr 19
struct  SOCKET
1249 hidnplayr 20
 
2402 hidnplayr 21
        NextPtr                 dd ? ; pointer to next socket in list
22
        PrevPtr                 dd ? ; pointer to previous socket in list
23
        Number                  dd ? ; socket number
1249 hidnplayr 24
 
2402 hidnplayr 25
        mutex                   MUTEX
1249 hidnplayr 26
 
2402 hidnplayr 27
        PID                     dd ? ; application process id
28
        Domain                  dd ? ; INET/UNIX/..
29
        Type                    dd ? ; RAW/STREAM/DGRAP
30
        Protocol                dd ? ; ICMP/IPv4/ARP/TCP/UDP
31
        errorcode               dd ?
1249 hidnplayr 32
 
2402 hidnplayr 33
        options                 dd ?
34
        state                   dd ?
35
        backlog                 dw ? ; how many incomming connections that can be queued
1249 hidnplayr 36
 
2402 hidnplayr 37
        snd_proc                dd ?
38
        rcv_proc                dd ?
1536 hidnplayr 39
 
2305 hidnplayr 40
ends
1249 hidnplayr 41
 
2402 hidnplayr 42
struct  IP_SOCKET               SOCKET
1254 hidnplayr 43
 
2402 hidnplayr 44
        LocalIP                 rd 4
45
        RemoteIP                rd 4
1318 hidnplayr 46
 
2305 hidnplayr 47
ends
1159 hidnplayr 48
 
2402 hidnplayr 49
struct  TCP_SOCKET              IP_SOCKET
1249 hidnplayr 50
 
2402 hidnplayr 51
        LocalPort               dw ?
52
        RemotePort              dw ?
1514 hidnplayr 53
 
2402 hidnplayr 54
        t_state                 dd ? ; TCB state
55
        t_rxtshift              dd ?
56
        t_rxtcur                dd ?
57
        t_dupacks               dd ?
58
        t_maxseg                dd ?
59
        t_force                 dd ?
60
        t_flags                 dd ?
1514 hidnplayr 61
 
62
;---------------
63
; RFC783 page 21
64
 
65
; send sequence
2402 hidnplayr 66
        SND_UNA                 dd ? ; sequence number of unack'ed sent Packets
67
        SND_NXT                 dd ? ; next send sequence number to use
68
        SND_UP                  dd ?
69
        SND_WL1                 dd ? ; window minus one
70
        SND_WL2                 dd ? ;
71
        ISS                     dd ? ; initial send sequence number
72
        SND_WND                 dd ? ; send window
1514 hidnplayr 73
 
74
; receive sequence
2402 hidnplayr 75
        RCV_WND                 dw ? ; receive window
76
        RCV_NXT                 dd ? ; next receive sequence number to use
77
        RCV_UP                  dd ?
78
        IRS                     dd ? ; initial receive sequence number
1514 hidnplayr 79
 
80
;---------------------
81
; Additional variables
82
 
83
; receive variables
2402 hidnplayr 84
        RCV_ADV                 dd ?
1514 hidnplayr 85
 
86
; retransmit variables
2402 hidnplayr 87
        SND_MAX                 dd ?
1514 hidnplayr 88
 
89
; congestion control
2402 hidnplayr 90
        SND_CWND                dd ?
91
        SND_SSTHRESH            dd ?
1514 hidnplayr 92
 
93
;----------------------
94
; Transmit timing stuff
2402 hidnplayr 95
        t_idle                  dd ?
96
        t_rtt                   dd ?
97
        t_rtseq                 dd ?
98
        t_srtt                  dd ?
99
        t_rttvar                dd ?
100
        t_rttmin                dd ?
101
        max_sndwnd              dd ?
1514 hidnplayr 102
 
103
;-----------------
104
; Out-of-band data
2402 hidnplayr 105
        t_oobflags              dd ?
106
        t_iobc                  dd ?
107
        t_softerror             dd ?
1514 hidnplayr 108
 
109
 
110
;---------
2310 hidnplayr 111
; RFC 1323                           ; the order of next 4 elements may not change
1514 hidnplayr 112
 
2402 hidnplayr 113
        SND_SCALE               db ?
114
        RCV_SCALE               db ?
115
        requested_s_scale       db ?
116
        request_r_scale         db ?
1514 hidnplayr 117
 
2402 hidnplayr 118
        ts_recent               dd ?
119
        ts_recent_age           dd ?
120
        last_ack_sent           dd ?
1519 hidnplayr 121
 
2310 hidnplayr 122
 
1519 hidnplayr 123
;-------
124
; Timers
2402 hidnplayr 125
        timer_retransmission    dw ? ; rexmt
126
        timer_persist           dw ?
127
        timer_keepalive         dw ? ; keepalive/syn timeout
128
        timer_timed_wait        dw ? ; also used as 2msl timer
1519 hidnplayr 129
 
2305 hidnplayr 130
ends
1249 hidnplayr 131
 
2402 hidnplayr 132
struct  UDP_SOCKET              IP_SOCKET
1249 hidnplayr 133
 
2402 hidnplayr 134
        LocalPort               dw ?
135
        RemotePort              dw ?
136
        firstpacket             db ?
1249 hidnplayr 137
 
2305 hidnplayr 138
ends
1249 hidnplayr 139
 
140
 
2402 hidnplayr 141
struct  ICMP_SOCKET             IP_SOCKET
1249 hidnplayr 142
 
2402 hidnplayr 143
        Identifier              dw ?
1514 hidnplayr 144
 
2305 hidnplayr 145
ends
1514 hidnplayr 146
 
147
 
2402 hidnplayr 148
struct  RING_BUFFER
2311 hidnplayr 149
 
2402 hidnplayr 150
        start_ptr               dd ? ; Pointer to start of buffer
151
        end_ptr                 dd ? ; pointer to end of buffer
152
        read_ptr                dd ? ; Read pointer
153
        write_ptr               dd ? ; Write pointer
154
        size                    dd ? ; Number of bytes buffered
2311 hidnplayr 155
 
2305 hidnplayr 156
ends
1514 hidnplayr 157
 
2402 hidnplayr 158
struct  STREAM_SOCKET           TCP_SOCKET
1529 hidnplayr 159
 
2402 hidnplayr 160
        rcv                     RING_BUFFER
161
        snd                     RING_BUFFER
1529 hidnplayr 162
 
2305 hidnplayr 163
ends
1529 hidnplayr 164
 
2402 hidnplayr 165
struct  socket_queue_entry
1529 hidnplayr 166
 
2402 hidnplayr 167
        data_ptr                dd ?
168
        buf_ptr                 dd ?
169
        data_size               dd ?
1529 hidnplayr 170
 
1274 hidnplayr 171
ends
172
 
1514 hidnplayr 173
 
2402 hidnplayr 174
SOCKETBUFFSIZE          equ 4096     ; in bytes
1514 hidnplayr 175
 
2402 hidnplayr 176
SOCKET_QUEUE_SIZE       equ 10       ; maximum number ofincoming packets queued for 1 socket
1514 hidnplayr 177
; the incoming packet queue for sockets is placed in the socket struct itself, at this location from start
2402 hidnplayr 178
SOCKET_QUEUE_LOCATION   equ (SOCKETBUFFSIZE - SOCKET_QUEUE_SIZE*sizeof.socket_queue_entry - sizeof.queue)
1249 hidnplayr 179
 
1159 hidnplayr 180
uglobal
2402 hidnplayr 181
        net_sockets     rd 4
182
        last_socket_num dd ?
183
        last_UDP_port   dw ? ; These values give the number of the last used ephemeral port
184
        last_TCP_port   dw ? ;
1159 hidnplayr 185
endg
186
 
187
 
1257 hidnplayr 188
;-----------------------------------------------------------------
1159 hidnplayr 189
;
190
; SOCKET_init
191
;
1257 hidnplayr 192
;-----------------------------------------------------------------
2402 hidnplayr 193
macro   SOCKET_init {
1159 hidnplayr 194
 
2402 hidnplayr 195
        xor     eax, eax
196
        mov     edi, net_sockets
197
        mov     ecx, 5
198
        rep     stosd
1159 hidnplayr 199
 
1529 hidnplayr 200
       @@:
2402 hidnplayr 201
        pseudo_random eax
202
        cmp     ax, MIN_EPHEMERAL_PORT
203
        jb      @r
204
        cmp     ax, MAX_EPHEMERAL_PORT
205
        ja      @r
206
        mov     [last_UDP_port], ax
1529 hidnplayr 207
 
208
       @@:
2402 hidnplayr 209
        pseudo_random eax
210
        cmp     ax, MIN_EPHEMERAL_PORT
211
        jb      @r
212
        cmp     ax, MAX_EPHEMERAL_PORT
213
        ja      @r
214
        mov     [last_TCP_port], ax
1529 hidnplayr 215
 
216
}
217
 
218
 
1257 hidnplayr 219
;-----------------------------------------------------------------
1159 hidnplayr 220
;
221
; Socket API (function 74)
222
;
1257 hidnplayr 223
;-----------------------------------------------------------------
2301 hidnplayr 224
align 16
225
sock_sysfn_table:
2402 hidnplayr 226
        dd      SOCKET_open     ; 0
227
        dd      SOCKET_close    ; 1
228
        dd      SOCKET_bind     ; 2
229
        dd      SOCKET_listen   ; 3
230
        dd      SOCKET_connect  ; 4
231
        dd      SOCKET_accept   ; 5
232
        dd      SOCKET_send     ; 6
233
        dd      SOCKET_receive  ; 7
234
        dd      SOCKET_set_opt  ; 8
235
        dd      SOCKET_get_opt  ; 9
2301 hidnplayr 236
 
237
SOCKET_SYSFUNCS = ($ - sock_sysfn_table)/4
238
 
239
 
1159 hidnplayr 240
align 4
241
sys_socket:
2402 hidnplayr 242
        cmp     ebx, SOCKET_SYSFUNCS-1
243
        ja      @f
244
        jmp     dword [sock_sysfn_table + 4*ebx]
1529 hidnplayr 245
       @@:
2402 hidnplayr 246
        cmp     ebx, 255
247
        jz      SOCKET_debug
1159 hidnplayr 248
 
1529 hidnplayr 249
s_error:
2402 hidnplayr 250
        DEBUGF  1,"socket error\n"
251
        mov     dword [esp+32], -1
1529 hidnplayr 252
 
2402 hidnplayr 253
        ret
1529 hidnplayr 254
 
1159 hidnplayr 255
 
2301 hidnplayr 256
 
1257 hidnplayr 257
;-----------------------------------------------------------------
1159 hidnplayr 258
;
259
; SOCKET_open
260
;
261
;  IN:  domain in ecx
262
;       type in edx
1196 hidnplayr 263
;       protocol in esi
1159 hidnplayr 264
;  OUT: eax is socket num, -1 on error
265
;
1257 hidnplayr 266
;-----------------------------------------------------------------
1206 hidnplayr 267
align 4
1514 hidnplayr 268
SOCKET_open:
1159 hidnplayr 269
 
2402 hidnplayr 270
        DEBUGF  1,"SOCKET_open: domain: %u, type: %u protocol: %x\n", ecx, edx, esi
1159 hidnplayr 271
 
2402 hidnplayr 272
        push    ecx edx esi
273
        call    SOCKET_alloc
274
        pop     esi edx ecx
275
        jz      s_error
1159 hidnplayr 276
 
2402 hidnplayr 277
        mov     [esp+32], edi                   ; return socketnumber
1542 hidnplayr 278
 
2402 hidnplayr 279
        mov     [eax + SOCKET.Domain], ecx
280
        mov     [eax + SOCKET.Type], edx
281
        mov     [eax + SOCKET.Protocol], esi
1159 hidnplayr 282
 
2402 hidnplayr 283
        cmp     ecx, AF_INET4
284
        jne     .no_inet4
1529 hidnplayr 285
 
2402 hidnplayr 286
        cmp     edx, SOCK_DGRAM
287
        je      .udp
1536 hidnplayr 288
 
2402 hidnplayr 289
        cmp     edx, SOCK_STREAM
290
        je      .tcp
1529 hidnplayr 291
 
2402 hidnplayr 292
        cmp     edx, SOCK_RAW
293
        je      .raw
1541 hidnplayr 294
 
1536 hidnplayr 295
  .no_inet4:
2402 hidnplayr 296
        ret
1536 hidnplayr 297
 
1542 hidnplayr 298
align 4
299
  .raw:
2402 hidnplayr 300
        test    esi, esi       ; IP_PROTO_IP
301
        jz      .ip
1529 hidnplayr 302
 
2402 hidnplayr 303
        cmp     esi, IP_PROTO_ICMP
304
        je      .icmp
1529 hidnplayr 305
 
2402 hidnplayr 306
        cmp     esi, IP_PROTO_UDP
307
        je      .udp
1533 hidnplayr 308
 
2402 hidnplayr 309
        cmp     esi, IP_PROTO_TCP
310
        je      .tcp
1536 hidnplayr 311
 
2402 hidnplayr 312
        ret
1159 hidnplayr 313
 
1542 hidnplayr 314
align 4
1536 hidnplayr 315
  .udp:
2402 hidnplayr 316
        mov     [eax + SOCKET.Protocol], IP_PROTO_UDP
317
        mov     [eax + SOCKET.snd_proc], SOCKET_send_udp
318
        mov     [eax + SOCKET.rcv_proc], SOCKET_receive_dgram
319
        ret
1529 hidnplayr 320
 
1542 hidnplayr 321
align 4
322
  .tcp:
2402 hidnplayr 323
        mov     [eax + SOCKET.Protocol], IP_PROTO_TCP
324
        mov     [eax + SOCKET.snd_proc], SOCKET_send_tcp
325
        mov     [eax + SOCKET.rcv_proc], SOCKET_receive_tcp
1838 hidnplayr 326
 
2402 hidnplayr 327
        mov     [eax + TCP_SOCKET.t_maxseg], 1480       ;;;;; FIXME
328
        ret
1529 hidnplayr 329
 
330
 
1543 hidnplayr 331
align 4
332
  .ip:
2402 hidnplayr 333
        mov     [eax + SOCKET.snd_proc], SOCKET_send_ip
334
        mov     [eax + SOCKET.rcv_proc], SOCKET_receive_dgram
335
        ret
1541 hidnplayr 336
 
1542 hidnplayr 337
 
338
align 4
1541 hidnplayr 339
  .icmp:
2402 hidnplayr 340
        mov     [eax + SOCKET.snd_proc], SOCKET_send_icmp
341
        mov     [eax + SOCKET.rcv_proc], SOCKET_receive_dgram
342
        ret
1541 hidnplayr 343
 
344
 
345
 
1257 hidnplayr 346
;-----------------------------------------------------------------
1159 hidnplayr 347
;
348
; SOCKET_bind
349
;
350
;  IN:  socket number in ecx
351
;       pointer to sockaddr struct in edx
352
;       length of that struct in esi
353
;  OUT: 0 on success
354
;
1257 hidnplayr 355
;-----------------------------------------------------------------
1206 hidnplayr 356
align 4
1514 hidnplayr 357
SOCKET_bind:
1159 hidnplayr 358
 
2402 hidnplayr 359
        DEBUGF  1,"socket_bind: socknum: %u sockaddr: %x, length: %u\n", ecx, edx, esi
1159 hidnplayr 360
 
2402 hidnplayr 361
        call    SOCKET_num_to_ptr
362
        jz      s_error
1159 hidnplayr 363
 
2402 hidnplayr 364
        cmp     esi, 2
365
        jb      s_error
1159 hidnplayr 366
 
2402 hidnplayr 367
        cmp     word [edx], AF_INET4
368
        je      .af_inet4
1159 hidnplayr 369
 
2402 hidnplayr 370
        cmp     word [edx], AF_UNIX
371
        je      .af_unix
1249 hidnplayr 372
 
2402 hidnplayr 373
        jmp     s_error
1249 hidnplayr 374
 
375
  .af_unix:
2402 hidnplayr 376
        ; TODO: write code here
1249 hidnplayr 377
 
2402 hidnplayr 378
        mov     dword [esp+32], 0
379
        ret
1249 hidnplayr 380
 
1159 hidnplayr 381
  .af_inet4:
382
 
2402 hidnplayr 383
        DEBUGF  1,"af_inet4\n"
1514 hidnplayr 384
 
2402 hidnplayr 385
        cmp     esi, 6
386
        jb      s_error
1159 hidnplayr 387
 
2402 hidnplayr 388
        pushw   [edx + 2]
389
        pop     [eax + UDP_SOCKET.LocalPort]
1159 hidnplayr 390
 
2402 hidnplayr 391
        pushd   [edx + 4]
392
        pop     [eax + IP_SOCKET.LocalIP]
1159 hidnplayr 393
 
2402 hidnplayr 394
        DEBUGF  1,"local ip: %u.%u.%u.%u\n",\
395
        [eax + IP_SOCKET.LocalIP + 0]:1,[eax + IP_SOCKET.LocalIP + 1]:1,\
396
        [eax + IP_SOCKET.LocalIP + 2]:1,[eax + IP_SOCKET.LocalIP + 3]:1
1159 hidnplayr 397
 
2402 hidnplayr 398
        mov     dword [esp+32], 0
399
        ret
1159 hidnplayr 400
 
401
 
402
 
403
 
1257 hidnplayr 404
;-----------------------------------------------------------------
1159 hidnplayr 405
;
406
; SOCKET_connect
407
;
408
;  IN:  socket number in ecx
409
;       pointer to sockaddr struct in edx
410
;       length of that struct in esi
411
;  OUT: 0 on success
412
;
1257 hidnplayr 413
;-----------------------------------------------------------------
1159 hidnplayr 414
align 4
1514 hidnplayr 415
SOCKET_connect:
1159 hidnplayr 416
 
2402 hidnplayr 417
        DEBUGF  1,"SOCKET_connect: socknum: %u sockaddr: %x, length: %u\n", ecx, edx, esi
1159 hidnplayr 418
 
2402 hidnplayr 419
        call    SOCKET_num_to_ptr
420
        jz      s_error
1159 hidnplayr 421
 
2402 hidnplayr 422
        cmp     esi, 8
423
        jb      s_error
1159 hidnplayr 424
 
2402 hidnplayr 425
        cmp     word [edx], AF_INET4
426
        je      .af_inet4
1159 hidnplayr 427
 
2402 hidnplayr 428
        jmp     s_error
1159 hidnplayr 429
 
430
  .af_inet4:
2402 hidnplayr 431
        cmp     [eax + IP_SOCKET.LocalIP], 0
432
        jne     @f
433
        push    [IP_LIST]
434
        pop     [eax + IP_SOCKET.LocalIP]
1543 hidnplayr 435
       @@:
1159 hidnplayr 436
 
2402 hidnplayr 437
        cmp     [eax + SOCKET.Protocol], IP_PROTO_UDP
438
        je      .udp
1159 hidnplayr 439
 
2402 hidnplayr 440
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
441
        je      .tcp
1159 hidnplayr 442
 
2402 hidnplayr 443
        cmp     [eax + SOCKET.Protocol], IP_PROTO_IP
444
        je      .ip
1541 hidnplayr 445
 
2402 hidnplayr 446
        cmp     [eax + SOCKET.Protocol], IP_PROTO_ICMP
447
        je      .ip
1542 hidnplayr 448
 
2402 hidnplayr 449
        jmp     s_error
1159 hidnplayr 450
 
1542 hidnplayr 451
align 4
1254 hidnplayr 452
  .udp:
2402 hidnplayr 453
        pusha
454
        lea     ecx, [eax + SOCKET.mutex]
455
        call    mutex_lock
456
        popa
1543 hidnplayr 457
 
2402 hidnplayr 458
        pushw   [edx + 2]
459
        pop     [eax + UDP_SOCKET.RemotePort]
1543 hidnplayr 460
 
2402 hidnplayr 461
        pushd   [edx + 4]
462
        pop     [eax + IP_SOCKET.RemoteIP]
1543 hidnplayr 463
 
2402 hidnplayr 464
        cmp     [eax + UDP_SOCKET.LocalPort], 0
465
        jne     @f
466
        call    SOCKET_find_port
1543 hidnplayr 467
       @@:
468
 
2402 hidnplayr 469
        mov     [eax + UDP_SOCKET.firstpacket], 0
1159 hidnplayr 470
 
2402 hidnplayr 471
        push    eax
472
        init_queue (eax + SOCKET_QUEUE_LOCATION)        ; Set up data receiving queue
473
        pop     eax
1159 hidnplayr 474
 
2402 hidnplayr 475
        lea     ecx, [eax + SOCKET.mutex]
476
        call    mutex_unlock
1159 hidnplayr 477
 
2402 hidnplayr 478
        mov     dword [esp+32], 0
479
        ret
480
 
1542 hidnplayr 481
align 4
1254 hidnplayr 482
  .tcp:
2402 hidnplayr 483
        pusha
484
        lea     ecx, [eax + SOCKET.mutex]
485
        call    mutex_lock
486
        popa
1159 hidnplayr 487
 
2402 hidnplayr 488
        pushw   [edx + 2]
489
        pop     [eax + TCP_SOCKET.RemotePort]
1159 hidnplayr 490
 
2402 hidnplayr 491
        pushd   [edx + 4]
492
        pop     [eax + IP_SOCKET.RemoteIP]
1159 hidnplayr 493
 
2402 hidnplayr 494
        cmp     [eax + TCP_SOCKET.LocalPort], 0
495
        jne     @f
496
        call    SOCKET_find_port
1543 hidnplayr 497
       @@:
1159 hidnplayr 498
 
2402 hidnplayr 499
        mov     [eax + TCP_SOCKET.timer_persist], 0
500
        mov     [eax + TCP_SOCKET.t_state], TCPS_SYN_SENT
501
        push    [TCP_sequence_num]
502
        add     [TCP_sequence_num], 6400
503
        pop     [eax + TCP_SOCKET.ISS]
504
        mov     [eax + TCP_SOCKET.timer_keepalive], TCP_time_keep_init
1519 hidnplayr 505
 
2402 hidnplayr 506
        TCP_sendseqinit eax
1529 hidnplayr 507
 
1543 hidnplayr 508
;        mov     [ebx + TCP_SOCKET.timer_retransmission],   ;; todo: create macro to set retransmission timer
1533 hidnplayr 509
 
2402 hidnplayr 510
        mov     ebx, eax
1159 hidnplayr 511
 
2402 hidnplayr 512
        lea     eax, [ebx + STREAM_SOCKET.snd]
513
        call    SOCKET_ring_create
1543 hidnplayr 514
 
2402 hidnplayr 515
        lea     eax, [ebx + STREAM_SOCKET.rcv]
516
        call    SOCKET_ring_create
1543 hidnplayr 517
 
2402 hidnplayr 518
        pusha
2403 hidnplayr 519
        lea     ecx, [eax + SOCKET.mutex]
2402 hidnplayr 520
        call    mutex_unlock
521
        popa
1733 hidnplayr 522
 
2402 hidnplayr 523
        mov     eax, ebx
524
        call    TCP_output
1733 hidnplayr 525
 
2402 hidnplayr 526
        mov     dword [esp+32], 0
527
        ret
1159 hidnplayr 528
 
1542 hidnplayr 529
align 4
530
  .ip:
2402 hidnplayr 531
        pusha
532
        lea     ecx, [eax + SOCKET.mutex]
533
        call    mutex_lock
534
        popa
1543 hidnplayr 535
 
2402 hidnplayr 536
        pushd   [edx + 4]
537
        pop     [eax + IP_SOCKET.RemoteIP]
1159 hidnplayr 538
 
2402 hidnplayr 539
        push    eax
540
        init_queue (eax + SOCKET_QUEUE_LOCATION)        ; Set up data receiving queue
541
        pop     eax
1543 hidnplayr 542
 
2402 hidnplayr 543
        lea     ecx, [eax + SOCKET.mutex]
544
        call    mutex_unlock
1541 hidnplayr 545
 
2402 hidnplayr 546
        mov     dword [esp+32], 0
547
        ret
1541 hidnplayr 548
 
2402 hidnplayr 549
 
1257 hidnplayr 550
;-----------------------------------------------------------------
1159 hidnplayr 551
;
552
; SOCKET_listen
553
;
554
;  IN:  socket number in ecx
555
;       backlog in edx
556
;  OUT: eax is socket num, -1 on error
557
;
1257 hidnplayr 558
;-----------------------------------------------------------------
1206 hidnplayr 559
align 4
1514 hidnplayr 560
SOCKET_listen:
1159 hidnplayr 561
 
2402 hidnplayr 562
        DEBUGF  1,"SOCKET_listen: socknum: %u backlog: %u\n", ecx, edx
1159 hidnplayr 563
 
2402 hidnplayr 564
        call    SOCKET_num_to_ptr
565
        jz      s_error
1159 hidnplayr 566
 
2402 hidnplayr 567
        cmp     [eax + SOCKET.Domain], AF_INET4
568
        jne     s_error
1254 hidnplayr 569
 
2402 hidnplayr 570
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
571
        jne     s_error
1254 hidnplayr 572
 
2402 hidnplayr 573
        cmp     [eax + TCP_SOCKET.LocalPort], 0
574
        je      s_error
1514 hidnplayr 575
 
2402 hidnplayr 576
        cmp     [eax + IP_SOCKET.LocalIP], 0
577
        jne     @f
578
        push    [IP_LIST]
579
        pop     [eax + IP_SOCKET.LocalIP]
1543 hidnplayr 580
       @@:
581
 
2402 hidnplayr 582
        cmp     edx, MAX_backlog
583
        jbe     @f
584
        mov     edx, MAX_backlog
1543 hidnplayr 585
       @@:
1159 hidnplayr 586
 
2402 hidnplayr 587
        mov     [eax + SOCKET.backlog], dx
588
        or      [eax + SOCKET.options], SO_ACCEPTCON
589
        mov     [eax + TCP_SOCKET.t_state], TCPS_LISTEN
1159 hidnplayr 590
 
2402 hidnplayr 591
        push    eax
592
        init_queue (eax + SOCKET_QUEUE_LOCATION)                ; Set up sockets queue
593
        pop     eax
1543 hidnplayr 594
 
2402 hidnplayr 595
        mov     dword [esp+32], 0
1514 hidnplayr 596
 
2402 hidnplayr 597
        ret
1159 hidnplayr 598
 
599
 
1257 hidnplayr 600
;-----------------------------------------------------------------
1159 hidnplayr 601
;
602
; SOCKET_accept
603
;
604
;  IN:  socket number in ecx
605
;       addr in edx
606
;       addrlen in esi
607
;  OUT: eax is socket num, -1 on error
608
;
1257 hidnplayr 609
;-----------------------------------------------------------------
1206 hidnplayr 610
align 4
1514 hidnplayr 611
SOCKET_accept:
1159 hidnplayr 612
 
2402 hidnplayr 613
        DEBUGF  1,"SOCKET_accept: socknum: %u sockaddr: %x, length: %u\n", ecx, edx, esi
1159 hidnplayr 614
 
2402 hidnplayr 615
        call    SOCKET_num_to_ptr
616
        jz      s_error
1159 hidnplayr 617
 
2402 hidnplayr 618
        test    [eax + SOCKET.options], SO_ACCEPTCON
619
        jz      s_error
1543 hidnplayr 620
 
2402 hidnplayr 621
        cmp     [eax + SOCKET.Domain], AF_INET4
622
        jne     s_error
1249 hidnplayr 623
 
2402 hidnplayr 624
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
625
        jne     s_error
1249 hidnplayr 626
 
2402 hidnplayr 627
        get_from_queue (eax + SOCKET_QUEUE_LOCATION), MAX_backlog, 4, s_error
1249 hidnplayr 628
 
2402 hidnplayr 629
        mov     eax, [esi]
630
        call    SOCKET_ptr_to_num
631
        jz      s_error
632
        mov     [esp+32], eax
633
        ret
1514 hidnplayr 634
 
1159 hidnplayr 635
 
1257 hidnplayr 636
;-----------------------------------------------------------------
1159 hidnplayr 637
;
638
; SOCKET_close
639
;
640
;  IN:  socket number in ecx
641
;  OUT: eax is socket num, -1 on error
642
;
1257 hidnplayr 643
;-----------------------------------------------------------------
1206 hidnplayr 644
align 4
1514 hidnplayr 645
SOCKET_close:
1159 hidnplayr 646
 
2402 hidnplayr 647
        DEBUGF  1,"SOCKET_close: socknum: %u\n", ecx
1159 hidnplayr 648
 
2402 hidnplayr 649
        call    SOCKET_num_to_ptr
650
        jz      s_error
1159 hidnplayr 651
 
2402 hidnplayr 652
        cmp     [eax + SOCKET.Domain], AF_INET4
653
        jne     s_error
1159 hidnplayr 654
 
2402 hidnplayr 655
        cmp     [eax + SOCKET.Protocol], IP_PROTO_UDP
656
        je      .free
1159 hidnplayr 657
 
2402 hidnplayr 658
        cmp     [eax + SOCKET.Protocol], IP_PROTO_ICMP
659
        je      .free
1159 hidnplayr 660
 
2402 hidnplayr 661
        cmp     [eax + SOCKET.Protocol], IP_PROTO_IP
662
        je      .free
1542 hidnplayr 663
 
2402 hidnplayr 664
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
665
        je      .tcp
1159 hidnplayr 666
 
2402 hidnplayr 667
        jmp     s_error
1159 hidnplayr 668
 
669
  .tcp:
2402 hidnplayr 670
        cmp     [eax + TCP_SOCKET.t_state], TCPS_SYN_RECEIVED    ; state must be LISTEN, SYN_SENT or CLOSED
671
        jb      .free
1318 hidnplayr 672
 
2402 hidnplayr 673
        call    TCP_output
674
        mov     dword [esp+32], 0
1159 hidnplayr 675
 
2402 hidnplayr 676
        ret
1159 hidnplayr 677
 
1514 hidnplayr 678
  .free:
2402 hidnplayr 679
        call    SOCKET_free
680
        mov     dword [esp+32], 0
1159 hidnplayr 681
 
2402 hidnplayr 682
        ret
1159 hidnplayr 683
 
684
 
1257 hidnplayr 685
;-----------------------------------------------------------------
1159 hidnplayr 686
;
687
; SOCKET_receive
688
;
689
;  IN:  socket number in ecx
1249 hidnplayr 690
;       addr to buffer in edx
691
;       length of buffer in esi
1159 hidnplayr 692
;       flags in edi
693
;  OUT: eax is number of bytes copied, -1 on error
694
;
1257 hidnplayr 695
;-----------------------------------------------------------------
1206 hidnplayr 696
align 4
1514 hidnplayr 697
SOCKET_receive:
1159 hidnplayr 698
 
2402 hidnplayr 699
        DEBUGF  1,"SOCKET_receive: socknum: %u bufaddr: %x, buflength: %u, flags: %x, ", ecx, edx, esi, edi
1514 hidnplayr 700
 
2402 hidnplayr 701
        call    SOCKET_num_to_ptr
702
        jz      s_error
1159 hidnplayr 703
 
2402 hidnplayr 704
        jmp     [eax + SOCKET.rcv_proc]
1533 hidnplayr 705
 
1536 hidnplayr 706
 
707
align 4
1541 hidnplayr 708
SOCKET_receive_dgram:
1536 hidnplayr 709
 
2402 hidnplayr 710
        DEBUGF  1,"SOCKET_receive: DGRAM\n"
1536 hidnplayr 711
 
2402 hidnplayr 712
        mov     ebx, esi
713
        mov     edi, edx                                        ; addr to buffer
1159 hidnplayr 714
 
2402 hidnplayr 715
        get_from_queue (eax + SOCKET_QUEUE_LOCATION), SOCKET_QUEUE_SIZE, sizeof.socket_queue_entry, s_error       ; destroys esi and ecx
1536 hidnplayr 716
 
2402 hidnplayr 717
        mov     ecx, [esi + socket_queue_entry.data_size]
718
        DEBUGF  1,"Got %u bytes of data\n", ecx
1159 hidnplayr 719
 
2402 hidnplayr 720
        cmp     ecx, ebx
721
        ja      .too_small
1514 hidnplayr 722
 
2402 hidnplayr 723
        push    [esi + socket_queue_entry.buf_ptr]              ; save the buffer addr so we can clear it later
724
        mov     esi, [esi + socket_queue_entry.data_ptr]
725
        DEBUGF  1,"Source buffer: %x, real addr: %x\n", [esp], esi
726
        mov     [esp+32+4], ecx                                 ; return number of bytes copied
1159 hidnplayr 727
 
1514 hidnplayr 728
; copy the data
2402 hidnplayr 729
        shr     ecx, 1
730
        jnc     .nb
731
        movsb
1536 hidnplayr 732
  .nb:
2402 hidnplayr 733
        shr     ecx, 1
734
        jnc     .nw
735
        movsw
1536 hidnplayr 736
  .nw:
2402 hidnplayr 737
        test    ecx, ecx
738
        jz      .nd
739
        rep     movsd
1536 hidnplayr 740
  .nd:
1159 hidnplayr 741
 
2402 hidnplayr 742
        call    kernel_free                                     ; remove the packet
743
        ret
1514 hidnplayr 744
 
1536 hidnplayr 745
  .too_small:
1533 hidnplayr 746
 
2402 hidnplayr 747
        DEBUGF  1,"Buffer too small...\n"
748
        jmp     s_error
1536 hidnplayr 749
 
750
align 4
751
SOCKET_receive_tcp:
752
 
2402 hidnplayr 753
        DEBUGF  1,"SOCKET_receive: TCP\n"
1536 hidnplayr 754
 
2402 hidnplayr 755
        mov     ecx, esi
756
        mov     edi, edx
757
        add     eax, STREAM_SOCKET.rcv
758
        call    SOCKET_ring_read
759
        call    SOCKET_ring_free
1533 hidnplayr 760
 
2402 hidnplayr 761
        mov     [esp+32], ecx                                   ; return number of bytes copied
1533 hidnplayr 762
 
2402 hidnplayr 763
        ret
1159 hidnplayr 764
 
765
 
1257 hidnplayr 766
;-----------------------------------------------------------------
1159 hidnplayr 767
;
768
; SOCKET_send
769
;
770
;
771
;  IN:  socket number in ecx
1206 hidnplayr 772
;       pointer to data in edx
773
;       datalength in esi
1159 hidnplayr 774
;       flags in edi
775
;  OUT: -1 on error
776
;
1257 hidnplayr 777
;-----------------------------------------------------------------
1206 hidnplayr 778
align 4
1514 hidnplayr 779
SOCKET_send:
1159 hidnplayr 780
 
2402 hidnplayr 781
        DEBUGF  1,"SOCKET_send: socknum: %u data ptr: %x, length: %u, flags: %x, ", ecx, edx, esi, edi
1159 hidnplayr 782
 
2402 hidnplayr 783
        call    SOCKET_num_to_ptr
784
        jz      s_error
1159 hidnplayr 785
 
2402 hidnplayr 786
        mov     ecx, esi
787
        mov     esi, edx
1763 hidnplayr 788
 
2402 hidnplayr 789
        jmp     [eax + SOCKET.snd_proc]
1206 hidnplayr 790
 
791
 
1536 hidnplayr 792
align 4
793
SOCKET_send_udp:
1529 hidnplayr 794
 
2402 hidnplayr 795
        DEBUGF  1,"SOCKET_send: UDP\n"
1159 hidnplayr 796
 
2402 hidnplayr 797
        call    UDP_output
1159 hidnplayr 798
 
2402 hidnplayr 799
        mov     [esp+32], eax
800
        ret
1159 hidnplayr 801
 
802
 
1536 hidnplayr 803
align 4
804
SOCKET_send_tcp:
1254 hidnplayr 805
 
2402 hidnplayr 806
        DEBUGF  1,"SOCKET_send: TCP\n"
1254 hidnplayr 807
 
2402 hidnplayr 808
        push    eax
809
        add     eax, STREAM_SOCKET.snd
810
        call    SOCKET_ring_write
811
        pop     eax
1536 hidnplayr 812
 
2402 hidnplayr 813
        call    TCP_output
1254 hidnplayr 814
 
2402 hidnplayr 815
        mov     [esp+32], eax
816
        ret
1159 hidnplayr 817
 
1249 hidnplayr 818
 
1543 hidnplayr 819
align 4
820
SOCKET_send_ip:
1249 hidnplayr 821
 
2402 hidnplayr 822
        DEBUGF  1,"type: IP\n"
1543 hidnplayr 823
 
2402 hidnplayr 824
        call    IPv4_output_raw
1543 hidnplayr 825
 
2402 hidnplayr 826
        mov     [esp+32], eax
827
        ret
1543 hidnplayr 828
 
1541 hidnplayr 829
align 4
830
SOCKET_send_icmp:
1249 hidnplayr 831
 
2402 hidnplayr 832
        DEBUGF  1,"SOCKET_send: ICMP\n"
1541 hidnplayr 833
 
2402 hidnplayr 834
        call    ICMP_output_raw
1541 hidnplayr 835
 
2402 hidnplayr 836
        mov     [esp+32], eax
837
        ret
1541 hidnplayr 838
 
839
 
840
 
841
 
1257 hidnplayr 842
;-----------------------------------------------------------------
1256 clevermous 843
;
1257 hidnplayr 844
; SOCKET_get_options
1256 clevermous 845
;
1514 hidnplayr 846
;  IN:  ecx = socket number
847
;       edx = pointer to the options:
1257 hidnplayr 848
;               dd      level, optname, optval, optlen
1256 clevermous 849
;  OUT: -1 on error
850
;
851
; At moment, uses only pseudo-optname -2 for get last_ack_number for TCP.
852
; TODO: find best way to notify that send()'ed data were acknowledged
1831 hidnplayr 853
; Also pseudo-optname -3 is valid and returns socket state, one of TCPS_*.
1256 clevermous 854
;
1257 hidnplayr 855
;-----------------------------------------------------------------
856
align 4
1514 hidnplayr 857
SOCKET_get_opt:
1257 hidnplayr 858
 
2402 hidnplayr 859
        DEBUGF  1,"SOCKET_get_opt\n"
1514 hidnplayr 860
 
2402 hidnplayr 861
        call    SOCKET_num_to_ptr
862
        jz      s_error
1514 hidnplayr 863
 
2402 hidnplayr 864
        cmp     dword [edx], IP_PROTO_TCP
865
        jne     s_error
866
        cmp     dword [edx+4], -2
867
        je      @f
868
        cmp     dword [edx+4], -3
869
        jne     s_error
1299 clevermous 870
@@:
1514 hidnplayr 871
;        mov     eax, [edx+12]
872
;        test    eax, eax
873
;        jz      .fail
874
;        cmp     dword [eax], 4
875
;        mov     dword [eax], 4
876
;        jb      .fail
877
;        stdcall net_socket_num_to_addr, ecx
878
;        test    eax, eax
879
;        jz      .fail
880
;        ; todo: check that eax is really TCP socket
881
;        mov     ecx, [eax + TCP_SOCKET.last_ack_number]
882
;        cmp     dword [edx+4], -2
883
;        jz      @f
884
;        mov     ecx, [eax + TCP_SOCKET.state]
1299 clevermous 885
@@:
2402 hidnplayr 886
        mov     eax, [edx+8]
887
        test    eax, eax
888
        jz      @f
889
        mov     [eax], ecx
1256 clevermous 890
@@:
2402 hidnplayr 891
        mov     dword [esp+32], 0
892
        ret
1159 hidnplayr 893
 
894
 
1529 hidnplayr 895
 
1542 hidnplayr 896
 
897
align 4
898
SOCKET_set_opt:
899
 
2402 hidnplayr 900
        ret
1542 hidnplayr 901
 
902
 
903
 
1257 hidnplayr 904
;-----------------------------------------------------------------
1206 hidnplayr 905
;
1529 hidnplayr 906
; SOCKET_debug
907
;
908
;  Copies socket variables to application buffer
909
;
910
;  IN:  ecx = socket number
911
;       edx = pointer to buffer
912
;
913
;  OUT: -1 on error
914
;-----------------------------------------------------------------
915
align 4
916
SOCKET_debug:
917
 
2402 hidnplayr 918
        DEBUGF  1,"socket_debug\n"
1529 hidnplayr 919
 
2402 hidnplayr 920
        call    SOCKET_num_to_ptr
921
        jz      s_error
1529 hidnplayr 922
 
2402 hidnplayr 923
        mov     esi, eax
924
        mov     edi, edx
925
        mov     ecx, SOCKETBUFFSIZE/4
926
        rep     movsd
1529 hidnplayr 927
 
2402 hidnplayr 928
        mov     dword [esp+32], 0
929
        ret
1529 hidnplayr 930
 
931
 
932
;-----------------------------------------------------------------
933
;
1514 hidnplayr 934
; SOCKET_find_port
1206 hidnplayr 935
;
1514 hidnplayr 936
; Fills in the local port number for TCP and UDP sockets
937
; This procedure always works because the number of sockets is
938
; limited to a smaller number then the number of possible ports
1206 hidnplayr 939
;
1514 hidnplayr 940
;  IN:  eax = socket pointer
941
;  OUT: /
1206 hidnplayr 942
;
1257 hidnplayr 943
;-----------------------------------------------------------------
1206 hidnplayr 944
align 4
1514 hidnplayr 945
SOCKET_find_port:
1159 hidnplayr 946
 
2402 hidnplayr 947
        DEBUGF  1,"SOCKET_find_port\n"
1159 hidnplayr 948
 
2402 hidnplayr 949
        push    ebx esi ecx
1514 hidnplayr 950
 
2402 hidnplayr 951
        cmp     [eax + SOCKET.Protocol], IP_PROTO_UDP
952
        je      .udp
1159 hidnplayr 953
 
2402 hidnplayr 954
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
955
        je      .tcp
1159 hidnplayr 956
 
2402 hidnplayr 957
        jmp     .error
1514 hidnplayr 958
 
959
  .done:
2402 hidnplayr 960
        mov     [eax + UDP_SOCKET.LocalPort], bx
1514 hidnplayr 961
  .error:
2402 hidnplayr 962
        pop     ecx esi ebx
963
        ret
1514 hidnplayr 964
 
1206 hidnplayr 965
  .udp:
2402 hidnplayr 966
        mov     bx, [last_UDP_port]
967
        call    .findit
968
        mov     [last_UDP_port], bx
969
        jmp     .done
1206 hidnplayr 970
 
971
  .tcp:
2402 hidnplayr 972
        mov     bx, [last_TCP_port]
973
        call    .findit
974
        mov     [last_TCP_port], bx
975
        jmp     .done
1206 hidnplayr 976
 
977
 
1514 hidnplayr 978
  .restart:
2402 hidnplayr 979
        mov     bx, MIN_EPHEMERAL_PORT
1514 hidnplayr 980
  .findit:
2402 hidnplayr 981
        inc     bx
1206 hidnplayr 982
 
2402 hidnplayr 983
        cmp     bx, MAX_EPHEMERAL_PORT
984
        jz      .restart
1206 hidnplayr 985
 
2402 hidnplayr 986
        call    SOCKET_check_port
987
        jz      .findit
1206 hidnplayr 988
 
2402 hidnplayr 989
        ret
1206 hidnplayr 990
 
1257 hidnplayr 991
 
992
 
993
;-----------------------------------------------------------------
1206 hidnplayr 994
;
1542 hidnplayr 995
; SOCKET_check_port (to be used with AF_INET only!)
1206 hidnplayr 996
;
1514 hidnplayr 997
; Checks if a local port number is unused
998
; If the proposed port number is unused, it is filled in in the socket structure
1206 hidnplayr 999
;
1514 hidnplayr 1000
;  IN:  eax = socket ptr (to find out if its a TCP/UDP socket)
1001
;        bx = proposed socket number
1206 hidnplayr 1002
;
1514 hidnplayr 1003
;  OUT:  ZF = cleared on error
1004
;
1257 hidnplayr 1005
;-----------------------------------------------------------------
1206 hidnplayr 1006
align 4
1514 hidnplayr 1007
SOCKET_check_port:
1008
 
2402 hidnplayr 1009
        DEBUGF  1,"SOCKET_check_port\n"
1514 hidnplayr 1010
 
2402 hidnplayr 1011
        mov     ecx, [eax + SOCKET.Protocol]
1012
        mov     esi, net_sockets
1206 hidnplayr 1013
 
1014
  .next_socket:
2402 hidnplayr 1015
        mov     esi, [esi + SOCKET.NextPtr]
1016
        or      esi, esi
1017
        jz      .port_ok
1206 hidnplayr 1018
 
2402 hidnplayr 1019
        cmp     [esi + SOCKET.Protocol], ecx
1020
        jne     .next_socket
1206 hidnplayr 1021
 
2402 hidnplayr 1022
        cmp     [esi + UDP_SOCKET.LocalPort], bx
1023
        jne     .next_socket
1206 hidnplayr 1024
 
2402 hidnplayr 1025
        DEBUGF  1,"local port %u already in use\n", bx
1026
        ret
1206 hidnplayr 1027
 
1028
  .port_ok:
2402 hidnplayr 1029
        mov     [eax + UDP_SOCKET.LocalPort], bx
1030
        or      bx, bx                                  ; set the zero-flag
1514 hidnplayr 1031
 
2402 hidnplayr 1032
        ret
1206 hidnplayr 1033
 
1034
 
1257 hidnplayr 1035
 
1036
;-----------------------------------------------------------------
1206 hidnplayr 1037
;
1514 hidnplayr 1038
; SOCKET_input
1206 hidnplayr 1039
;
1536 hidnplayr 1040
; Updates a (stateless) socket with received data
1206 hidnplayr 1041
;
1514 hidnplayr 1042
; Note: the mutex should already be set !
1206 hidnplayr 1043
;
1249 hidnplayr 1044
;  IN:  eax = socket ptr
1514 hidnplayr 1045
;       ebx = pointer to device struct
1046
;       ecx = data size
1047
;       esi = ptr to data
1048
;       [esp] = ptr to buf
1049
;       [esp + 4] = buf size
1249 hidnplayr 1050
;
1514 hidnplayr 1051
;  OUT: /
1206 hidnplayr 1052
;
1257 hidnplayr 1053
;-----------------------------------------------------------------
1206 hidnplayr 1054
align 4
1514 hidnplayr 1055
SOCKET_input:
1206 hidnplayr 1056
 
2402 hidnplayr 1057
        DEBUGF  1,"SOCKET_input: socket=%x, data=%x size=%u\n", eax, esi, ecx
1206 hidnplayr 1058
 
2402 hidnplayr 1059
        mov     [esp+4], ecx
1060
        push    esi
1061
        mov     esi, esp
1514 hidnplayr 1062
 
2402 hidnplayr 1063
        add_to_queue (eax + SOCKET_QUEUE_LOCATION), SOCKET_QUEUE_SIZE, sizeof.socket_queue_entry, SOCKET_input.full
1514 hidnplayr 1064
 
2402 hidnplayr 1065
        DEBUGF  1,"SOCKET_input: queued packet successfully\n"
1066
        add     esp, sizeof.socket_queue_entry
1206 hidnplayr 1067
 
2402 hidnplayr 1068
        pusha
1069
        lea     ecx, [eax + SOCKET.mutex]
1070
        call    mutex_unlock
1071
        popa
1072
 
1073
        jmp     SOCKET_notify_owner
1074
 
1514 hidnplayr 1075
  .full:
2402 hidnplayr 1076
        DEBUGF  2,"SOCKET_input: socket %x is full!\n", eax
1206 hidnplayr 1077
 
2402 hidnplayr 1078
        pusha
1079
        lea     ecx, [eax + SOCKET.mutex]
1080
        call    mutex_unlock
1081
        popa
1514 hidnplayr 1082
 
2402 hidnplayr 1083
        call    kernel_free
1084
        add     esp, 8
1533 hidnplayr 1085
 
2402 hidnplayr 1086
        ret
1087
 
1088
 
1533 hidnplayr 1089
;--------------------------
1090
;
1091
; eax = ptr to ring struct (just a buffer of the right size)
1092
;
1093
align 4
1094
SOCKET_ring_create:
1095
 
2402 hidnplayr 1096
        push    esi
1097
        mov     esi, eax
1543 hidnplayr 1098
 
2402 hidnplayr 1099
        push    edx
1100
        stdcall create_ring_buffer, SOCKET_MAXDATA, PG_SW
1101
        pop     edx
1533 hidnplayr 1102
 
2402 hidnplayr 1103
        DEBUGF  1,"SOCKET_ring_created: %x\n", eax
1104
        mov     [esi + RING_BUFFER.start_ptr], eax
1105
        mov     [esi + RING_BUFFER.write_ptr], eax
1106
        mov     [esi + RING_BUFFER.read_ptr], eax
1107
        mov     [esi + RING_BUFFER.size], 0
1108
        add     eax,  SOCKET_MAXDATA
1109
        mov     [esi + RING_BUFFER.end_ptr], eax
1110
        mov     eax, esi
1111
        pop     esi
1533 hidnplayr 1112
 
2402 hidnplayr 1113
        ret
1533 hidnplayr 1114
 
1514 hidnplayr 1115
;-----------------------------------------------------------------
1116
;
1533 hidnplayr 1117
; SOCKET_ring_write
1529 hidnplayr 1118
;
1533 hidnplayr 1119
; Adds data to a stream socket, and updates write pointer and size
1529 hidnplayr 1120
;
1121
;  IN:  eax = ptr to ring struct
1122
;       ecx = data size
1123
;       esi = ptr to data
1124
;
1533 hidnplayr 1125
;  OUT: ecx = number of bytes stored
1529 hidnplayr 1126
;
1127
;-----------------------------------------------------------------
1128
align 4
1533 hidnplayr 1129
SOCKET_ring_write:
1529 hidnplayr 1130
 
2402 hidnplayr 1131
        DEBUGF  1,"SOCKET_ring_write: ringbuff=%x ptr=%x size=%u\n", eax, esi, ecx
1529 hidnplayr 1132
 
2402 hidnplayr 1133
        add     [eax + RING_BUFFER.size], ecx
1134
        cmp     [eax + RING_BUFFER.size], SOCKET_MAXDATA
1135
        ja      .too_large
1529 hidnplayr 1136
 
1137
  .copy:
2402 hidnplayr 1138
        mov     edi, [eax + RING_BUFFER.write_ptr]
1139
        DEBUGF  2,"SOCKET_ring_write: %u bytes from %x to %x\n", ecx, esi, edi
1529 hidnplayr 1140
 
2402 hidnplayr 1141
        push    ecx
1142
        shr     ecx, 1
1143
        jnc     .nb
1144
        movsb
1536 hidnplayr 1145
  .nb:
2402 hidnplayr 1146
        shr     ecx, 1
1147
        jnc     .nw
1148
        movsw
1536 hidnplayr 1149
  .nw:
2402 hidnplayr 1150
        test    ecx, ecx
1151
        jz      .nd
1152
        rep     movsd
1536 hidnplayr 1153
  .nd:
2402 hidnplayr 1154
        pop     ecx
1529 hidnplayr 1155
 
2402 hidnplayr 1156
        cmp     edi, [eax + RING_BUFFER.end_ptr]
1157
        jae     .wrap
1158
        mov     [eax + RING_BUFFER.write_ptr], edi
1533 hidnplayr 1159
 
2402 hidnplayr 1160
        ret
1529 hidnplayr 1161
 
1533 hidnplayr 1162
  .wrap:
2402 hidnplayr 1163
        sub     edi, SOCKET_MAXDATA
1164
        mov     [eax + RING_BUFFER.write_ptr], edi
1533 hidnplayr 1165
 
2402 hidnplayr 1166
        ret
1533 hidnplayr 1167
 
2404 hidnplayr 1168
  .too_large:                                                           ; update size, we will fill buffer completely
1169
        sub     [eax + RING_BUFFER.size], SOCKET_MAXDATA
2402 hidnplayr 1170
        sub     ecx, [eax + RING_BUFFER.size]
2404 hidnplayr 1171
        mov     [eax + RING_BUFFER.size], SOCKET_MAXDATA
1529 hidnplayr 1172
 
2404 hidnplayr 1173
        test    ecx, ecx
1174
        jnz     .copy
1529 hidnplayr 1175
 
2402 hidnplayr 1176
        DEBUGF  2,"SOCKET_ring_write: ring buffer is full!\n"
1177
        xor     ecx, ecx
1178
        ret
1529 hidnplayr 1179
 
1180
 
1181
;-----------------------------------------------------------------
1182
;
1183
; SOCKET_ring_read
1184
;
1533 hidnplayr 1185
; reads the data, BUT DOES NOT CLEAR IT FROM MEMORY YET
1529 hidnplayr 1186
;
1187
;  IN:  eax = ptr to ring struct
1188
;       ecx = buffer size
1189
;       edi = ptr to buffer
1190
;
1533 hidnplayr 1191
;  OUT: ecx = number of bytes read
1529 hidnplayr 1192
;
1193
;-----------------------------------------------------------------
1194
align 4
1195
SOCKET_ring_read:
1196
 
2402 hidnplayr 1197
        DEBUGF  1,"SOCKET_ring_read: ringbuff=%x ptr=%x size=%u\n", eax, edi, ecx
1529 hidnplayr 1198
 
2402 hidnplayr 1199
        cmp     ecx, [eax + RING_BUFFER.size]
1200
        ja      .less_data
1529 hidnplayr 1201
 
1202
  .copy:
2402 hidnplayr 1203
        mov     esi, [eax + RING_BUFFER.read_ptr]
1529 hidnplayr 1204
 
2402 hidnplayr 1205
        DEBUGF  2,"SOCKET_ring_read: %u bytes from %x to %x\n", ecx, esi, edi
1206
        push    ecx
1207
        shr     ecx, 1
1208
        jnc     .nb
1209
        movsb
1536 hidnplayr 1210
  .nb:
2402 hidnplayr 1211
        shr     ecx, 1
1212
        jnc     .nw
1213
        movsw
1536 hidnplayr 1214
  .nw:
2402 hidnplayr 1215
        test    ecx, ecx
1216
        jz      .nd
1217
        rep     movsd
1536 hidnplayr 1218
  .nd:
2402 hidnplayr 1219
        pop     ecx
1529 hidnplayr 1220
 
1830 hidnplayr 1221
  .no_data_at_all:
2402 hidnplayr 1222
        ret
1529 hidnplayr 1223
 
1533 hidnplayr 1224
  .less_data:
2402 hidnplayr 1225
        mov     ecx, [eax + RING_BUFFER.size]
1830 hidnplayr 1226
;        test    ecx, ecx
1533 hidnplayr 1227
;        jz      .no_data_at_all
2402 hidnplayr 1228
        jmp     .copy
1529 hidnplayr 1229
 
1230
 
1231
;-----------------------------------------------------------------
1232
;
1233
; SOCKET_ring_free
1234
;
1235
; Free's some bytes from the ringbuffer
1236
;
1237
;  IN:  eax = ptr to ring struct
1238
;       ecx = data size
1239
;
1240
;  OUT: ecx = number of bytes free-ed
1241
;
1242
;-----------------------------------------------------------------
1243
align 4
1244
SOCKET_ring_free:
1245
 
2402 hidnplayr 1246
        DEBUGF  1,"SOCKET_ring_free: %u bytes from ring %x\n", ecx, eax
1529 hidnplayr 1247
 
2402 hidnplayr 1248
        sub     [eax + RING_BUFFER.size], ecx
1249
        jb      .sumthinwong
1250
        add     [eax + RING_BUFFER.read_ptr], ecx
1529 hidnplayr 1251
 
2402 hidnplayr 1252
        mov     edx, [eax + RING_BUFFER.end_ptr]
1253
        cmp     [eax + RING_BUFFER.read_ptr], edx
1254
        jb      @f
1255
        sub     [eax + RING_BUFFER.read_ptr], SOCKET_MAXDATA
1529 hidnplayr 1256
       @@:
2402 hidnplayr 1257
        ret
1529 hidnplayr 1258
 
2402 hidnplayr 1259
  .sumthinwong:                ; we could free all available bytes, but that would be stupid, i guess..
1260
        add     [eax + RING_BUFFER.size], ecx
1261
        xor     ecx, ecx
1262
        ret
1529 hidnplayr 1263
 
1264
 
1265
;-----------------------------------------------------------------
1266
;
1514 hidnplayr 1267
; SOCKET_notify_owner
1268
;
1269
; notify's the owner of a socket that something happened
1270
;
1271
;  IN:  eax = socket ptr
1272
;  OUT: /
1273
;
1274
;-----------------------------------------------------------------
1275
align 4
1276
SOCKET_notify_owner:
1277
 
2402 hidnplayr 1278
        DEBUGF  1,"SOCKET_notify_owner: %x\n", eax
1514 hidnplayr 1279
 
2402 hidnplayr 1280
        call    SOCKET_check
1281
        jz      .error
1514 hidnplayr 1282
 
2402 hidnplayr 1283
        push    eax ecx esi
1514 hidnplayr 1284
 
1285
; socket exists, now try to flag an event to the application
1286
 
2402 hidnplayr 1287
        mov     eax, [eax + SOCKET.PID]
1288
        mov     ecx, 1
1289
        mov     esi, TASK_DATA + TASKDATA.pid
1206 hidnplayr 1290
 
1291
       .next_pid:
2402 hidnplayr 1292
        cmp     [esi], eax
1293
        je      .found_pid
1294
        inc     ecx
1295
        add     esi, 0x20
1296
        cmp     ecx, [TASK_COUNT]
1297
        jbe     .next_pid
1206 hidnplayr 1298
 
1514 hidnplayr 1299
; PID not found, TODO: close socket!
1300
 
2402 hidnplayr 1301
        jmp     .error2
1514 hidnplayr 1302
 
1206 hidnplayr 1303
       .found_pid:
2402 hidnplayr 1304
        shl     ecx, 8
1305
        or      [ecx + SLOT_BASE + APPDATA.event_mask], EVENT_NETWORK
1306
        mov     [check_idle_semaphore], 200
1206 hidnplayr 1307
 
2402 hidnplayr 1308
        DEBUGF  1,"SOCKET_notify_owner: succes!\n"
1514 hidnplayr 1309
 
1310
  .error2:
2402 hidnplayr 1311
        pop     esi ecx eax
1536 hidnplayr 1312
 
1514 hidnplayr 1313
  .error:
1314
 
2402 hidnplayr 1315
        ret
1206 hidnplayr 1316
 
1317
 
1514 hidnplayr 1318
;--------------------------------------------------------------------
1319
;
1320
; SOCKET_alloc
1321
;
1159 hidnplayr 1322
; Allocate memory for socket data and put new socket into the list
1323
; Newly created socket is initialized with calling PID and number and
1324
; put into beginning of list (which is a fastest way).
1325
;
1514 hidnplayr 1326
; IN:  /
1327
; OUT: eax = 0 on error, socket ptr otherwise
1328
;      edi = socket number
1329
;       ZF = cleared on error
1159 hidnplayr 1330
;
1514 hidnplayr 1331
;--------------------------------------------------------------------
1332
align 4
1333
SOCKET_alloc:
1334
 
2402 hidnplayr 1335
        push    ebx
1514 hidnplayr 1336
 
2402 hidnplayr 1337
        stdcall kernel_alloc, SOCKETBUFFSIZE
1338
        DEBUGF  1, "SOCKET_alloc: ptr=%x\n", eax
1339
        or      eax, eax
1340
        jz      .exit
1159 hidnplayr 1341
 
1514 hidnplayr 1342
; zero-initialize allocated memory
2402 hidnplayr 1343
        push    eax
1344
        mov     edi, eax
1345
        mov     ecx, SOCKETBUFFSIZE / 4
1346
        xor     eax, eax
1347
        rep     stosd
1348
        pop     eax
1159 hidnplayr 1349
 
1536 hidnplayr 1350
; set send-and receive procedures to return -1
2402 hidnplayr 1351
        mov     [eax + SOCKET.snd_proc], s_error
1352
        mov     [eax + SOCKET.rcv_proc], s_error
1536 hidnplayr 1353
 
1514 hidnplayr 1354
; find first free socket number and use it
2402 hidnplayr 1355
        mov     edi, [last_socket_num]
1159 hidnplayr 1356
  .next_socket_number:
2402 hidnplayr 1357
        inc     edi
1358
        jz      .next_socket_number     ; avoid socket nr 0
1359
        cmp     edi, -1
1360
        je      .next_socket_number     ; avoid socket nr -1
1361
        mov     ebx, net_sockets
1159 hidnplayr 1362
  .next_socket:
2402 hidnplayr 1363
        mov     ebx, [ebx + SOCKET.NextPtr]
1364
        test    ebx, ebx
1365
        jz      .last_socket
1536 hidnplayr 1366
 
2402 hidnplayr 1367
        cmp     [ebx + SOCKET.Number], edi
1368
        jne     .next_socket
1369
        jmp     .next_socket_number
1159 hidnplayr 1370
 
1514 hidnplayr 1371
  .last_socket:
2402 hidnplayr 1372
        mov     [last_socket_num], edi
1373
        mov     [eax + SOCKET.Number], edi
1374
        DEBUGF  1, "SOCKET_alloc: number=%u\n", edi
1159 hidnplayr 1375
 
1514 hidnplayr 1376
; Fill in PID
2402 hidnplayr 1377
        mov     ebx, [TASK_BASE]
1378
        mov     ebx, [ebx + TASKDATA.pid]
1379
        mov     [eax + SOCKET.PID], ebx
1514 hidnplayr 1380
 
2403 hidnplayr 1381
; init mutex
1382
        pusha
1383
        lea     ecx, [eax + SOCKET.mutex]
1384
        call    mutex_init
1385
        popa
1386
 
1529 hidnplayr 1387
; add socket to the list by re-arranging some pointers
2402 hidnplayr 1388
        mov     ebx, [net_sockets + SOCKET.NextPtr]
1514 hidnplayr 1389
 
2402 hidnplayr 1390
        mov     [eax + SOCKET.PrevPtr], net_sockets
1391
        mov     [eax + SOCKET.NextPtr], ebx
1514 hidnplayr 1392
 
2402 hidnplayr 1393
        test    ebx, ebx
1394
        jz      @f
1395
 
1396
        pusha
1397
        lea     ecx, [ebx + SOCKET.mutex]
1398
        call    mutex_lock
1399
        popa
1400
 
1401
        mov     [ebx + SOCKET.PrevPtr], eax
1402
 
1403
        pusha
1404
        lea     ecx, [ebx + SOCKET.mutex]
1405
        call    mutex_unlock
1406
        popa
1514 hidnplayr 1407
       @@:
1408
 
2402 hidnplayr 1409
        mov     [net_sockets + SOCKET.NextPtr], eax
1410
        or      eax, eax                ; used to clear zero flag
1159 hidnplayr 1411
  .exit:
2402 hidnplayr 1412
        pop     ebx
1514 hidnplayr 1413
 
2402 hidnplayr 1414
        ret
1159 hidnplayr 1415
 
1514 hidnplayr 1416
 
1417
;----------------------------------------------------
1159 hidnplayr 1418
;
1514 hidnplayr 1419
; SOCKET_free
1159 hidnplayr 1420
;
1514 hidnplayr 1421
; Free socket data memory and remove socket from the list
1422
;
1423
; IN:  eax = socket ptr
1424
; OUT: /
1425
;
1426
;----------------------------------------------------
1427
align 4
1428
SOCKET_free:
1159 hidnplayr 1429
 
2402 hidnplayr 1430
        DEBUGF  1, "SOCKET_free: %x\n", eax
1514 hidnplayr 1431
 
2402 hidnplayr 1432
        call    SOCKET_check
1433
        jz      .error
1159 hidnplayr 1434
 
2402 hidnplayr 1435
        push    ebx
1514 hidnplayr 1436
 
2402 hidnplayr 1437
        pusha
1438
        lea     ecx, [eax + SOCKET.mutex]
1439
        call    mutex_lock
1440
        popa
1514 hidnplayr 1441
 
2402 hidnplayr 1442
        DEBUGF  1, "SOCKET_free: freeing socket..\n"
1529 hidnplayr 1443
 
2402 hidnplayr 1444
        cmp     [eax + SOCKET.Domain], AF_INET4
1445
        jnz     .no_tcp
1529 hidnplayr 1446
 
2402 hidnplayr 1447
        cmp     [eax + SOCKET.Protocol], IP_PROTO_TCP
1448
        jnz     .no_tcp
1449
 
1450
        mov     ebx, eax
1451
        stdcall kernel_free, [ebx + STREAM_SOCKET.rcv.start_ptr]
1452
        stdcall kernel_free, [ebx + STREAM_SOCKET.snd.start_ptr]
1453
        mov     eax, ebx
1536 hidnplayr 1454
  .no_tcp:
1529 hidnplayr 1455
 
2402 hidnplayr 1456
        push    eax                             ; this will be passed to kernel_free
1457
        mov     ebx, [eax + SOCKET.NextPtr]
1458
        mov     eax, [eax + SOCKET.PrevPtr]
1514 hidnplayr 1459
 
2402 hidnplayr 1460
        DEBUGF  1, "SOCKET_free: linking socket %x to socket %x\n", eax, ebx
1514 hidnplayr 1461
 
2402 hidnplayr 1462
        test    eax, eax
1463
        jz      @f
1464
        mov     [eax + SOCKET.NextPtr], ebx
1514 hidnplayr 1465
       @@:
1159 hidnplayr 1466
 
2402 hidnplayr 1467
        test    ebx, ebx
1468
        jz      @f
1469
        mov     [ebx + SOCKET.PrevPtr], eax
1514 hidnplayr 1470
       @@:
1249 hidnplayr 1471
 
2402 hidnplayr 1472
        call    kernel_free
1473
        pop     ebx
1159 hidnplayr 1474
 
2402 hidnplayr 1475
        DEBUGF  1, "SOCKET_free: success!\n"
1514 hidnplayr 1476
 
1159 hidnplayr 1477
  .error:
2402 hidnplayr 1478
        ret
1159 hidnplayr 1479
 
1543 hidnplayr 1480
;------------------------------------
1481
;
1482
; SOCKET_fork
1483
;
1484
; Create a child socket
1485
;
1533 hidnplayr 1486
; IN:  socket nr in ebx
1543 hidnplayr 1487
; OUT: child socket nr in eax
1488
;
1489
;-----------------------------------
1529 hidnplayr 1490
align 4
1491
SOCKET_fork:
1492
 
2402 hidnplayr 1493
        DEBUGF  1,"SOCKET_fork: %x\n", ebx
1529 hidnplayr 1494
 
1543 hidnplayr 1495
; Exit if backlog queue is full
2402 hidnplayr 1496
        mov     eax, [ebx + SOCKET_QUEUE_LOCATION + queue.size]
1497
        cmp     ax, [ebx + SOCKET.backlog]
1498
        jae     .fail
1543 hidnplayr 1499
 
1529 hidnplayr 1500
; Allocate new socket
2402 hidnplayr 1501
        push    ebx
1502
        call    SOCKET_alloc
1503
        pop     ebx
1504
        jz      .fail
1529 hidnplayr 1505
 
2402 hidnplayr 1506
        push    eax
1507
        mov     esi, esp
1508
        add_to_queue (ebx + SOCKET_QUEUE_LOCATION), MAX_backlog, 4, .fail2
1509
        pop     eax
1543 hidnplayr 1510
 
1511
; Copy structure from current socket to new
1512
; We start at PID to preserve the socket num, and the 2 pointers at beginning of socket
2402 hidnplayr 1513
        lea     esi, [ebx + SOCKET.PID]
1514
        lea     edi, [eax + SOCKET.PID]
1515
        mov     ecx, (SOCKET_QUEUE_LOCATION - SOCKET.PID + 3)/4
1516
        rep     movsd
1529 hidnplayr 1517
 
2402 hidnplayr 1518
        and     [eax + SOCKET.options], not SO_ACCEPTCON
1529 hidnplayr 1519
 
2402 hidnplayr 1520
        ret
1529 hidnplayr 1521
 
1543 hidnplayr 1522
  .fail2:
2402 hidnplayr 1523
        add     esp, 4+4+4
1543 hidnplayr 1524
  .fail:
2402 hidnplayr 1525
        DEBUGF  1,"SOCKET_fork: failed\n"
1526
        xor     eax, eax
1527
        ret
1529 hidnplayr 1528
 
1543 hidnplayr 1529
 
1514 hidnplayr 1530
;---------------------------------------------------
1531
;
1532
; SOCKET_num_to_ptr
1533
;
1159 hidnplayr 1534
; Get socket structure address by its number
1535
;
1514 hidnplayr 1536
; IN:  ecx = socket number
1533 hidnplayr 1537
; OUT: eax = 0 on error, socket ptr otherwise
1514 hidnplayr 1538
;       ZF = set on error
1159 hidnplayr 1539
;
1514 hidnplayr 1540
;---------------------------------------------------
1541
align 4
1542
SOCKET_num_to_ptr:
1159 hidnplayr 1543
 
2402 hidnplayr 1544
        DEBUGF  1,"SOCKET_num_to_ptr: %u ", ecx
1514 hidnplayr 1545
 
2402 hidnplayr 1546
        mov     eax, net_sockets
1514 hidnplayr 1547
 
1159 hidnplayr 1548
  .next_socket:
2402 hidnplayr 1549
        mov     eax, [eax + SOCKET.NextPtr]
1550
        or      eax, eax
1551
        jz      .error
1552
        cmp     [eax + SOCKET.Number], ecx
1553
        jne     .next_socket
1159 hidnplayr 1554
 
2402 hidnplayr 1555
        test    eax, eax
1159 hidnplayr 1556
 
2402 hidnplayr 1557
        DEBUGF  1,"(%x)\n", eax
1159 hidnplayr 1558
  .error:
2402 hidnplayr 1559
        ret
1159 hidnplayr 1560
 
1514 hidnplayr 1561
 
1562
;---------------------------------------------------
1159 hidnplayr 1563
;
1514 hidnplayr 1564
; SOCKET_ptr_to_num
1159 hidnplayr 1565
;
1514 hidnplayr 1566
; Get socket number by its address
1567
;
1568
; IN:  eax = socket ptr
1569
; OUT: eax = 0 on error, socket num otherwise
1570
;       ZF = set on error
1571
;
1572
;---------------------------------------------------
1573
align 4
1574
SOCKET_ptr_to_num:
1575
 
2402 hidnplayr 1576
        DEBUGF  1,"SOCKET_ptr_to_num: %x ", eax
1514 hidnplayr 1577
 
2402 hidnplayr 1578
        call    SOCKET_check
1579
        jz      .error
1159 hidnplayr 1580
 
2402 hidnplayr 1581
        mov     eax, [eax + SOCKET.Number]
1514 hidnplayr 1582
 
2402 hidnplayr 1583
        DEBUGF  1,"(%u)\n", eax
1514 hidnplayr 1584
 
1585
  .error:
2402 hidnplayr 1586
        ret
1514 hidnplayr 1587
 
1588
 
1589
;---------------------------------------------------
1590
;
1591
; SOCKET_check
1592
;
1593
; checks if the given value is really a socket ptr
1594
;
1595
; IN:  eax = socket ptr
1596
; OUT: eax = 0 on error, unchanged otherwise
1597
;       ZF = set on error
1598
;
1599
;---------------------------------------------------
1600
align 4
1601
SOCKET_check:
1602
 
2402 hidnplayr 1603
        DEBUGF  1,"SOCKET_check: %x\n", eax
1514 hidnplayr 1604
 
2402 hidnplayr 1605
        push    ebx
1606
        mov     ebx, net_sockets
1514 hidnplayr 1607
 
1159 hidnplayr 1608
  .next_socket:
2402 hidnplayr 1609
        mov     ebx, [ebx + SOCKET.NextPtr]
1610
        or      ebx, ebx
1611
        jz      .done
1612
        cmp     ebx, eax
1613
        jnz     .next_socket
1159 hidnplayr 1614
 
1514 hidnplayr 1615
  .done:
2402 hidnplayr 1616
        mov     eax, ebx
1617
        test    eax, eax
1618
        pop     ebx
1514 hidnplayr 1619
 
2402 hidnplayr 1620
        ret
1159 hidnplayr 1621
 
1514 hidnplayr 1622
 
1623
 
1624
;---------------------------------------------------
1625
;
1626
; SOCKET_check_owner
1627
;
1628
; checks if the caller application owns the socket
1629
;
1630
; IN:  eax = socket ptr
1631
; OUT:  ZF = true/false
1632
;
1633
;---------------------------------------------------
1634
align 4
1635
SOCKET_check_owner:
1636
 
2402 hidnplayr 1637
        DEBUGF  1,"SOCKET_check_owner: %x\n", eax
1514 hidnplayr 1638
 
2402 hidnplayr 1639
        push    ebx
1640
        mov     ebx, [TASK_BASE]
1641
        mov     ebx, [ecx + TASKDATA.pid]
1642
        cmp     [eax + SOCKET.PID], ebx
1643
        pop      ebx
1514 hidnplayr 1644
 
2402 hidnplayr 1645
        ret
1514 hidnplayr 1646
 
1647
 
1648
 
1649
 
1885 hidnplayr 1650
;------------------------------------------------------
1514 hidnplayr 1651
;
1652
; SOCKET_process_end
1653
;
1654
; Kernel calls this function when a certain process ends
1655
; This function will check if the process had any open sockets
1656
; And update them accordingly
1657
;
1658
; IN:  eax = pid
1659
; OUT: /
1660
;
1661
;------------------------------------------------------
1662
align 4
1663
SOCKET_process_end:
1664
 
2402 hidnplayr 1665
        DEBUGF  1,"SOCKET_process_end: %x\n", eax
1514 hidnplayr 1666
 
2402 hidnplayr 1667
        push    ebx
1668
        mov     ebx, net_sockets
1514 hidnplayr 1669
 
1670
  .next_socket:
1671
 
2402 hidnplayr 1672
        mov     ebx, [ebx + SOCKET.NextPtr]
1514 hidnplayr 1673
  .test_socket:
2402 hidnplayr 1674
        test    ebx, ebx
1675
        jz      .done
1514 hidnplayr 1676
 
2402 hidnplayr 1677
        cmp     [ebx + SOCKET.PID], eax
1678
        jne     .next_socket
1514 hidnplayr 1679
 
2402 hidnplayr 1680
        DEBUGF  1,"closing socket %x", eax, ebx
1514 hidnplayr 1681
 
2402 hidnplayr 1682
        mov     [ebx + SOCKET.PID], 0
1514 hidnplayr 1683
 
2402 hidnplayr 1684
        cmp     [ebx + SOCKET.Protocol], IP_PROTO_UDP
1685
        je      .udp
1514 hidnplayr 1686
 
2402 hidnplayr 1687
        cmp     [ebx + SOCKET.Protocol], IP_PROTO_TCP
1688
        je      .tcp
1514 hidnplayr 1689
 
2402 hidnplayr 1690
        jmp     .next_socket    ; kill all sockets for given PID
1514 hidnplayr 1691
 
1692
  .udp:
2402 hidnplayr 1693
        mov     eax, ebx
1694
        mov     ebx, [ebx + SOCKET.NextPtr]
1695
        call    SOCKET_free
1696
        jmp     .test_socket
1514 hidnplayr 1697
 
1698
  .tcp:
1699
 
2402 hidnplayr 1700
        ;;; TODO
1885 hidnplayr 1701
 
2402 hidnplayr 1702
        jmp     .next_socket
1514 hidnplayr 1703
 
1704
  .done:
2402 hidnplayr 1705
        pop     ebx
1514 hidnplayr 1706
 
2402 hidnplayr 1707
        ret
1773 hidnplayr 1708
 
1709
 
1710
 
1711
 
1885 hidnplayr 1712
;-----------------------------------------------------------------
1713
;
1714
; SOCKET_is_connecting
1715
;
1716
;  IN:  eax = socket ptr
1717
;  OUT: /
1718
;
1719
;-----------------------------------------------------------------
1773 hidnplayr 1720
 
1885 hidnplayr 1721
align 4
1722
SOCKET_is_connecting:
1773 hidnplayr 1723
 
1724
 
2402 hidnplayr 1725
        and     [eax + SOCKET.options], not (SS_ISCONNECTED + SS_ISDISCONNECTING + SS_ISCONFIRMING)
1726
        or      [eax + SOCKET.options], SS_ISCONNECTING
1773 hidnplayr 1727
 
2402 hidnplayr 1728
        jmp     SOCKET_notify_owner
1885 hidnplayr 1729
 
1730
 
1731
 
1773 hidnplayr 1732
;-----------------------------------------------------------------
1733
;
1885 hidnplayr 1734
; SOCKET_is_connected
1735
;
1736
;  IN:  eax = socket ptr
1737
;  OUT: /
1738
;
1739
;-----------------------------------------------------------------
1740
 
1741
align 4
1742
SOCKET_is_connected:
1743
 
1744
 
2402 hidnplayr 1745
        and     [eax + SOCKET.options], not (SS_ISCONNECTING + SS_ISDISCONNECTING + SS_ISCONFIRMING)
1746
        or      [eax + SOCKET.options], SS_ISCONNECTED
1885 hidnplayr 1747
 
2402 hidnplayr 1748
        jmp     SOCKET_notify_owner
1885 hidnplayr 1749
 
1750
 
1751
 
1752
 
1753
;-----------------------------------------------------------------
1754
;
1773 hidnplayr 1755
; SOCKET_is_disconnecting
1756
;
1757
;  IN:  eax = socket ptr
1758
;  OUT: /
1759
;
1760
;-----------------------------------------------------------------
1761
 
1762
align 4
1763
SOCKET_is_disconnecting:
1764
 
2402 hidnplayr 1765
        and     [eax + SOCKET.options], not (SS_ISCONNECTING)
1766
        or      [eax + SOCKET.options], SS_ISDISCONNECTING + SS_CANTRCVMORE + SS_CANTSENDMORE
1773 hidnplayr 1767
 
2402 hidnplayr 1768
        jmp     SOCKET_notify_owner
1773 hidnplayr 1769
 
1770
 
1771
 
1772
;-----------------------------------------------------------------
1773
;
1774
; SOCKET_is_disconnected
1775
;
1776
;  IN:  eax = socket ptr
1777
;  OUT: /
1778
;
1779
;-----------------------------------------------------------------
1780
 
1781
align 4
1782
SOCKET_is_disconnected:
1783
 
2402 hidnplayr 1784
        and     [eax + SOCKET.options], not (SS_ISCONNECTING + SS_ISCONNECTED + SS_ISDISCONNECTING)
1785
        or      [eax + SOCKET.options], SS_CANTRCVMORE + SS_CANTSENDMORE
1773 hidnplayr 1786
 
2402 hidnplayr 1787
        jmp     SOCKET_notify_owner
1774 hidnplayr 1788
 
1789
 
1790
;-----------------------------------------------------------------
1791
;
1792
; SOCKET_cant_recv_more
1793
;
1794
;  IN:  eax = socket ptr
1795
;  OUT: /
1796
;
1797
;-----------------------------------------------------------------
1798
 
1799
align 4
1800
SOCKET_cant_recv_more:
1801
 
2402 hidnplayr 1802
        or      [eax + SOCKET.options], SS_CANTRCVMORE
1885 hidnplayr 1803
 
2402 hidnplayr 1804
        ret
1831 hidnplayr 1805
 
1806
 
1807
 
1808
;-----------------------------------------------------------------
1809
;
1885 hidnplayr 1810
; SOCKET_cant_send_more
1831 hidnplayr 1811
;
1812
;  IN:  eax = socket ptr
1813
;  OUT: /
1814
;
1815
;-----------------------------------------------------------------
1816
 
1817
align 4
1885 hidnplayr 1818
SOCKET_cant_send_more:
1831 hidnplayr 1819
 
2402 hidnplayr 1820
        or      [eax + SOCKET.options], SS_CANTSENDMORE
1831 hidnplayr 1821
 
2402 hidnplayr 1822
        ret