Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
1171 hidnplayr 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                                 ;;
3251 hidnplayr 3
;; Copyright (C) KolibriOS team 2004-2013. All rights reserved.    ;;
1171 hidnplayr 4
;; Distributed under terms of the GNU General Public License       ;;
5
;;                                                                 ;;
6
;;  STACK.INC                                                      ;;
7
;;                                                                 ;;
1763 hidnplayr 8
;;  TCP/IP stack for KolibriOS                                     ;;
1171 hidnplayr 9
;;                                                                 ;;
10
;;    Written by hidnplayr@kolibrios.org                           ;;
11
;;                                                                 ;;
1763 hidnplayr 12
;;     Some parts of code are based on the work of:                ;;
13
;;      Mike Hibbett (menuetos network stack)                      ;;
14
;;      Eugen Brasoveanu (solar os network stack and drivers)      ;;
15
;;      mike.dld (kolibrios socket code)                           ;;
1171 hidnplayr 16
;;                                                                 ;;
1763 hidnplayr 17
;;     TCP part is based on 4.4BSD                                 ;;
18
;;                                                                 ;;
1171 hidnplayr 19
;;          GNU GENERAL PUBLIC LICENSE                             ;;
20
;;             Version 2, June 1991                                ;;
21
;;                                                                 ;;
22
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1159 hidnplayr 23
 
1206 hidnplayr 24
$Revision: 3523 $
1159 hidnplayr 25
 
26
uglobal
2366 hidnplayr 27
        net_10ms        dd ?
28
        net_tmr_count   dw ?
1159 hidnplayr 29
endg
30
 
2731 hidnplayr 31
MAX_NET_DEVICES         = 16
3360 hidnplayr 32
ARP_BLOCK               = 1             ; true or false
1159 hidnplayr 33
 
2731 hidnplayr 34
MIN_EPHEMERAL_PORT      = 49152
2995 hidnplayr 35
MIN_EPHEMERAL_PORT_N    = 0x00C0        ; same in Network byte order (FIXME)
2731 hidnplayr 36
MAX_EPHEMERAL_PORT      = 61000
2995 hidnplayr 37
MAX_EPHEMERAL_PORT_N    = 0x48EE        ; same in Network byte order (FIXME)
1159 hidnplayr 38
 
1514 hidnplayr 39
; Ethernet protocol numbers
2731 hidnplayr 40
ETHER_ARP               = 0x0608
41
ETHER_IPv4              = 0x0008
42
ETHER_IPv6              = 0xDD86
43
ETHER_PPP_DISCOVERY     = 0x6388
44
ETHER_PPP_SESSION       = 0x6488
1185 hidnplayr 45
 
2931 hidnplayr 46
; PPP protocol numbers
47
PPP_IPv4                = 0x2100
2964 hidnplayr 48
PPP_IPV6                = 0x5780
2931 hidnplayr 49
 
1514 hidnplayr 50
;Protocol family
2731 hidnplayr 51
AF_UNSPEC               = 0
3251 hidnplayr 52
AF_LOCAL                = 1
2731 hidnplayr 53
AF_INET4                = 2
54
AF_INET6                = 10
2931 hidnplayr 55
AF_PPP                  = 777
1159 hidnplayr 56
 
1514 hidnplayr 57
; Internet protocol numbers
2731 hidnplayr 58
IP_PROTO_IP             = 0
59
IP_PROTO_ICMP           = 1
60
IP_PROTO_TCP            = 6
61
IP_PROTO_UDP            = 17
1159 hidnplayr 62
 
2931 hidnplayr 63
; PPP protocol number
64
PPP_PROTO_ETHERNET      = 666
65
 
1200 hidnplayr 66
; Socket types
2731 hidnplayr 67
SOCK_STREAM             = 1
68
SOCK_DGRAM              = 2
69
SOCK_RAW                = 3
1200 hidnplayr 70
 
1514 hidnplayr 71
; Socket options
2731 hidnplayr 72
SO_ACCEPTCON            = 1 shl 0
73
SO_BROADCAST            = 1 shl 1
74
SO_DEBUG                = 1 shl 2
75
SO_DONTROUTE            = 1 shl 3
76
SO_KEEPALIVE            = 1 shl 4
77
SO_OOBINLINE            = 1 shl 5
78
SO_REUSEADDR            = 1 shl 6
79
SO_REUSEPORT            = 1 shl 7
80
SO_USELOOPBACK          = 1 shl 8
2877 hidnplayr 81
SO_BINDTODEVICE         = 1 shl 9
1159 hidnplayr 82
 
3257 hidnplayr 83
SO_BLOCK                = 1 shl 10    ; TO BE REMOVED
84
SO_NONBLOCK             = 1 shl 31
2994 hidnplayr 85
 
3459 hidnplayr 86
; Socket flags for user calls
87
MSG_PEEK                = 0x02
88
MSG_DONTWAIT            = 0x40
89
 
2877 hidnplayr 90
; Socket level
91
SOL_SOCKET              = 0
1885 hidnplayr 92
 
2877 hidnplayr 93
 
1773 hidnplayr 94
; Socket States
3257 hidnplayr 95
SS_NOFDREF              = 0x0001      ; no file table ref any more
96
SS_ISCONNECTED          = 0x0002      ; socket connected to a peer
97
SS_ISCONNECTING         = 0x0004      ; in process of connecting to peer
98
SS_ISDISCONNECTING      = 0x0008      ; in process of disconnecting
99
SS_CANTSENDMORE         = 0x0010      ; can't send more data to peer
100
SS_CANTRCVMORE          = 0x0020      ; can't receive more data from peer
101
SS_RCVATMARK            = 0x0040      ; at mark on input
102
SS_ISABORTING           = 0x0080      ; aborting fd references - close()
103
SS_RESTARTSYS           = 0x0100      ; restart blocked system calls
104
SS_ISDISCONNECTED       = 0x0800      ; socket disconnected from peer
1773 hidnplayr 105
 
3257 hidnplayr 106
SS_ASYNC                = 0x0100      ; async i/o notify
107
SS_ISCONFIRMING         = 0x0200      ; deciding to accept connection req
108
SS_MORETOCOME           = 0x0400
1773 hidnplayr 109
 
3257 hidnplayr 110
SS_BLOCKED              = 0x8000
1773 hidnplayr 111
 
3257 hidnplayr 112
 
2731 hidnplayr 113
SOCKET_MAXDATA          = 4096*32     ; must be 4096*(power of 2) where 'power of 2' is at least 8
1254 hidnplayr 114
 
1514 hidnplayr 115
; Network driver types
2914 hidnplayr 116
NET_TYPE_LOOPBACK       = 0
2731 hidnplayr 117
NET_TYPE_ETH            = 1
118
NET_TYPE_SLIP           = 2
1254 hidnplayr 119
 
2731 hidnplayr 120
MAX_backlog             = 20          ; maximum backlog for stream sockets
1254 hidnplayr 121
 
1716 hidnplayr 122
; Error Codes
2731 hidnplayr 123
ENOBUFS                 = 55
124
ECONNREFUSED            = 61
125
ECONNRESET              = 52
126
ETIMEDOUT               = 60
127
ECONNABORTED            = 53
1529 hidnplayr 128
 
2731 hidnplayr 129
; Api protocol numbers
130
API_ETH                 = 0
131
API_IPv4                = 1
132
API_ICMP                = 2
133
API_UDP                 = 3
134
API_TCP                 = 4
135
API_ARP                 = 5
136
API_PPPOE               = 6
3185 hidnplayr 137
API_IPv6                = 7
1716 hidnplayr 138
 
2924 hidnplayr 139
HWACC_TCP_IPv4          = 1 shl 0
140
 
2366 hidnplayr 141
struct  NET_DEVICE
1254 hidnplayr 142
 
2366 hidnplayr 143
        type            dd ?    ; Type field
144
        mtu             dd ?    ; Maximal Transmission Unit
145
        name            dd ?    ; Ptr to 0 terminated string
1519 hidnplayr 146
 
2366 hidnplayr 147
        unload          dd ?    ; Ptrs to driver functions
148
        reset           dd ?    ;
149
        transmit        dd ?    ;
1519 hidnplayr 150
 
2366 hidnplayr 151
        bytes_tx        dq ?    ; Statistics, updated by the driver
152
        bytes_rx        dq ?    ;
153
        packets_tx      dd ?    ;
154
        packets_rx      dd ?    ;
1519 hidnplayr 155
 
3346 hidnplayr 156
        state           dd ?    ; link state (0 = no link)
157
        hwacc           dd ?    ; bitmask stating enabled HW accelerations (offload engines)
1519 hidnplayr 158
 
2305 hidnplayr 159
ends
1529 hidnplayr 160
 
1254 hidnplayr 161
 
1514 hidnplayr 162
; Exactly as it says..
1318 hidnplayr 163
macro pseudo_random reg {
2366 hidnplayr 164
        add     reg, [esp]
165
        rol     reg, 5
166
        xor     reg, [timer_ticks]
167
        add     reg, [CPU_FREQ]
168
        imul    reg, 214013
169
        xor     reg, 0xdeadbeef
170
        rol     reg, 9
1514 hidnplayr 171
}
1318 hidnplayr 172
 
3249 hidnplayr 173
; Network to Hardware byte order (dword)
1543 hidnplayr 174
macro ntohd reg {
1318 hidnplayr 175
 
2366 hidnplayr 176
        rol     word reg, 8
177
        rol     dword reg, 16
178
        rol     word reg , 8
1514 hidnplayr 179
 
1318 hidnplayr 180
}
181
 
3249 hidnplayr 182
; Network to Hardware byte order (word)
1543 hidnplayr 183
macro ntohw reg {
1514 hidnplayr 184
 
2366 hidnplayr 185
        rol     word reg, 8
1514 hidnplayr 186
 
187
}
188
 
2382 hidnplayr 189
 
1159 hidnplayr 190
include "queue.inc"
1514 hidnplayr 191
 
2914 hidnplayr 192
include "loopback.inc"
1514 hidnplayr 193
include "ethernet.inc"
1719 hidnplayr 194
 
2931 hidnplayr 195
include "PPPoE.inc"
1514 hidnplayr 196
 
1187 hidnplayr 197
include "ARP.inc"
198
include "IPv4.inc"
3185 hidnplayr 199
include "IPv6.inc"
1514 hidnplayr 200
 
201
include "icmp.inc"
202
include "udp.inc"
1249 hidnplayr 203
include "tcp.inc"
1159 hidnplayr 204
 
1514 hidnplayr 205
include "socket.inc"
206
 
207
 
208
 
209
align 4
210
uglobal
211
 
2366 hidnplayr 212
        NET_RUNNING     dd  ?
213
        NET_DEFAULT     dd  ?
214
        NET_DRV_LIST    rd  MAX_NET_DEVICES
1514 hidnplayr 215
 
216
endg
217
 
218
 
1257 hidnplayr 219
;-----------------------------------------------------------------
1159 hidnplayr 220
;
221
; stack_init
222
;
223
;  This function calls all network init procedures
224
;
225
;  IN:  /
226
;  OUT: /
227
;
1257 hidnplayr 228
;-----------------------------------------------------------------
1159 hidnplayr 229
align 4
230
stack_init:
231
 
1514 hidnplayr 232
; Init the network drivers list
2366 hidnplayr 233
        xor     eax, eax
234
        mov     edi, NET_RUNNING
235
        mov     ecx, (MAX_NET_DEVICES + 2)
236
        rep     stosd
1514 hidnplayr 237
 
2960 hidnplayr 238
        PPPoE_init
1514 hidnplayr 239
 
2366 hidnplayr 240
        IPv4_init
2731 hidnplayr 241
;        IPv6_init
2366 hidnplayr 242
        ICMP_init
1514 hidnplayr 243
 
2366 hidnplayr 244
        ARP_init
245
        UDP_init
246
        TCP_init
1514 hidnplayr 247
 
2366 hidnplayr 248
        SOCKET_init
1514 hidnplayr 249
 
2366 hidnplayr 250
        mov     [net_tmr_count], 0
1159 hidnplayr 251
 
2366 hidnplayr 252
        ret
1159 hidnplayr 253
 
254
 
1257 hidnplayr 255
;-----------------------------------------------------------------
1159 hidnplayr 256
;
257
; stack_handler
258
;
1514 hidnplayr 259
;  This function is called in kernel loop
1159 hidnplayr 260
;
261
;  IN:  /
262
;  OUT: /
263
;
1257 hidnplayr 264
;-----------------------------------------------------------------
1159 hidnplayr 265
align 4
266
stack_handler:
267
 
2366 hidnplayr 268
        cmp     [NET_RUNNING], 0
269
        je      .exit
1159 hidnplayr 270
 
3459 hidnplayr 271
 
2366 hidnplayr 272
        ; Test for 10ms tick
273
        mov     eax, [timer_ticks]
274
        cmp     eax, [net_10ms]
275
        je      .exit
276
        mov     [net_10ms], eax
1159 hidnplayr 277
 
2366 hidnplayr 278
        test    [net_10ms], 0x0f        ; 160ms
279
        jnz     .exit
1249 hidnplayr 280
 
2366 hidnplayr 281
        TCP_timer_160ms
1159 hidnplayr 282
 
2366 hidnplayr 283
        test    [net_10ms], 0x3f        ; 640ms
284
        jnz     .exit
1519 hidnplayr 285
 
2366 hidnplayr 286
        TCP_timer_640ms
287
        ARP_decrease_entry_ttls
288
        IPv4_decrease_fragment_ttls
1159 hidnplayr 289
 
290
  .exit:
2366 hidnplayr 291
        ret
1159 hidnplayr 292
 
293
 
1514 hidnplayr 294
 
3340 hidnplayr 295
align 4
296
NET_link_changed:
297
 
3388 hidnplayr 298
        DEBUGF  1,"NET_link_changed device=0x%x status=0x%x\n", ebx, [ebx + NET_DEVICE.state]
3359 hidnplayr 299
 
3340 hidnplayr 300
align 4
301
NET_send_event:
302
 
3346 hidnplayr 303
        DEBUGF  1,"NET_send_event\n"
304
 
3340 hidnplayr 305
; Send event to all applications
306
        push    edi ecx
307
        mov     edi, SLOT_BASE
308
        mov     ecx, [TASK_COUNT]
309
  .loop:
310
        add     edi, 256
311
        or      [edi + APPDATA.event_mask], EVENT_NETWORK2
312
        loop    .loop
313
        pop     ecx edi
314
 
3518 hidnplayr 315
        call    change_task
3340 hidnplayr 316
 
317
        ret
318
 
319
 
320
 
1249 hidnplayr 321
;-----------------------------------------------------------------
322
;
2220 hidnplayr 323
; NET_add_device:
1514 hidnplayr 324
;
325
;  This function is called by the network drivers,
326
;  to register each running NIC to the kernel
327
;
328
;  IN:  Pointer to device structure in ebx
329
;  OUT: Device num in eax, -1 on error
330
;
331
;-----------------------------------------------------------------
332
align 4
333
NET_add_device:
334
 
2366 hidnplayr 335
        DEBUGF  1,"NET_Add_Device: %x\n", ebx   ;;; TODO: use mutex to lock net device list
1514 hidnplayr 336
 
3359 hidnplayr 337
        cmp     [NET_RUNNING], MAX_NET_DEVICES
2366 hidnplayr 338
        jae     .error
1514 hidnplayr 339
 
340
;----------------------------------
341
; Check if device is already listed
2366 hidnplayr 342
        mov     eax, ebx
343
        mov     ecx, MAX_NET_DEVICES    ; We need to check whole list because a device may be removed without re-organizing list
344
        mov     edi, NET_DRV_LIST
1514 hidnplayr 345
 
2366 hidnplayr 346
        repne   scasd                   ; See if device is already in the list
347
        jz      .error
1514 hidnplayr 348
 
349
;----------------------------
350
; Find empty slot in the list
2366 hidnplayr 351
        xor     eax, eax
352
        mov     ecx, MAX_NET_DEVICES
353
        mov     edi, NET_DRV_LIST
1514 hidnplayr 354
 
2366 hidnplayr 355
        repne   scasd
356
        jnz     .error
1514 hidnplayr 357
 
2366 hidnplayr 358
        sub     edi, 4
1514 hidnplayr 359
 
2220 hidnplayr 360
;-----------------------------
361
; Add device to the found slot
2366 hidnplayr 362
        mov     [edi], ebx              ; add device to list
1514 hidnplayr 363
 
2366 hidnplayr 364
        mov     eax, edi                ; Calculate device number in eax
365
        sub     eax, NET_DRV_LIST
366
        shr     eax, 2
1514 hidnplayr 367
 
2366 hidnplayr 368
        inc     [NET_RUNNING]           ; Indicate that one more network device is up and running
1514 hidnplayr 369
 
2366 hidnplayr 370
        cmp     eax, 1                  ; If it's the first network device, try to set it as default
371
        jne     @f
372
        push    eax
373
        call    NET_set_default
374
        pop     eax
2220 hidnplayr 375
       @@:
1514 hidnplayr 376
 
3340 hidnplayr 377
        call    NET_send_event
378
 
2366 hidnplayr 379
        DEBUGF  1,"Device number: %u\n", eax
380
        ret
1514 hidnplayr 381
 
2220 hidnplayr 382
  .error:
2366 hidnplayr 383
        or      eax, -1
384
        DEBUGF  2,"Adding network device failed\n"
385
        ret
1514 hidnplayr 386
 
387
 
388
 
2220 hidnplayr 389
;-----------------------------------------------------------------
390
;
391
; NET_set_default
392
;
393
;  API to set the default interface
394
;
395
;  IN:  Device num in eax
396
;  OUT: Device num in eax, -1 on error
397
;
398
;-----------------------------------------------------------------
399
align 4
400
NET_set_default:
1514 hidnplayr 401
 
2891 hidnplayr 402
        DEBUGF  1,"NET_set_default: device=%x\n", eax
1514 hidnplayr 403
 
2366 hidnplayr 404
        cmp     eax, MAX_NET_DEVICES
405
        jae     .error
1514 hidnplayr 406
 
2366 hidnplayr 407
        cmp     [NET_DRV_LIST+eax*4], 0
408
        je      .error
2220 hidnplayr 409
 
2366 hidnplayr 410
        mov     [NET_DEFAULT], eax
2220 hidnplayr 411
 
2891 hidnplayr 412
        DEBUGF  1,"NET_set_default: succes\n"
2366 hidnplayr 413
        ret
1514 hidnplayr 414
 
415
  .error:
2366 hidnplayr 416
        or      eax, -1
2891 hidnplayr 417
        DEBUGF  1,"NET_set_default: failed\n"
2366 hidnplayr 418
        ret
1514 hidnplayr 419
 
420
 
421
;-----------------------------------------------------------------
422
;
423
; NET_Remove_Device:
424
;
425
;  This function is called by etwork drivers,
426
;  to unregister network devices from the kernel
2891 hidnplayr 427
;
1514 hidnplayr 428
;  IN:  Pointer to device structure in ebx
429
;  OUT: eax: -1 on error
430
;
431
;-----------------------------------------------------------------
432
align 4
433
NET_remove_device:
434
 
2366 hidnplayr 435
        cmp     [NET_RUNNING], 0
436
        je      .error
1514 hidnplayr 437
 
2366 hidnplayr 438
        cmp     [NET_DRV_LIST], ebx
439
        jne     @f
440
        mov     [NET_DRV_LIST], 0
441
        cmp     [NET_RUNNING], 1
442
        je      @f
443
        ; there are still active devices, find one and make it default
444
        xor     eax, eax
445
        mov     ecx, MAX_NET_DEVICES
446
        mov     edi, NET_DRV_LIST
447
        repe    scasd
448
        je      @f
449
        shr     edi, 2
450
        dec     edi
451
        mov     [NET_DEFAULT], edi
2220 hidnplayr 452
       @@:
453
 
1514 hidnplayr 454
;----------------------------
455
; Find the driver in the list
456
 
2366 hidnplayr 457
        mov     eax, ebx
458
        mov     ecx, MAX_NET_DEVICES
459
        mov     edi, NET_DRV_LIST+4
1514 hidnplayr 460
 
2366 hidnplayr 461
        repne   scasd
462
        jnz     .error
1514 hidnplayr 463
 
464
;------------------------
465
; Remove it from the list
466
 
2366 hidnplayr 467
        xor     eax, eax
468
        mov     dword [edi-4], eax
1514 hidnplayr 469
 
3340 hidnplayr 470
        call    NET_send_event
471
 
2366 hidnplayr 472
        dec     [NET_RUNNING]
473
        ret
1514 hidnplayr 474
 
475
  .error:
2366 hidnplayr 476
        or      eax, -1
477
        ret
1514 hidnplayr 478
 
479
 
480
 
481
;-----------------------------------------------------------------
482
;
483
; NET_ptr_to_num
484
;
485
; IN:  ebx = ptr to device struct
486
; OUT: edi = -1 on error, device number otherwise
487
;
488
;-----------------------------------------------------------------
489
align 4
490
NET_ptr_to_num:
2366 hidnplayr 491
        push    ecx
1514 hidnplayr 492
 
2366 hidnplayr 493
        mov     ecx, MAX_NET_DEVICES
494
        mov     edi, NET_DRV_LIST
1514 hidnplayr 495
 
496
  .loop:
2366 hidnplayr 497
        cmp     ebx, [edi]
498
        jz      .found
499
        add     edi, 4
500
        dec     ecx
501
        jnz     .loop
1514 hidnplayr 502
 
2366 hidnplayr 503
        ; repnz  scasd could work too if eax is used instead of ebx!
1514 hidnplayr 504
 
2366 hidnplayr 505
        or      edi, -1
1514 hidnplayr 506
 
2366 hidnplayr 507
        pop     ecx
508
        ret
1514 hidnplayr 509
 
510
  .found:
2366 hidnplayr 511
        sub     edi, NET_DRV_LIST
512
        shr     edi, 2
1514 hidnplayr 513
 
2366 hidnplayr 514
        pop     ecx
515
        ret
1514 hidnplayr 516
 
517
;-----------------------------------------------------------------
518
;
1249 hidnplayr 519
; checksum_1
520
;
1482 hidnplayr 521
;  This is the first of two functions needed to calculate a checksum.
1249 hidnplayr 522
;
1473 hidnplayr 523
;  IN:  edx = start offset for semi-checksum
1249 hidnplayr 524
;       esi = pointer to data
525
;       ecx = data size
526
;  OUT: edx = semi-checksum
527
;
1473 hidnplayr 528
;
529
; Code was optimized by diamond
530
;
1249 hidnplayr 531
;-----------------------------------------------------------------
532
align 4
533
checksum_1:
1159 hidnplayr 534
 
2366 hidnplayr 535
        shr     ecx, 1
536
        pushf
537
        jz      .no_2
1159 hidnplayr 538
 
2366 hidnplayr 539
        shr     ecx, 1
540
        pushf
541
        jz      .no_4
1473 hidnplayr 542
 
2366 hidnplayr 543
        shr     ecx, 1
544
        pushf
545
        jz      .no_8
1473 hidnplayr 546
 
547
  .loop:
2366 hidnplayr 548
        add     dl, [esi+1]
549
        adc     dh, [esi+0]
1473 hidnplayr 550
 
2366 hidnplayr 551
        adc     dl, [esi+3]
552
        adc     dh, [esi+2]
1473 hidnplayr 553
 
2366 hidnplayr 554
        adc     dl, [esi+5]
555
        adc     dh, [esi+4]
1473 hidnplayr 556
 
2366 hidnplayr 557
        adc     dl, [esi+7]
558
        adc     dh, [esi+6]
1473 hidnplayr 559
 
2366 hidnplayr 560
        adc     edx, 0
561
        add     esi, 8
1473 hidnplayr 562
 
2366 hidnplayr 563
        dec     ecx
564
        jnz     .loop
1473 hidnplayr 565
 
2366 hidnplayr 566
        adc     edx, 0
1473 hidnplayr 567
 
568
  .no_8:
2366 hidnplayr 569
        popf
570
        jnc     .no_4
1473 hidnplayr 571
 
2366 hidnplayr 572
        add     dl, [esi+1]
573
        adc     dh, [esi+0]
1473 hidnplayr 574
 
2366 hidnplayr 575
        adc     dl, [esi+3]
576
        adc     dh, [esi+2]
1473 hidnplayr 577
 
2366 hidnplayr 578
        adc     edx, 0
579
        add     esi, 4
1473 hidnplayr 580
 
581
  .no_4:
2366 hidnplayr 582
        popf
583
        jnc     .no_2
1473 hidnplayr 584
 
2366 hidnplayr 585
        add     dl, [esi+1]
586
        adc     dh, [esi+0]
1473 hidnplayr 587
 
2366 hidnplayr 588
        adc     edx, 0
589
        inc     esi
590
        inc     esi
1473 hidnplayr 591
 
592
  .no_2:
2366 hidnplayr 593
        popf
594
        jnc     .end
1159 hidnplayr 595
 
2366 hidnplayr 596
        add     dh, [esi+0]
597
        adc     edx, 0
1473 hidnplayr 598
  .end:
2366 hidnplayr 599
        ret
1159 hidnplayr 600
 
1249 hidnplayr 601
;-----------------------------------------------------------------
602
;
603
; checksum_2
604
;
605
;  This function calculates the final ip/tcp/udp checksum for you
606
;
607
;  IN:  edx = semi-checksum
608
;  OUT: dx = checksum (in INET byte order)
609
;
610
;-----------------------------------------------------------------
611
align 4
612
checksum_2:
613
 
2366 hidnplayr 614
        mov     ecx, edx
615
        shr     ecx, 16
616
        and     edx, 0xffff
617
        add     edx, ecx
1249 hidnplayr 618
 
2366 hidnplayr 619
        mov     ecx, edx
620
        shr     ecx, 16
621
        add     dx, cx
622
        test    dx, dx          ; it seems that ZF is not set when CF is set :(
623
        not     dx
624
        jnz     .not_zero
625
        dec     dx
1249 hidnplayr 626
  .not_zero:
2366 hidnplayr 627
        xchg    dl, dh
1249 hidnplayr 628
 
3251 hidnplayr 629
        DEBUGF  1,"Checksum: %x\n", dx
1249 hidnplayr 630
 
2366 hidnplayr 631
        ret
1249 hidnplayr 632
 
633
 
634
 
1159 hidnplayr 635
;----------------------------------------------------------------
636
;
3146 hidnplayr 637
;  System function to work with network devices (75)
1159 hidnplayr 638
;
639
;----------------------------------------------------------------
640
align 4
2366 hidnplayr 641
sys_network:                    ; FIXME: make default device easily accessible
1159 hidnplayr 642
 
2366 hidnplayr 643
        cmp     ebx, -1
644
        jne     @f
1196 hidnplayr 645
 
2366 hidnplayr 646
        mov     eax, [NET_RUNNING]
647
        jmp     .return
1196 hidnplayr 648
 
649
   @@:
2366 hidnplayr 650
        cmp     bh, MAX_NET_DEVICES             ; Check if device number exists
651
        jae     .doesnt_exist
1159 hidnplayr 652
 
2366 hidnplayr 653
        mov     esi, ebx
654
        and     esi, 0x0000ff00
655
        shr     esi, 6
1159 hidnplayr 656
 
2366 hidnplayr 657
        cmp     dword [esi + NET_DRV_LIST], 0   ; check if driver is running
658
        je      .doesnt_exist
1159 hidnplayr 659
 
2621 hidnplayr 660
        mov     eax, [esi + NET_DRV_LIST]
2220 hidnplayr 661
 
2621 hidnplayr 662
        and     ebx, 0x000000ff
663
        cmp     ebx, .number
664
        ja      .doesnt_exist
665
        jmp     dword [.table + 4*ebx]
2220 hidnplayr 666
 
2621 hidnplayr 667
  .table:
668
        dd      .get_type               ; 0
669
        dd      .get_dev_name           ; 1
670
        dd      .reset                  ; 2
671
        dd      .stop                   ; 3
672
        dd      .get_ptr                ; 4
673
        dd      .get_drv_name           ; 5
674
        dd      .set_default            ; 6
675
  .number = ($ - .table) / 4 - 1
1514 hidnplayr 676
 
2621 hidnplayr 677
  .get_type:                            ; 0 = Get device type (ethernet/token ring/...)
678
 
679
        mov     eax, [eax + NET_DEVICE.type]
2366 hidnplayr 680
        jmp     .return
1159 hidnplayr 681
 
682
 
2621 hidnplayr 683
  .get_dev_name:                        ; 1 = Get device name
1159 hidnplayr 684
 
2621 hidnplayr 685
        mov     esi, [eax + NET_DEVICE.name]
2366 hidnplayr 686
        mov     edi, ecx
1159 hidnplayr 687
 
2621 hidnplayr 688
        mov     ecx, 64/4 ; max length
689
        rep     movsd
1159 hidnplayr 690
 
2366 hidnplayr 691
        xor     eax, eax
692
        jmp     .return
1159 hidnplayr 693
 
2621 hidnplayr 694
  .reset:                               ; 2 = Reset the device
1159 hidnplayr 695
 
2621 hidnplayr 696
        call    [eax + NET_DEVICE.reset]
2366 hidnplayr 697
        jmp     .return
1192 hidnplayr 698
 
2621 hidnplayr 699
  .stop:                                ; 3 = Stop driver for this device
1192 hidnplayr 700
 
2621 hidnplayr 701
        call    [eax + NET_DEVICE.unload]
2366 hidnplayr 702
        jmp     .return
1192 hidnplayr 703
 
704
 
2621 hidnplayr 705
  .get_ptr:                             ; 4 = Get driver pointer
706
 
2366 hidnplayr 707
        jmp     .return
1249 hidnplayr 708
 
709
 
2621 hidnplayr 710
  .get_drv_name:                        ; 5 = Get driver name
1249 hidnplayr 711
 
2366 hidnplayr 712
        xor     eax, eax
713
        jmp     .return
2220 hidnplayr 714
 
715
 
2621 hidnplayr 716
  .set_default:                         ; 6 = Set default device
2220 hidnplayr 717
 
2366 hidnplayr 718
        call    NET_set_default
719
        jmp     .return
2220 hidnplayr 720
 
1159 hidnplayr 721
  .doesnt_exist:
2366 hidnplayr 722
        mov     eax, -1
1159 hidnplayr 723
 
1192 hidnplayr 724
  .return:
2621 hidnplayr 725
        mov     [esp+32], eax
2366 hidnplayr 726
        ret
1159 hidnplayr 727
 
728
 
729
;----------------------------------------------------------------
730
;
2731 hidnplayr 731
;  System function to work with protocols  (76)
1159 hidnplayr 732
;
733
;----------------------------------------------------------------
734
align 4
735
sys_protocols:
2366 hidnplayr 736
        cmp     bh, MAX_NET_DEVICES             ; Check if device number exists
737
        jae     .doesnt_exist
1159 hidnplayr 738
 
2366 hidnplayr 739
        mov     esi, ebx
740
        and     esi, 0x0000ff00
741
        shr     esi, 6                          ; now we have the device num * 4 in esi
742
        cmp     [esi + NET_DRV_LIST], 0         ; check if driver is running
743
        je      .doesnt_exist
1159 hidnplayr 744
 
2366 hidnplayr 745
        push    .return                         ; return address (we will be using jumps instead of calls)
1159 hidnplayr 746
 
2366 hidnplayr 747
        mov     eax, ebx                        ; set ax to protocol number
748
        shr     eax, 16                         ;
1159 hidnplayr 749
 
2731 hidnplayr 750
        cmp     ax, API_ETH
751
        je      ETH_api
752
 
753
        cmp     ax, API_IPv4
2614 hidnplayr 754
        je      IPv4_api
1159 hidnplayr 755
 
2731 hidnplayr 756
        cmp     ax, API_ICMP
2614 hidnplayr 757
        je      ICMP_api
1159 hidnplayr 758
 
2731 hidnplayr 759
        cmp     ax, API_UDP
2614 hidnplayr 760
        je      UDP_api
1159 hidnplayr 761
 
2731 hidnplayr 762
        cmp     ax, API_TCP
2614 hidnplayr 763
        je      TCP_api
1159 hidnplayr 764
 
2731 hidnplayr 765
        cmp     ax, API_ARP
2614 hidnplayr 766
        je      ARP_api
1159 hidnplayr 767
 
2931 hidnplayr 768
        cmp     ax, API_PPPOE
769
        je      PPPoE_api
2614 hidnplayr 770
 
3185 hidnplayr 771
        cmp     ax, API_IPv6
772
        je      IPv6_api
773
 
2366 hidnplayr 774
        add     esp, 4                           ; if we reached here, no function was called, so we need to balance stack
1159 hidnplayr 775
 
776
  .doesnt_exist:
2366 hidnplayr 777
        mov     eax, -1
1159 hidnplayr 778
 
779
  .return:
2614 hidnplayr 780
        mov     [esp+28+4], eax                 ; return eax value to the program
2366 hidnplayr 781
        ret