Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
3200 hidnplayr 1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                                 ;;
3
;; Copyright (C) KolibriOS team 2010-2013. All rights reserved.    ;;
4
;; Distributed under terms of the GNU General Public License       ;;
5
;;                                                                 ;;
6
;;  zeroconfig.asm - Zeroconfig service for KolibriOS              ;;
7
;;                                                                 ;;
8
;;  Written by hidnplayr@kolibrios.org                             ;;
9
;;    Some code contributed by Derpenguin                          ;;
10
;;                                                                 ;;
11
;;  DHCP code is based on that by Mike Hibbet                      ;;
12
;       (DHCP client for menuetos)                                 ;;
13
;;                                                                 ;;
14
;;          GNU GENERAL PUBLIC LICENSE                             ;;
15
;;             Version 2, June 1991                                ;;
16
;;                                                                 ;;
17
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1164 hidnplayr 18
 
2856 hidnplayr 19
format binary as ""
20
 
1164 hidnplayr 21
use32
2856 hidnplayr 22
               org    0x0
1164 hidnplayr 23
 
2856 hidnplayr 24
               db     'MENUET01'            ; 8 byte id
25
               dd     0x01                  ; header version
26
               dd     START                 ; start of code
27
               dd     IM_END                ; size of image
28
               dd     (I_END+0x100)         ; memory for app
29
               dd     (I_END+0x100)         ; esp
30
               dd     0x0 , path            ; I_Param , I_Icon
1164 hidnplayr 31
 
32
; CONFIGURATION
33
 
2856 hidnplayr 34
TIMEOUT             equ 60                  ; in seconds
35
BUFFER              equ 1024                ; in bytes
36
__DEBUG__           equ 1                   ; enable/disable
37
__DEBUG_LEVEL__     equ 1                   ; 1 = all, 2 = errors
1164 hidnplayr 38
 
39
; CONFIGURATION FOR LINK-LOCAL
40
 
2856 hidnplayr 41
PROBE_WAIT          equ 1                   ; second  (initial random delay)
42
PROBE_MIN           equ 1                   ; second  (minimum delay till repeated probe)
43
PROBE_MAX           equ 2                   ; seconds (maximum delay till repeated probe)
44
PROBE_NUM           equ 3                   ;         (number of probe packets)
1164 hidnplayr 45
 
2856 hidnplayr 46
ANNOUNCE_NUM        equ 2                   ;         (number of announcement packets)
47
ANNOUNCE_INTERVAL   equ 2                   ; seconds (time between announcement packets)
48
ANNOUNCE_WAIT       equ 2                   ; seconds (delay before announcing)
1164 hidnplayr 49
 
2856 hidnplayr 50
MAX_CONFLICTS       equ 10                  ;         (max conflicts before rate limiting)
1164 hidnplayr 51
 
2856 hidnplayr 52
RATE_LIMIT_INTERVAL equ 60                  ; seconds (delay between successive attempts)
1164 hidnplayr 53
 
2856 hidnplayr 54
DEFEND_INTERVAL     equ 10                  ; seconds (min. wait between defensive ARPs)
1164 hidnplayr 55
 
56
 
1166 hidnplayr 57
include '../proc32.inc'
58
include '../macros.inc'
59
include '../debug-fdo.inc'
1542 hidnplayr 60
include '../network.inc'
1164 hidnplayr 61
include 'dhcp.inc'
2856 hidnplayr 62
include '../dll.inc'
1164 hidnplayr 63
 
64
 
65
Ip2dword:
66
    push    edx
67
 
68
    ; This code validates if the query is an IP containing 4 numbers and 3 dots
69
 
2856 hidnplayr 70
    xor     al, al            ; make al (dot count) zero
1164 hidnplayr 71
 
72
   @@:
73
    cmp     byte[edx],'0'     ; check if this byte is a number, if not jump to no_IP
2856 hidnplayr 74
    jl      no_IP             ;
1164 hidnplayr 75
    cmp     byte[edx],'9'     ;
2856 hidnplayr 76
    jg      no_IP             ;
1164 hidnplayr 77
 
2856 hidnplayr 78
    inc     edx               ; the byte was a number, so lets check the next byte
1164 hidnplayr 79
 
80
    cmp     byte[edx],0       ; is this byte zero? (have we reached end of query?)
2856 hidnplayr 81
    jz      @f                ; jump to next @@ then
1164 hidnplayr 82
    cmp     byte[edx],':'
2856 hidnplayr 83
    jz      @f
1164 hidnplayr 84
 
85
    cmp     byte[edx],'.'     ; is this byte a dot?
2856 hidnplayr 86
    jne     @r                ; if not, jump to previous @@
1164 hidnplayr 87
 
2856 hidnplayr 88
    inc     al                ; the byte was a dot so increment al(dot count)
89
    inc     edx               ; next byte
90
    jmp     @r                ; lets check for numbers again (jump to previous @@)
1164 hidnplayr 91
 
2856 hidnplayr 92
   @@:                        ; we reach this when end of query reached
93
    cmp     al,3              ; check if there where 3 dots
94
    jnz     no_IP             ; if not, jump to no_IP
1164 hidnplayr 95
 
96
    ; The following code will convert this IP into a dword and output it in eax
97
    ; If there is also a port number specified, this will be returned in ebx, otherwise ebx is -1
98
 
2856 hidnplayr 99
    pop     esi               ; edx (query address) was pushed onto stack and is now popped in esi
1164 hidnplayr 100
 
2856 hidnplayr 101
    xor     edx, edx          ; result
102
    xor     eax, eax          ; current character
103
    xor     ebx, ebx          ; current byte
1164 hidnplayr 104
 
3200 hidnplayr 105
  .outer_loop:
1164 hidnplayr 106
    shl     edx, 8
107
    add     edx, ebx
108
    xor     ebx, ebx
3200 hidnplayr 109
  .inner_loop:
1164 hidnplayr 110
    lodsb
111
    test    eax, eax
2856 hidnplayr 112
    jz      .finish
1164 hidnplayr 113
    cmp     al, '.'
2856 hidnplayr 114
    jz      .outer_loop
1164 hidnplayr 115
    sub     eax, '0'
116
    imul    ebx, 10
117
    add     ebx, eax
118
    jmp     .inner_loop
3200 hidnplayr 119
  .finish:
1164 hidnplayr 120
    shl     edx, 8
121
    add     edx, ebx
122
 
2856 hidnplayr 123
    bswap   edx               ; we want little endian order
1164 hidnplayr 124
 
125
    ret
126
 
127
no_IP:
128
    pop     edx
129
    xor     edx, edx
130
 
131
    ret
132
 
133
 
134
 
135
 
136
 
137
 
3200 hidnplayr 138
START:
1164 hidnplayr 139
 
3200 hidnplayr 140
        mcall   40, EVM_STACK   ; network event
1164 hidnplayr 141
 
3200 hidnplayr 142
        DEBUGF  1,">Zero-config service loaded\n"
1164 hidnplayr 143
 
3200 hidnplayr 144
        mcall   76, API_ETH + 4 ; get MAC of ethernet interface 0
2856 hidnplayr 145
        cmp     eax, -1
146
        je      exit
1164 hidnplayr 147
 
2856 hidnplayr 148
        mov     word[MAC], bx
149
        mov     dword[MAC+2], eax
1164 hidnplayr 150
 
2856 hidnplayr 151
        DEBUGF  1,"->MAC: %x-%x-%x-%x-%x-%x\n",[MAC]:2,[MAC+1]:2,[MAC+2]:2,[MAC+3]:2,[MAC+4]:2,[MAC+5]:2
1164 hidnplayr 152
 
3200 hidnplayr 153
        mov     edi, path       ; Calculate the length of zero-terminated string
154
        xor     al, al
2856 hidnplayr 155
        mov     ecx, 1024
3200 hidnplayr 156
        repne   scasb
2856 hidnplayr 157
        dec     edi
1174 hidnplayr 158
 
3200 hidnplayr 159
        mov     esi, filename   ; append with .ini
2856 hidnplayr 160
        movsd
161
        movsb
1174 hidnplayr 162
 
3200 hidnplayr 163
        DEBUGF  1,"->Loading ini %s\n", path
1164 hidnplayr 164
 
3200 hidnplayr 165
        mcall   68, 11
1164 hidnplayr 166
 
2856 hidnplayr 167
        stdcall dll.Load,@IMPORT
3200 hidnplayr 168
        or      eax, eax
169
        jnz     try_dhcp
1164 hidnplayr 170
 
3200 hidnplayr 171
        invoke  ini.get_str, path, str_ipconfig, str_type, inibuf, 16, 0
1164 hidnplayr 172
 
3200 hidnplayr 173
        cmp     dword[inibuf], 'stat'
174
        jne     try_dhcp
1164 hidnplayr 175
 
3200 hidnplayr 176
        invoke  ini.get_str, path, str_ipconfig, str_ip, inibuf, 16, 0
177
        mov     edx, inibuf
178
        call    Ip2dword
179
        mcall   76, API_IPv4 + 3, edx
1164 hidnplayr 180
 
3200 hidnplayr 181
        invoke  ini.get_str, path, str_ipconfig, str_gateway, inibuf, 16, 0
182
        mov     edx, inibuf
183
        call    Ip2dword
184
        mcall   76, API_IPv4 + 9, edx
1164 hidnplayr 185
 
3200 hidnplayr 186
        invoke  ini.get_str, path, str_ipconfig, str_dns, inibuf, 16, 0
187
        mov     edx, inibuf
188
        call    Ip2dword
189
        mcall   76, API_IPv4 + 5, edx
1164 hidnplayr 190
 
3200 hidnplayr 191
        invoke  ini.get_str, path, str_ipconfig, str_subnet, inibuf, 16, 0
192
        mov     edx, inibuf
193
        call    Ip2dword
194
        mcall   76, API_IPv4 + 7, edx
1164 hidnplayr 195
 
196
 
3200 hidnplayr 197
        mcall   -1
1164 hidnplayr 198
 
199
 
3200 hidnplayr 200
try_dhcp:
1164 hidnplayr 201
 
3200 hidnplayr 202
        DEBUGF  1,"->Trying DHCP\n"
1164 hidnplayr 203
 
3200 hidnplayr 204
        mcall   75, 0, AF_INET4, SOCK_DGRAM, 0          ; open socket (parameters: domain, type, reserved)
205
        cmp     eax, -1
206
        je      error
207
        mov     [socketNum], eax
1164 hidnplayr 208
 
3200 hidnplayr 209
        DEBUGF  1,"->Socket %x opened\n", eax
1164 hidnplayr 210
 
3200 hidnplayr 211
        mcall   75, 2, [socketNum], sockaddr1, 18       ; bind socket to local port 68
212
        cmp     eax, -1
213
        je      error
1164 hidnplayr 214
 
2856 hidnplayr 215
        DEBUGF  1,"->Socket Bound to local port 68\n"
1164 hidnplayr 216
 
3200 hidnplayr 217
        mcall   75, 4, [socketNum], sockaddr2, 18       ; connect to 255.255.255.255 on port 67
218
        cmp     eax, -1
219
        je      error
1164 hidnplayr 220
 
2856 hidnplayr 221
        DEBUGF  1,"->Connected to 255.255.255.255 on port 67\n"
1164 hidnplayr 222
 
3200 hidnplayr 223
        mov     [dhcpMsgType], 0x01                     ; DHCP discover
224
        mov     [dhcpLease], esi                        ; esi is still -1 (-1 = forever)
1164 hidnplayr 225
 
3200 hidnplayr 226
        mcall   26, 9                                   ; Get system time
227
        imul    eax, 100
228
        mov     [currTime], eax
1164 hidnplayr 229
 
3200 hidnplayr 230
build_request:                                          ; Creates a DHCP request packet.
1164 hidnplayr 231
 
2856 hidnplayr 232
        DEBUGF  1,"->Building request\n"
1164 hidnplayr 233
 
2856 hidnplayr 234
        stdcall mem.Alloc, BUFFER
235
        mov     [dhcpMsg], eax
3200 hidnplayr 236
        test    eax, eax
2856 hidnplayr 237
        jz      apipa
1164 hidnplayr 238
 
2856 hidnplayr 239
            ;;; todo: skip this bullcrap
1164 hidnplayr 240
 
2856 hidnplayr 241
        mov     edi, eax
242
        mov     ecx, BUFFER
243
        xor     eax, eax
244
        rep     stosb
1164 hidnplayr 245
 
2856 hidnplayr 246
            ;; todo: put this in a buffer instead of writing bytes and words!
1164 hidnplayr 247
 
3200 hidnplayr 248
        mov     edx, [dhcpMsg]
1164 hidnplayr 249
 
2856 hidnplayr 250
        mov     [edx], byte 0x01                ; Boot request
251
        mov     [edx+1], byte 0x01              ; Ethernet
252
        mov     [edx+2], byte 0x06              ; Ethernet h/w len
253
        mov     [edx+4], dword 0x11223344       ; xid                 ;;;;;;;
3200 hidnplayr 254
        mov     eax, [currTime]
2856 hidnplayr 255
        mov     [edx+8], eax                    ; secs, our uptime
256
        mov     [edx+10], byte 0x80             ; broadcast flag set
257
        mov     eax, dword [MAC]                ; first 4 bytes of MAC
258
        mov     [edx+28],dword eax
259
        mov     ax, word [MAC+4]                ; last 2 bytes of MAC
260
        mov     [edx+32],word ax
261
        mov     [edx+236], dword 0x63538263     ; magic cookie
262
        mov     [edx+240], word 0x0135          ; option DHCP msg type
263
        mov     al, [dhcpMsgType]
264
        mov     [edx+240+2], al
265
        mov     [edx+240+3], word 0x0433        ; option Lease time = infinity
266
        mov     eax, [dhcpLease]
267
        mov     [edx+240+5], eax
268
        mov     [edx+240+9], word 0x0432        ; option requested IP address
2859 hidnplayr 269
        mov     eax, [dhcp.ip]
2856 hidnplayr 270
        mov     [edx+240+11], eax
271
        mov     [edx+240+15], word 0x0437       ; option request list
272
        mov     [edx+240+17], dword 0x0f060301
1164 hidnplayr 273
 
2856 hidnplayr 274
        cmp     [dhcpMsgType], byte 0x01        ; Check which msg we are sending
275
        jne     request_options
1164 hidnplayr 276
 
2856 hidnplayr 277
        mov     [edx+240+21], byte 0xff         ; "Discover" options
1164 hidnplayr 278
 
2856 hidnplayr 279
        mov     [dhcpMsgLen], dword 262         ; end of options marker
3200 hidnplayr 280
        jmp     send_dhcpmsg
1514 hidnplayr 281
 
1164 hidnplayr 282
request_options:
2856 hidnplayr 283
        mov     [edx+240+21], word 0x0436       ; server IP
284
        mov     eax, [dhcpServerIP]
285
        mov     [edx+240+23], eax
1164 hidnplayr 286
 
2856 hidnplayr 287
        mov     [edx+240+27], byte 0xff         ; end of options marker
1164 hidnplayr 288
 
2856 hidnplayr 289
        mov     [dhcpMsgLen], dword 268
1164 hidnplayr 290
 
3200 hidnplayr 291
send_dhcpmsg:
2856 hidnplayr 292
        mcall   75, 6, [socketNum], [dhcpMsg], [dhcpMsgLen]     ; write to socket ( send broadcast request )
1164 hidnplayr 293
 
2856 hidnplayr 294
        mov     eax, [dhcpMsg]                          ; Setup the DHCP buffer to receive response
295
        mov     [dhcpMsgLen], eax                       ; Used as a pointer to the data
1164 hidnplayr 296
 
2856 hidnplayr 297
        mcall   23, TIMEOUT*10                          ; wait for data
1164 hidnplayr 298
 
2856 hidnplayr 299
read_data:                                              ; we have data - this will be the response
300
        mcall   75, 7, [socketNum], [dhcpMsg], BUFFER   ; read data from socket
1164 hidnplayr 301
 
2856 hidnplayr 302
        DEBUGF  1,"->%d bytes received\n", eax
1164 hidnplayr 303
 
2856 hidnplayr 304
        cmp     eax, -1
305
        je      error
1164 hidnplayr 306
 
2856 hidnplayr 307
        mov     [dhcpMsgLen], eax
1164 hidnplayr 308
 
3200 hidnplayr 309
; depending on which msg we sent, handle the response
310
; accordingly.
311
; If the response is to a dhcp discover, then:
312
;  1) If response is DHCP OFFER then
313
;  1.1) record server IP, lease time & IP address.
314
;  1.2) send a request packet
315
; If the response is to a dhcp request, then:
316
;  1) If the response is DHCP ACK then
317
;  1.1) extract the DNS & subnet fields. Set them in the stack
1164 hidnplayr 318
 
3200 hidnplayr 319
        cmp     [dhcpMsgType], 0x01             ; did we send a discover?
320
        je      discover
1164 hidnplayr 321
 
3200 hidnplayr 322
        cmp     [dhcpMsgType], 0x03             ; did we send a request?
323
        je      request
1164 hidnplayr 324
 
3200 hidnplayr 325
        call    dhcp_end                        ; we should never reach here ;)
326
        jmp     exit
327
 
1164 hidnplayr 328
discover:
3200 hidnplayr 329
        call    parse_response
1164 hidnplayr 330
 
3200 hidnplayr 331
        cmp     [dhcpMsgType], 0x02             ; Was the response an offer?
332
        je      send_request
1164 hidnplayr 333
 
3200 hidnplayr 334
        call    dhcp_end
335
        jmp     link_local
336
 
337
send_request:
338
        mov     [dhcpMsgType], 0x03             ; make it a request
339
        jmp     build_request
340
 
1164 hidnplayr 341
request:
3200 hidnplayr 342
        call    parse_response
343
        call    dhcp_end
1164 hidnplayr 344
 
3200 hidnplayr 345
        cmp     [dhcpMsgType], 0x05             ; Was the response an ACK? It should be
346
        jne     link_local                      ; NO - so we do link-local
1164 hidnplayr 347
 
3200 hidnplayr 348
        mcall   76, API_IPv4 + 3, [dhcp.ip]             ; ip
349
        mcall   76, API_IPv4 + 5, [dhcp.dns]            ; dns
350
        mcall   76, API_IPv4 + 7, [dhcp.subnet]         ; subnet
351
        mcall   76, API_IPv4 + 9, [dhcp.gateway]        ; gateway
2859 hidnplayr 352
 
2856 hidnplayr 353
        jmp     exit
1164 hidnplayr 354
 
3200 hidnplayr 355
dhcp_end:
356
        mcall   close, [socketNum]
357
        stdcall mem.Free, [dhcpMsg]
358
 
359
        ret
360
 
1164 hidnplayr 361
;***************************************************************************
362
;   Function
363
;      parseResponse
364
;
365
;   Description
366
;      extracts the fields ( client IP address and options ) from
367
;      a DHCP response
368
;      The values go into
369
;       dhcpMsgType,dhcpLease,dhcpClientIP,dhcpServerIP,
370
;       dhcpDNSIP, dhcpSubnet
371
;      The message is stored in dhcpMsg
372
;
373
;***************************************************************************
3200 hidnplayr 374
parse_response:
1164 hidnplayr 375
 
3200 hidnplayr 376
        DEBUGF  1,"Data received, parsing response\n"
377
        mov     edx, [dhcpMsg]
1164 hidnplayr 378
 
3200 hidnplayr 379
        push    dword [edx+16]
380
        pop     [dhcp.ip]
381
        DEBUGF  1,"Client: %u.%u.%u.%u\n", [edx+16]:1, [edx+17]:1, [edx+18]:1, [edx+19]:1
1164 hidnplayr 382
 
3200 hidnplayr 383
; TODO: check if there really are options
1164 hidnplayr 384
 
3200 hidnplayr 385
        mov     al, 240                         ; Point to first option
386
        movzx   ecx, al
1164 hidnplayr 387
 
3200 hidnplayr 388
  .next_option:
389
        add     edx, ecx
2859 hidnplayr 390
 
3200 hidnplayr 391
        mov     al, [edx]                       ; get message identifier
2859 hidnplayr 392
 
3200 hidnplayr 393
        cmp     al, 0xff                        ; End of options?
394
        je      .done
1164 hidnplayr 395
 
3200 hidnplayr 396
        cmp     al, 0
397
        je      .pad
1164 hidnplayr 398
 
3200 hidnplayr 399
; TODO: check if we still are inside the buffer
1164 hidnplayr 400
 
3200 hidnplayr 401
        inc     edx
402
        movzx   ecx, byte [edx]                 ; get data length
403
        inc     edx                             ; point to data
1164 hidnplayr 404
 
3200 hidnplayr 405
        cmp     al, dhcp_msg_type               ; Msg type is a single byte option
406
        je      .msgtype
1164 hidnplayr 407
 
3200 hidnplayr 408
        cmp     al, dhcp_dhcp_server_id
409
        je      .server
1164 hidnplayr 410
 
3200 hidnplayr 411
        cmp     al, dhcp_address_time
412
        je      .lease
1164 hidnplayr 413
 
3200 hidnplayr 414
        cmp     al, dhcp_subnet_mask
415
        je      .subnet
1164 hidnplayr 416
 
3200 hidnplayr 417
        cmp     al, dhcp_router
418
        je      .router
1164 hidnplayr 419
 
3200 hidnplayr 420
        cmp     al, dhcp_domain_server
421
        je      .dns
1164 hidnplayr 422
 
3200 hidnplayr 423
        DEBUGF  1,"Unsupported DHCP option: %u\n", al
1164 hidnplayr 424
 
3200 hidnplayr 425
        jmp     .next_option
1164 hidnplayr 426
 
3200 hidnplayr 427
  .pad:
428
        xor     ecx, ecx
429
        inc     ecx
430
        jmp     .next_option
1164 hidnplayr 431
 
3200 hidnplayr 432
  .msgtype:
433
        mov     al, [edx]
434
        mov     [dhcpMsgType], al
1164 hidnplayr 435
 
3200 hidnplayr 436
        DEBUGF  1,"DHCP Msg type: %u\n", al
437
        jmp     .next_option                    ; Get next option
438
 
439
  .server:
440
        mov     eax, [edx]
441
        mov     [dhcpServerIP], eax
442
        DEBUGF  1,"Server: %u.%u.%u.%u\n",[edx]:1,[edx+1]:1,[edx+2]:1,[edx+3]:1
443
        jmp     .next_option
444
 
445
  .lease:
446
        pusha
447
        mov     eax,[edx]
448
        bswap   eax
449
        mov     [dhcpLease],eax
450
        DEBUGF  1,"lease: %d\n",eax
451
        popa
452
        jmp     .next_option
453
 
454
  .subnet:
455
        push    dword [edx]
456
        pop     [dhcp.subnet]
457
        DEBUGF  1,"Subnet: %u.%u.%u.%u\n",[edx]:1,[edx+1]:1,[edx+2]:1,[edx+3]:1
458
        jmp     .next_option
459
 
460
  .router:
461
        push    dword [edx]
462
        pop     [dhcp.gateway]
463
        DEBUGF  1,"Gateway: %u.%u.%u.%u\n",[edx]:1,[edx+1]:1,[edx+2]:1,[edx+3]:1
464
        jmp     .next_option
465
 
466
  .dns:
467
        push    dword [edx]
468
        pop     [dhcp.dns]
469
        DEBUGF  1,"DNS: %u.%u.%u.%u\n",[edx]:1,[edx+1]:1,[edx+2]:1,[edx+3]:1
470
        jmp     .next_option
471
 
472
  .done:
2856 hidnplayr 473
        ret
474
 
1164 hidnplayr 475
 
476
 
477
apipa:
2857 hidnplayr 478
        mcall   close, [socketNum]
479
        stdcall mem.Free, [dhcpMsg]
1164 hidnplayr 480
 
3200 hidnplayr 481
 
1164 hidnplayr 482
link_local:
3200 hidnplayr 483
        call    random
484
        mov     ecx, 0xfea9                             ; IP 169.254.0.0 link local net, see RFC3927
485
        mov     cx, ax
486
        mcall   76, API_IPv4 + 3, ecx                     ; mask is 255.255.0.0
487
        DEBUGF  1,"Link Local IP assinged: 169.254.%u.%u\n", [generator+2]:1, [generator+3]:1
488
        mcall   76, API_IPv4 + 5, 0xffff
489
        mcall   76, API_IPv4 + 9, 0x0
490
        mcall   76, API_IPv4 + 7, 0x0
1164 hidnplayr 491
 
3200 hidnplayr 492
        mcall   5, PROBE_WAIT*100
1164 hidnplayr 493
 
3200 hidnplayr 494
        xor     esi, esi
1164 hidnplayr 495
   probe_loop:
3200 hidnplayr 496
        call    random                                  ; create a pseudo random number in eax (seeded by MAC)
1164 hidnplayr 497
 
3200 hidnplayr 498
        cmp     al, PROBE_MIN*100                       ; check if al is bigger then PROBE_MIN
499
        jae     @f                                      ; all ok
500
        add     al, (PROBE_MAX-PROBE_MIN)*100           ; al is too small
1164 hidnplayr 501
   @@:
502
 
3200 hidnplayr 503
        cmp     al, PROBE_MAX*100
504
        jbe     @f
505
        sub     al, (PROBE_MAX-PROBE_MIN)*100
1164 hidnplayr 506
   @@:
507
 
3200 hidnplayr 508
        movzx   ebx,al
509
        DEBUGF  1,"Waiting %u0ms\n",ebx
510
        mcall   5
1164 hidnplayr 511
 
3200 hidnplayr 512
        DEBUGF  1,"Sending Probe\n"
513
        mcall   76, API_ARP + 6
514
        inc     esi
1164 hidnplayr 515
 
3200 hidnplayr 516
        cmp     esi, PROBE_NUM
517
        jb      probe_loop
1164 hidnplayr 518
 
519
; now we wait further ANNOUNCE_WAIT seconds and send ANNOUNCE_NUM ARP announces. If any other host has assingned
520
; IP within this time, we should create another adress, that have to be done later
521
 
3200 hidnplayr 522
        DEBUGF  1,"Waiting %us\n", ANNOUNCE_WAIT
523
        mcall   5, ANNOUNCE_WAIT*100
524
        xor   esi, esi
1164 hidnplayr 525
   announce_loop:
526
 
3200 hidnplayr 527
        DEBUGF  1,"Sending Announce\n"
528
        mcall   76, API_ARP + 6
1164 hidnplayr 529
 
3200 hidnplayr 530
        inc     esi
531
        cmp     esi,ANNOUNCE_NUM
532
        je      @f
1164 hidnplayr 533
 
3200 hidnplayr 534
        DEBUGF  1,"Waiting %us\n", ANNOUNCE_INTERVAL
535
        mcall   5, ANNOUNCE_INTERVAL*100
536
        jmp     announce_loop
1164 hidnplayr 537
   @@:
538
 
3200 hidnplayr 539
 
1164 hidnplayr 540
error:
3200 hidnplayr 541
        DEBUGF  1,"Socket error\n"
542
exit:   ; we should, instead of closing, detect ARP conflicts and detect if cable keeps connected ;)
543
        mcall   -1
1164 hidnplayr 544
 
545
 
546
random:  ; Pseudo random actually
547
 
3200 hidnplayr 548
        mov     eax, [generator]
549
        add     eax, -43ab45b5h
550
        ror     eax, 1
551
        bswap   eax
552
        xor     eax, dword[MAC]
553
        ror     eax, 1
554
        xor     eax, dword[MAC+2]
555
        mov     [generator], eax
1164 hidnplayr 556
 
3200 hidnplayr 557
        ret
1164 hidnplayr 558
 
559
; DATA AREA
560
 
561
align 16
562
@IMPORT:
563
 
564
library \
2856 hidnplayr 565
        libini,'libini.obj'
1164 hidnplayr 566
 
2856 hidnplayr 567
import  libini, \
568
        ini.get_str,'ini_get_str'
1164 hidnplayr 569
 
570
include_debug_strings
571
 
3200 hidnplayr 572
filename        db '.ini', 0
573
str_ip          db 'ip', 0
574
str_subnet      db 'subnet', 0
575
str_gateway     db 'gateway', 0
576
str_dns         db 'dns', 0
577
str_ipconfig    db 'ipconfig', 0
578
str_type        db 'type', 0
1164 hidnplayr 579
 
580
 
581
sockaddr1:
582
 
2856 hidnplayr 583
        dw AF_INET4
2995 hidnplayr 584
        dw 68 shl 8     ; local port
2856 hidnplayr 585
        dd 0            ; local IP
1164 hidnplayr 586
 
2856 hidnplayr 587
        rb 10
1164 hidnplayr 588
 
589
 
590
sockaddr2:
591
 
2856 hidnplayr 592
        dw AF_INET4
2995 hidnplayr 593
        dw 67 shl 8     ; destination port
2856 hidnplayr 594
        dd -1           ; destination IP
1164 hidnplayr 595
 
2856 hidnplayr 596
        rb 10
1164 hidnplayr 597
 
598
 
599
IM_END:
600
 
2856 hidnplayr 601
inibuf          rb 16
1164 hidnplayr 602
 
2856 hidnplayr 603
dhcpMsgType     db  ?
604
dhcpLease       dd  ?
605
dhcpServerIP    dd  ?
1164 hidnplayr 606
 
2859 hidnplayr 607
dhcp:
608
.ip             dd  ?
609
.subnet         dd  ?
610
.dns            dd  ?
611
.gateway        dd  ?
612
 
613
 
2856 hidnplayr 614
dhcpMsgLen      dd  ?
615
socketNum       dd  ?
1164 hidnplayr 616
 
2856 hidnplayr 617
MAC             dp  ?
1164 hidnplayr 618
 
2856 hidnplayr 619
currTime        dd  ?
620
generator       dd  ?
1164 hidnplayr 621
 
2856 hidnplayr 622
dhcpMsg         dd  ?
1164 hidnplayr 623
 
624
I_END_2:
625
 
2856 hidnplayr 626
path            rb  1024+5
1164 hidnplayr 627
 
2856 hidnplayr 628
                rb  65536
1542 hidnplayr 629
 
1164 hidnplayr 630
I_END: