Subversion Repositories Kolibri OS

Rev

Rev 4101 | Rev 4431 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 4101 Rev 4345
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
1
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
2
;;                                                                 ;;
2
;;                                                                 ;;
3
;; Copyright (C) KolibriOS team 2009-2013. All rights reserved.    ;;
3
;; Copyright (C) KolibriOS team 2009-2013. All rights reserved.    ;;
4
;; Distributed under terms of the GNU General Public License       ;;
4
;; Distributed under terms of the GNU General Public License       ;;
5
;;                                                                 ;;
5
;;                                                                 ;;
6
;;  downloader.asm - HTTP client for KolibriOS                     ;;
6
;;  downloader.asm - HTTP client for KolibriOS                     ;;
7
;;                                                                 ;;
7
;;                                                                 ;;
8
;;  Based on HTTPC.asm for menuetos by ville turjanmaa             ;;
8
;;  Based on HTTPC.asm for menuetos by ville turjanmaa             ;;
9
;;                                                                 ;;
9
;;                                                                 ;;
10
;;  Programmers: Barsuk, Clevermouse, Marat Zakiyanov,             ;;
10
;;  Programmers: Barsuk, Clevermouse, Marat Zakiyanov,             ;;
11
;;      Kirill Lipatov, dunkaist, HidnPlayr                        ;;
11
;;      Kirill Lipatov, dunkaist, HidnPlayr                        ;;
12
;;                                                                 ;;
12
;;                                                                 ;;
13
;;          GNU GENERAL PUBLIC LICENSE                             ;;
13
;;          GNU GENERAL PUBLIC LICENSE                             ;;
14
;;             Version 2, June 1991                                ;;
14
;;             Version 2, June 1991                                ;;
15
;;                                                                 ;;
15
;;                                                                 ;;
16
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
16
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
17
 
17
 
18
URLMAXLEN       = 1024
18
URLMAXLEN       = 1024
19
BUFFERSIZE      = 4096
19
BUFFERSIZE      = 4096
20
 
20
 
21
__DEBUG__       = 1
21
__DEBUG__       = 1
22
__DEBUG_LEVEL__ = 1
22
__DEBUG_LEVEL__ = 1
23
 
23
 
24
format binary as ""
24
format binary as ""
25
 
25
 
26
use32
26
use32
27
        org     0x0
27
        org     0x0
28
 
28
 
29
        db      'MENUET01'      ; header
29
        db      'MENUET01'      ; header
30
        dd      0x01            ; header version
30
        dd      0x01            ; header version
31
        dd      START           ; entry point
31
        dd      START           ; entry point
32
        dd      IM_END          ; image size
32
        dd      IM_END          ; image size
33
        dd      I_END+0x1000    ; required memory
33
        dd      I_END+0x1000    ; required memory
34
        dd      I_END+0x1000    ; esp
34
        dd      I_END+0x1000    ; esp
35
        dd      params          ; I_PARAM
35
        dd      params          ; I_PARAM
36
        dd      0x0             ; I_Path
36
        dd      0x0             ; I_Path
37
 
37
 
38
include '../../macros.inc'
38
include '../../macros.inc'
39
include '../../proc32.inc'
39
include '../../proc32.inc'
40
include '../../network.inc'
40
include '../../network.inc'
41
include '../../develop/libraries/box_lib/trunk/box_lib.mac'
41
include '../../develop/libraries/box_lib/trunk/box_lib.mac'
42
include '../../dll.inc'
42
include '../../dll.inc'
43
include '../../debug-fdo.inc'
43
include '../../debug-fdo.inc'
44
 
44
 
45
START:
45
START:
46
 
46
 
47
        mcall   68, 11                  ; init heap so we can allocate memory dynamically
47
        mcall   68, 11                  ; init heap so we can allocate memory dynamically
48
 
48
 
49
; load libraries
49
; load libraries
50
        stdcall dll.Load, @IMPORT
50
        stdcall dll.Load, @IMPORT
51
        test    eax, eax
51
        test    eax, eax
52
        jnz     exit
52
        jnz     exit
53
 
53
 
54
; prepare webAddr area
54
; prepare webAddr area
55
        mov     al, ' '
55
        mov     al, ' '
56
        mov     edi, webAddr
56
        mov     edi, webAddr
57
        mov     ecx, URLMAXLEN
57
        mov     ecx, URLMAXLEN
58
        rep     stosb
58
        rep     stosb
59
        xor     eax, eax
59
        xor     eax, eax
60
        stosb
60
        stosb
61
 
61
 
62
; prepare document area 
62
; prepare document area 
63
        mov     al, '/'
63
        mov     al, '/'
64
        mov     edi, document
64
        mov     edi, document
65
        stosb
65
        stosb
66
        mov     al, ' '
66
        mov     al, ' '
67
        mov     ecx, URLMAXLEN-1
67
        mov     ecx, URLMAXLEN-1
68
        rep     stosb
68
        rep     stosb
69
 
69
 
70
; load proxy settings
70
; load proxy settings
71
        invoke  ini.get_str, inifile, sec_proxy, key_proxy, proxyAddr, 256, proxyAddr
71
        invoke  ini.get_str, inifile, sec_proxy, key_proxy, proxyAddr, 256, proxyAddr
72
        invoke  ini.get_int, inifile, sec_proxy, key_proxyport, 80
72
        invoke  ini.get_int, inifile, sec_proxy, key_proxyport, 80
73
        mov     [proxyPort], eax
73
        mov     [proxyPort], eax
74
        invoke  ini.get_str, inifile, sec_proxy, key_user, proxyUser, 256, proxyUser
74
        invoke  ini.get_str, inifile, sec_proxy, key_user, proxyUser, 256, proxyUser
75
        invoke  ini.get_str, inifile, sec_proxy, key_password, proxyPassword, 256, proxyPassword
75
        invoke  ini.get_str, inifile, sec_proxy, key_password, proxyPassword, 256, proxyPassword
76
 
76
 
77
; check parameters
77
; check parameters
78
        cmp     byte[params], 0         ; no parameters ?
78
        cmp     byte[params], 0         ; no parameters ?
79
        je      reset_events            ; load the GUI
79
        je      reset_events            ; load the GUI
80
 
80
 
81
; we have an url, copy untill space or 0
81
; we have an url, copy untill space or 0
82
        mov     esi, params
82
        mov     esi, params
83
        mov     edi, document_user
83
        mov     edi, document_user
84
        mov     ecx, 1024               ; max parameter size
84
        mov     ecx, 1024               ; max parameter size
85
        mov     [shared_name], 0
85
        mov     [shared_name], 0
86
  .copy_param:
86
  .copy_param:
87
        lodsb
87
        lodsb
88
        test    al, al
88
        test    al, al
89
        jz      .done
89
        jz      .done
90
 
90
 
91
        cmp     al, ' '
91
        cmp     al, ' '
92
        jz      .done_with_shared
92
        jz      .done_with_shared
93
 
93
 
94
        stosb
94
        stosb
95
        dec     ecx
95
        dec     ecx
96
        jnz     .copy_param
96
        jnz     .copy_param
97
        DEBUGF  2, "Invalid parameters\n"
97
        DEBUGF  2, "Invalid parameters\n"
98
        jmp     exit
98
        jmp     exit
99
 
99
 
100
  .done_with_shared:
100
  .done_with_shared:
101
        mov     [shared_name], esi
101
        mov     [shared_name], esi
102
  .done:
102
  .done:
103
        xor     al, al
103
        xor     al, al
104
        stosb
104
        stosb
105
 
105
 
106
 
106
 
107
download:
107
download:
108
 
108
 
109
        DEBUGF  1, "Starting download\n"
109
        DEBUGF  1, "Starting download\n"
110
 
110
 
111
        call    parse_url
111
        call    parse_url
112
 
112
 
113
        cmp     [server_ip], 0
113
        cmp     [server_ip], 0
114
        je      dns_error
114
        je      dns_error
115
 
115
 
116
        call    open_socket
116
        call    open_socket
117
        call    send_request
117
        call    send_request
118
 
118
 
119
        mcall   68, 12, BUFFERSIZE      ; create buffer, we'll resize it later if needed..
119
        mcall   68, 12, BUFFERSIZE      ; create buffer, we'll resize it later if needed..
120
        mov     [buf_ptr], eax
120
        mov     [buf_ptr], eax
121
        mov     [buf_size], 0
121
        mov     [buf_size], 0
122
 
122
 
123
        call    read_incoming_data
123
        call    read_incoming_data
124
 
124
 
125
        mcall   close, [socketnum]
125
        mcall   close, [socketnum]
126
 
126
 
127
        call    parse_result
127
        call    parse_result
128
        call    save
128
        call    save
129
 
129
 
130
        mcall   68, 13, [final_buffer]  ; free buffer
130
        mcall   68, 13, [final_buffer]  ; free buffer
131
 
131
 
132
dns_error:
132
dns_error:
133
        cmp     byte [params], 0
133
        cmp     byte [params], 0
134
        jne     exit
134
        jne     exit
135
 
135
 
136
reset_events:
136
reset_events:
137
 
137
 
138
        DEBUGF  1, "resetting events\n"
138
        DEBUGF  1, "resetting events\n"
139
 
139
 
140
; Report events
140
; Report events
141
; defaults + mouse
141
; defaults + mouse
142
        mcall   40,EVM_REDRAW+EVM_KEY+EVM_BUTTON+EVM_MOUSE+EVM_MOUSE_FILTER
142
        mcall   40,EVM_REDRAW+EVM_KEY+EVM_BUTTON+EVM_MOUSE+EVM_MOUSE_FILTER
143
 
143
 
144
redraw:
144
redraw:
145
        call    draw_window
145
        call    draw_window
146
 
146
 
147
still:
147
still:
148
        DEBUGF  1, "waiting for events\n"
148
        DEBUGF  1, "waiting for events\n"
149
 
149
 
150
        mcall   10      ; wait here for event
150
        mcall   10      ; wait here for event
151
 
151
 
152
        cmp     eax, EV_REDRAW
152
        cmp     eax, EV_REDRAW
153
        je      redraw
153
        je      redraw
154
 
154
 
155
        cmp     eax, EV_KEY
155
        cmp     eax, EV_KEY
156
        je      key
156
        je      key
157
 
157
 
158
        cmp     eax, EV_BUTTON
158
        cmp     eax, EV_BUTTON
159
        je      button
159
        je      button
160
        
160
        
161
        cmp     eax, EV_MOUSE
161
        cmp     eax, EV_MOUSE
162
        je      mouse
162
        je      mouse
163
 
163
 
164
        jmp     still
164
        jmp     still
165
 
165
 
166
key:
166
key:
167
        mcall   2       ; read key
167
        mcall   2       ; read key
168
 
168
 
169
        stdcall [edit_box_key], dword edit1
169
        stdcall [edit_box_key], dword edit1
170
 
170
 
171
        cmp     ax, 13 shl 8
171
        cmp     ax, 13 shl 8
172
        je      download
172
        je      download
173
        
173
        
174
        jmp     still
174
        jmp     still
175
        
175
        
176
button:
176
button:
177
 
177
 
178
        mcall   17      ; get id
178
        mcall   17      ; get id
179
 
179
 
180
        cmp     ah, 26
180
        cmp     ah, 26
181
        jne     @f
181
        jne     @f
182
        call    save_to_file
182
        call    save_to_file
183
        jmp     still
183
        jmp     still
184
  @@:
184
  @@:
185
        cmp     ah, 1   ; button id=1 ?
185
        cmp     ah, 1   ; button id=1 ?
186
        je      exit
186
        je      exit
187
 
187
 
188
        jmp     download
188
        jmp     download
189
 
189
 
190
mouse:
190
mouse:
191
        stdcall [edit_box_mouse], edit1
191
        stdcall [edit_box_mouse], edit1
192
        jmp     still
192
        jmp     still
193
 
193
 
194
exit:
194
exit:
195
        DEBUGF  1, "Exiting\n"
195
        DEBUGF  1, "Exiting\n"
196
        or      eax, -1 ; close this program
196
        or      eax, -1 ; close this program
197
        mcall
197
        mcall
198
 
198
 
199
 
199
 
200
save:
200
save:
201
        cmp     [shared_name], 0
201
        cmp     [shared_name], 0
202
        je      .use_file
202
        je      .use_file
203
 
203
 
204
        call    save_in_shared
204
        call    save_in_shared
205
        jmp     .done
205
        jmp     .done
206
 
206
 
207
  .use_file:
207
  .use_file:
208
 
208
 
209
        call    save_to_file
209
        call    save_to_file
210
 
210
 
211
  .done:
211
  .done:
212
 
212
 
213
; if called from command line, then exit
213
; if called from command line, then exit
214
        cmp     byte[params], 0
214
        cmp     byte[params], 0
215
        jne     exit
215
        jne     exit
216
 
216
 
217
        mov     ecx, [sc.work_text]
217
        mov     ecx, [sc.work_text]
218
        or      ecx, 0x80000000
218
        or      ecx, 0x80000000
219
        mcall   4, <10, 93>, , download_complete
219
        mcall   4, <10, 93>, , download_complete
220
 
220
 
221
        ret
221
        ret
222
 
222
 
223
save_in_shared:
223
save_in_shared:
224
 
224
 
225
; open the shared memory area
225
; open the shared memory area
226
        mov     esi, 1
226
        mov     esi, 1
227
        mcall   68, 22, [shared_name], , 1 ; SHM_OPEN+SHM_WRITE
227
        mcall   68, 22, [shared_name], , 1 ; SHM_OPEN+SHM_WRITE
228
        test    eax, eax
228
        test    eax, eax
229
        jz      exit
229
        jz      exit
230
 
230
 
231
        mov     ecx, [final_size]
231
        mov     ecx, [final_size]
232
; store the size
232
; store the size
233
        mov     [eax], ecx
233
        mov     [eax], ecx
234
 
234
 
235
; now copy the data
235
; now copy the data
236
        lea     edi, [eax+4]
236
        lea     edi, [eax+4]
237
        mov     esi, [final_buffer]
237
        mov     esi, [final_buffer]
238
        mov     eax, ecx
238
        mov     eax, ecx
239
        shr     ecx, 2
239
        shr     ecx, 2
240
        rep     movsd
240
        rep     movsd
241
        mov     ecx, eax
241
        mov     ecx, eax
242
        and     ecx, 3
242
        and     ecx, 3
243
        rep     movsb
243
        rep     movsb
244
 
244
 
245
        ret
245
        ret
246
 
246
 
247
 
247
 
248
;****************************************************************************
248
;****************************************************************************
249
;    Function
249
;    Function
250
;       save_to_file
250
;       save_to_file
251
;
251
;
252
;   Description
252
;   Description
253
;
253
;
254
;
254
;
255
;****************************************************************************
255
;****************************************************************************
256
 
256
 
257
save_to_file:
257
save_to_file:
258
 
258
 
259
        DEBUGF  2, "Saving to file\n"
259
        DEBUGF  2, "Saving to file\n"
260
        mcall   70, fileinfo
260
        mcall   70, fileinfo
261
 
261
 
262
        ret
262
        ret
263
 
263
 
264
 
264
 
265
;****************************************************************************
265
;****************************************************************************
266
;    Function
266
;    Function
267
;       send_request
267
;       send_request
268
;
268
;
269
;   Description
269
;   Description
270
;       Transmits the GET request to the server.
270
;       Transmits the GET request to the server.
271
;       This is done as GET then URL then HTTP/1.1', 13, 10, 13, 10 in 3 packets
271
;       This is done as GET then URL then HTTP/1.1', 13, 10, 13, 10 in 3 packets
272
;
272
;
273
;****************************************************************************
273
;****************************************************************************
274
send_request:
274
send_request:
275
 
275
 
276
        DEBUGF  1, "Sending request\n"
276
        DEBUGF  1, "Sending request\n"
277
 
277
 
278
        mov     esi, string0
278
        mov     esi, string0
279
        mov     edi, request
279
        mov     edi, request
280
        movsd
280
        movsd
281
; If proxy is used, make absolute URI - prepend http://
281
; If proxy is used, make absolute URI - prepend http://
282
        cmp     byte[proxyAddr], 0
282
        cmp     byte[proxyAddr], 0
283
        jz      .noproxy
283
        jz      .noproxy
284
        mov     dword[edi], 'http'
284
        mov     dword[edi], 'http'
285
        mov     byte[edi+4], ':'
285
        mov     byte[edi+4], ':'
286
        mov     word[edi+5], '//'
286
        mov     word[edi+5], '//'
287
        add     edi, 7
287
        add     edi, 7
288
        mov     esi, webAddr
288
        mov     esi, webAddr
289
 
289
 
290
  .copy_host_loop:
290
  .copy_host_loop:
291
        lodsb
291
        lodsb
292
        cmp     al, ' '
292
        cmp     al, ' '
293
        jz      .noproxy
293
        jz      .noproxy
294
        stosb
294
        stosb
295
        jmp     .copy_host_loop
295
        jmp     .copy_host_loop
296
 
296
 
297
  .noproxy:
297
  .noproxy:
298
        xor     edx, edx ; 0
298
        xor     edx, edx ; 0
299
 
299
 
300
  .next_edx:
300
  .next_edx:
301
; Determine the length of the url to send in the GET request
301
; Determine the length of the url to send in the GET request
302
        mov     al, [edx+document]
302
        mov     al, [edx+document]
303
        cmp     al, ' '
303
        cmp     al, ' '
304
        jbe     .document_done
304
        jbe     .document_done
305
        mov     [edi], al
305
        mov     [edi], al
306
        inc     edi
306
        inc     edi
307
        inc     edx
307
        inc     edx
308
        jmp     .next_edx
308
        jmp     .next_edx
309
 
309
 
310
  .document_done:
310
  .document_done:
311
        mov     esi, stringh
311
        mov     esi, stringh
312
        mov     ecx, stringh_end-stringh
312
        mov     ecx, stringh_end-stringh
313
        rep     movsb
313
        rep     movsb
314
        xor     edx, edx ; 0
314
        xor     edx, edx ; 0
315
 
315
 
316
  .webaddr_next:
316
  .webaddr_next:
317
        mov     al, [webAddr + edx]
317
        mov     al, [webAddr + edx]
318
        cmp     al, ' '
318
        cmp     al, ' '
319
        jbe     .webaddr_done
319
        jbe     .webaddr_done
320
        mov     [edi], al
320
        mov     [edi], al
321
        inc     edi
321
        inc     edi
322
        inc     edx
322
        inc     edx
323
        jmp     .webaddr_next
323
        jmp     .webaddr_next
324
 
324
 
325
  .webaddr_done:
325
  .webaddr_done:
326
        cmp     byte[proxyUser], 0
326
        cmp     byte[proxyUser], 0
327
        jz      @f
327
        jz      @f
328
        call    append_proxy_auth_header
328
        call    append_proxy_auth_header
329
    @@:
329
    @@:
330
        mov     esi, connclose
330
        mov     esi, connclose
331
        mov     ecx, connclose_end-connclose
331
        mov     ecx, connclose_end-connclose
332
        rep     movsb
332
        rep     movsb
333
 
333
 
334
        pusha   
334
        pusha   
335
        mov     eax, 63
335
        mov     eax, 63
336
        mov     ebx, 1
336
        mov     ebx, 1
337
        mov     edx, request
337
        mov     edx, request
338
    @@:
338
    @@:
339
        mov     cl, [edx]
339
        mov     cl, [edx]
340
        cmp     edx, edi
340
        cmp     edx, edi
341
        jz      @f
341
        jz      @f
342
        mcall
342
        mcall
343
        inc     edx
343
        inc     edx
344
        jmp     @b
344
        jmp     @b
345
    @@:
345
    @@:
346
        popa
346
        popa
347
 
347
 
348
        mov     esi, edi
348
        mov     esi, edi
349
        sub     esi, request    ; length
349
        sub     esi, request    ; length
350
        xor     edi, edi        ; flags
350
        xor     edi, edi        ; flags
351
        mcall   send, [socketnum], request  ;' HTTP/1.1 .. '
351
        mcall   send, [socketnum], request  ;' HTTP/1.1 .. '
352
 
352
 
353
        ret
353
        ret
354
 
354
 
355
;****************************************************************************
355
;****************************************************************************
356
;    Function
356
;    Function
357
;       read_incoming_data
357
;       read_incoming_data
358
;
358
;
359
;   Description
359
;   Description
360
;       receive the web page from the server, storing it without processing
360
;       receive the web page from the server, storing it without processing
361
;
361
;
362
;****************************************************************************
362
;****************************************************************************
363
read_incoming_data:
363
read_incoming_data:
364
 
364
 
365
        DEBUGF  1, "Reading incoming data\n"
365
        DEBUGF  1, "Reading incoming data\n"
366
 
366
 
367
        mov     eax, [buf_ptr]
367
        mov     eax, [buf_ptr]
368
        mov     [pos], eax
368
        mov     [pos], eax
369
  .read:
369
  .read:
370
        mcall   recv, [socketnum], [pos], BUFFERSIZE, 0
370
        mcall   recv, [socketnum], [pos], BUFFERSIZE, 0
371
        inc     eax             ; -1 = error (socket closed?)
371
        inc     eax             ; -1 = error (socket closed?)
-
 
372
        jz      .error
-
 
373
        dec     eax             ; 0 bytes means the remote end closed the connection
372
        jz      .no_more_data
374
        jz      .no_more_data
373
        dec     eax             ; 0 bytes...
-
 
374
        jz      .read
-
 
375
 
375
 
376
        DEBUGF  1, "Got chunk of %u bytes\n", eax
376
        DEBUGF  1, "Got chunk of %u bytes\n", eax
377
 
377
 
378
        add     [buf_size], eax
378
        add     [buf_size], eax
379
        add     [pos], eax
379
        add     [pos], eax
380
        push    eax
380
        push    eax
381
        mov     ecx, [buf_size]
381
        mov     ecx, [buf_size]
382
        add     ecx, BUFFERSIZE
382
        add     ecx, BUFFERSIZE
383
        mcall   68, 20, , [buf_ptr]     ; reallocate memory block (make bigger)
383
        mcall   68, 20, , [buf_ptr]     ; reallocate memory block (make bigger)
384
        ; TODO: parse header and resize buffer only once
384
        ; TODO: parse header and resize buffer only once
385
        pop     eax
385
        pop     eax
386
        jmp     .read
386
        jmp     .read
-
 
387
 
-
 
388
  .error:
-
 
389
        DEBUGF  1, "Socket error: %u\n", ebx
387
        
390
        
388
  .no_more_data:
391
  .no_more_data:
389
        mov     eax, [buf_ptr]
392
        mov     eax, [buf_ptr]
390
        sub     [pos], eax
393
        sub     [pos], eax
391
 
394
 
392
        DEBUGF  1, "No more data\n"
395
        DEBUGF  1, "No more data\n"
393
 
396
 
394
        ret
397
        ret
395
        
398
        
396
 
399
 
397
        
400
        
398
; this function cuts header, and removes chunk sizes if doc is chunked
401
; this function cuts header, and removes chunk sizes if doc is chunked
399
; in: buf_ptr, pos; out: buf_ptr, pos.
402
; in: buf_ptr, pos; out: buf_ptr, pos.
400
        
403
        
401
parse_result:
404
parse_result:
402
 
405
 
403
        mov     edi, [buf_ptr]
406
        mov     edi, [buf_ptr]
404
        mov     edx, [pos]
407
        mov     edx, [pos]
405
;        mov     [buf_size], edx
408
;        mov     [buf_size], edx
406
;       mcall   70, fileinfo_tmp
409
;       mcall   70, fileinfo_tmp
407
        DEBUGF  1, "Parsing result (%u bytes)\n", edx
410
        DEBUGF  1, "Parsing result (%u bytes)\n", edx
408
 
411
 
409
; first, find end of headers
412
; first, find end of headers
410
  .next_byte:
413
  .next_byte:
411
        cmp     dword[edi], 0x0a0d0a0d
414
        cmp     dword[edi], 0x0a0d0a0d
412
        je      .end_of_headers
415
        je      .end_of_headers
413
        inc     edi
416
        inc     edi
414
        dec     edx
417
        dec     edx
415
        ja      .next_byte
418
        ja      .next_byte
416
        DEBUGF  1, "Uh-oh, there's no end of header!\n"
419
        DEBUGF  1, "Uh-oh, there's no end of header!\n"
417
; no end of headers. it's an error. let client see all those headers.
420
; no end of headers. it's an error. let client see all those headers.
418
        ret
421
        ret
419
 
422
 
420
  .end_of_headers:
423
  .end_of_headers:
421
; here we look at headers and search content-length or transfer-encoding headers
424
; here we look at headers and search content-length or transfer-encoding headers
422
        DEBUGF  1, "Found end of header\n"
425
        DEBUGF  1, "Found end of header\n"
423
 
426
 
424
        sub     edi, [buf_ptr]
427
        sub     edi, [buf_ptr]
425
        add     edi, 4
428
        add     edi, 4
426
        mov     [body_pos], edi  ; store position where document body starts
429
        mov     [body_pos], edi  ; store position where document body starts
427
        mov     [is_chunked], 0
430
        mov     [is_chunked], 0
428
; find content-length in headers
431
; find content-length in headers
429
; not good method, but should work for 'Content-Length:'
432
; not good method, but should work for 'Content-Length:'
430
        mov     esi, [buf_ptr]
433
        mov     esi, [buf_ptr]
431
        mov     edi, s_contentlength
434
        mov     edi, s_contentlength
432
        mov     ebx, [body_pos]
435
        mov     ebx, [body_pos]
433
        xor     edx, edx ; 0
436
        xor     edx, edx ; 0
434
  .cl_next:
437
  .cl_next:
435
        mov     al, [esi]
438
        mov     al, [esi]
436
        cmp     al, [edi + edx]
439
        cmp     al, [edi + edx]
437
        jne     .cl_fail
440
        jne     .cl_fail
438
        inc     edx
441
        inc     edx
439
        cmp     edx, len_contentlength
442
        cmp     edx, len_contentlength
440
        je      .cl_found
443
        je      .cl_found
441
        jmp     .cl_incr
444
        jmp     .cl_incr
442
  .cl_fail:
445
  .cl_fail:
443
        xor     edx, edx ; 0
446
        xor     edx, edx ; 0
444
  .cl_incr:
447
  .cl_incr:
445
        inc     esi
448
        inc     esi
446
        dec     ebx
449
        dec     ebx
447
        je      .cl_error
450
        je      .cl_error
448
        jmp     .cl_next
451
        jmp     .cl_next
449
  .cl_error:
452
  .cl_error:
450
        DEBUGF  1, "content-length not found\n"
453
        DEBUGF  1, "content-length not found\n"
451
 
454
 
452
; find 'chunked'
455
; find 'chunked'
453
; äà, ÿ êîïèðóþ êîä, ýòî óæàñíî, íî ìíå õî÷åòñÿ, ÷òîáû ïîñêîðåå çàðàáîòàëî
456
; äà, ÿ êîïèðóþ êîä, ýòî óæàñíî, íî ìíå õî÷åòñÿ, ÷òîáû ïîñêîðåå çàðàáîòàëî
454
; à òàì óæ îòðåôàêòîðþ
457
; à òàì óæ îòðåôàêòîðþ
455
        mov     esi, [buf_ptr]
458
        mov     esi, [buf_ptr]
456
        mov     edi, s_chunked
459
        mov     edi, s_chunked
457
        mov     ebx, [body_pos]
460
        mov     ebx, [body_pos]
458
        xor     edx, edx ; 0
461
        xor     edx, edx ; 0
459
 
462
 
460
  .ch_next:
463
  .ch_next:
461
        mov     al, [esi]
464
        mov     al, [esi]
462
        cmp     al, [edi + edx]
465
        cmp     al, [edi + edx]
463
        jne     .ch_fail
466
        jne     .ch_fail
464
        inc     edx
467
        inc     edx
465
        cmp     edx, len_chunked
468
        cmp     edx, len_chunked
466
        je      .ch_found
469
        je      .ch_found
467
        jmp     .ch_incr
470
        jmp     .ch_incr
468
 
471
 
469
  .ch_fail:
472
  .ch_fail:
470
        xor     edx, edx ; 0
473
        xor     edx, edx ; 0
471
 
474
 
472
  .ch_incr:
475
  .ch_incr:
473
        inc     esi
476
        inc     esi
474
        dec     ebx
477
        dec     ebx
475
        je      .ch_error
478
        je      .ch_error
476
        jmp     .ch_next
479
        jmp     .ch_next
477
 
480
 
478
  .ch_error:
481
  .ch_error:
479
; if neither of the 2 headers is found, it's an error
482
; if neither of the 2 headers is found, it's an error
480
;       DEBUGF  1, "transfer-encoding: chunked not found\n"
483
;       DEBUGF  1, "transfer-encoding: chunked not found\n"
481
        mov     eax, [pos]
484
        mov     eax, [pos]
482
        sub     eax, [body_pos]
485
        sub     eax, [body_pos]
483
        jmp     .write_final_size
486
        jmp     .write_final_size
484
 
487
 
485
  .ch_found:
488
  .ch_found:
486
        mov     [is_chunked], 1
489
        mov     [is_chunked], 1
487
        mov     eax, [body_pos]
490
        mov     eax, [body_pos]
488
        add     eax, [buf_ptr]
491
        add     eax, [buf_ptr]
489
        sub     eax, 2
492
        sub     eax, 2
490
        mov     [prev_chunk_end], eax
493
        mov     [prev_chunk_end], eax
491
        jmp     parse_chunks
494
        jmp     parse_chunks
492
        
495
        
493
  .cl_found:
496
  .cl_found:
494
        call    read_number     ; eax = number from *esi
497
        call    read_number     ; eax = number from *esi
495
        DEBUGF  1, "Content length: %u\n", eax
498
        DEBUGF  1, "Content length: %u\n", eax
496
 
499
 
497
  .write_final_size:
500
  .write_final_size:
498
        
501
        
499
        mov     ebx, [buf_size]
502
        mov     ebx, [buf_size]
500
        sub     ebx, [body_pos]
503
        sub     ebx, [body_pos]
501
        cmp     eax, ebx
504
        cmp     eax, ebx
502
        jbe     .size_ok
505
        jbe     .size_ok
503
        sub     eax, ebx
506
        sub     eax, ebx
504
        DEBUGF  2, "%u bytes of data are missing!\n", eax
507
        DEBUGF  2, "%u bytes of data are missing!\n", eax
505
        mov     eax, ebx
508
        mov     eax, ebx
506
  .size_ok:
509
  .size_ok:
507
        mov     [final_size], eax
510
        mov     [final_size], eax
508
 
511
 
509
        mov     ebx, [body_pos]
512
        mov     ebx, [body_pos]
510
        add     ebx, [buf_ptr]
513
        add     ebx, [buf_ptr]
511
        mov     [final_buffer], ebx
514
        mov     [final_buffer], ebx
512
 
515
 
513
        ret
516
        ret
514
        
517
        
515
parse_chunks:
518
parse_chunks:
516
        DEBUGF  1, "parse chunks\n"
519
        DEBUGF  1, "parse chunks\n"
517
        ; we have to look through the data and remove sizes of chunks we see
520
        ; we have to look through the data and remove sizes of chunks we see
518
        ; 1. read size of next chunk
521
        ; 1. read size of next chunk
519
        ; 2. if 0, it's end. if not, continue.
522
        ; 2. if 0, it's end. if not, continue.
520
        ; 3. make a good buffer and copy a chunk there
523
        ; 3. make a good buffer and copy a chunk there
521
        xor     eax, eax
524
        xor     eax, eax
522
        mov     [final_buffer], eax      ; 0
525
        mov     [final_buffer], eax      ; 0
523
        mov     [final_size], eax        ; 0
526
        mov     [final_size], eax        ; 0
524
        
527
        
525
.read_size:
528
.read_size:
526
        mov     eax, [prev_chunk_end]
529
        mov     eax, [prev_chunk_end]
527
        mov     ebx, eax
530
        mov     ebx, eax
528
        sub     ebx, [buf_ptr]
531
        sub     ebx, [buf_ptr]
529
        mov     edx, eax
532
        mov     edx, eax
530
        DEBUGF  1, "rs "
533
        DEBUGF  1, "rs "
531
        cmp     ebx, [pos]
534
        cmp     ebx, [pos]
532
        jae     chunks_end      ; not good
535
        jae     chunks_end      ; not good
533
        
536
        
534
        call    read_hex        ; in: eax=pointer to text. out:eax=hex number, ebx=end of text.
537
        call    read_hex        ; in: eax=pointer to text. out:eax=hex number, ebx=end of text.
535
        cmp     eax, 0
538
        cmp     eax, 0
536
        jz      chunks_end
539
        jz      chunks_end
537
 
540
 
538
        add     ebx, 1
541
        add     ebx, 1
539
        mov     edx, ebx ; edx = size of size of chunk
542
        mov     edx, ebx ; edx = size of size of chunk
540
        
543
        
541
        add     ebx, eax
544
        add     ebx, eax
542
        mov     [prev_chunk_end], ebx
545
        mov     [prev_chunk_end], ebx
543
        
546
        
544
        DEBUGF  1, "sz "
547
        DEBUGF  1, "sz "
545
 
548
 
546
; do copying: from buf_ptr+edx to final_buffer+prev_final_size count eax
549
; do copying: from buf_ptr+edx to final_buffer+prev_final_size count eax
547
; realloc final buffer
550
; realloc final buffer
548
        push    eax
551
        push    eax
549
        push    edx
552
        push    edx
550
        push    dword [final_size]
553
        push    dword [final_size]
551
        add     [final_size], eax
554
        add     [final_size], eax
552
        mcall   68, 20, [final_size], [final_buffer]
555
        mcall   68, 20, [final_size], [final_buffer]
553
        mov     [final_buffer], eax
556
        mov     [final_buffer], eax
554
        DEBUGF  1, "re "
557
        DEBUGF  1, "re "
555
        pop     edi
558
        pop     edi
556
        pop     esi
559
        pop     esi
557
        pop     ecx
560
        pop     ecx
558
;       add     [pos], ecx
561
;       add     [pos], ecx
559
        add     edi, [final_buffer]
562
        add     edi, [final_buffer]
560
        DEBUGF  1, "cp "
563
        DEBUGF  1, "cp "
561
 
564
 
562
        rep     movsb
565
        rep     movsb
563
        jmp     .read_size
566
        jmp     .read_size
564
        
567
        
565
chunks_end:
568
chunks_end:
566
        DEBUGF  1, "chunks end\n"
569
        DEBUGF  1, "chunks end\n"
567
        mcall   68, 13, [buf_ptr]       ; free old buffer
570
        mcall   68, 13, [buf_ptr]       ; free old buffer
568
 
571
 
569
        ret
572
        ret
570
 
573
 
571
; reads content-length from [edi+ecx], result in eax
574
; reads content-length from [edi+ecx], result in eax
572
read_number:
575
read_number:
573
        push    ebx
576
        push    ebx
574
        xor     eax, eax
577
        xor     eax, eax
575
        xor     ebx, ebx
578
        xor     ebx, ebx
576
 
579
 
577
  .next:
580
  .next:
578
        mov     bl, [esi]
581
        mov     bl, [esi]
579
 
582
 
580
        cmp     bl, '0'
583
        cmp     bl, '0'
581
        jb      .not_number
584
        jb      .not_number
582
        cmp     bl, '9'
585
        cmp     bl, '9'
583
        ja      .not_number
586
        ja      .not_number
584
        sub     bl, '0'
587
        sub     bl, '0'
585
        shl     eax, 1
588
        shl     eax, 1
586
        lea     eax, [eax + eax * 4]     ; eax *= 10
589
        lea     eax, [eax + eax * 4]     ; eax *= 10
587
        add     eax, ebx
590
        add     eax, ebx
588
 
591
 
589
  .not_number:
592
  .not_number:
590
        cmp     bl, 13
593
        cmp     bl, 13
591
        je      .done
594
        je      .done
592
        inc     esi
595
        inc     esi
593
        jmp     .next
596
        jmp     .next
594
 
597
 
595
  .done:
598
  .done:
596
        pop     ebx
599
        pop     ebx
597
        ret
600
        ret
598
        
601
        
599
; reads hex from eax, result in eax, end of text in ebx
602
; reads hex from eax, result in eax, end of text in ebx
600
read_hex:
603
read_hex:
601
        add     eax, 2
604
        add     eax, 2
602
        mov     ebx, eax
605
        mov     ebx, eax
603
        mov     eax, [ebx]
606
        mov     eax, [ebx]
604
        mov     [deba], eax
607
        mov     [deba], eax
605
 
608
 
606
        xor     eax, eax
609
        xor     eax, eax
607
        xor     ecx, ecx
610
        xor     ecx, ecx
608
  .next:
611
  .next:
609
        mov     cl, [ebx]
612
        mov     cl, [ebx]
610
        inc     ebx
613
        inc     ebx
611
        
614
        
612
        cmp     cl, 0x0d
615
        cmp     cl, 0x0d
613
        jz      .done
616
        jz      .done
614
 
617
 
615
        or      cl, 0x20
618
        or      cl, 0x20
616
        sub     cl, '0'
619
        sub     cl, '0'
617
        jb      .bad
620
        jb      .bad
618
 
621
 
619
        cmp     cl, 0x9
622
        cmp     cl, 0x9
620
        jbe     .adding
623
        jbe     .adding
621
 
624
 
622
        sub     cl, 'a'-'0'-10
625
        sub     cl, 'a'-'0'-10
623
        cmp     cl, 0x0a
626
        cmp     cl, 0x0a
624
        jb      .bad
627
        jb      .bad
625
 
628
 
626
        cmp     cl, 0x0f
629
        cmp     cl, 0x0f
627
        ja      .bad
630
        ja      .bad
628
 
631
 
629
  .adding:
632
  .adding:
630
        shl     eax, 4
633
        shl     eax, 4
631
        or      eax, ecx
634
        or      eax, ecx
632
  .bad:
635
  .bad:
633
        jmp     .next
636
        jmp     .next
634
  .done:
637
  .done:
635
 
638
 
636
        ret
639
        ret
637
 
640
 
638
;****************************************************************************
641
;****************************************************************************
639
;    Function
642
;    Function
640
;       open_socket
643
;       open_socket
641
;
644
;
642
;   Description
645
;   Description
643
;       opens the socket
646
;       opens the socket
644
;
647
;
645
;****************************************************************************
648
;****************************************************************************
646
open_socket:
649
open_socket:
647
 
650
 
648
        DEBUGF  1, "opening socket\n"
651
        DEBUGF  1, "opening socket\n"
649
 
652
 
650
        mov     edx, 80
653
        mov     edx, 80
651
        cmp     byte [proxyAddr], 0
654
        cmp     byte [proxyAddr], 0
652
        jz      @f
655
        jz      @f
653
        mov     eax, [proxyPort]
656
        mov     eax, [proxyPort]
654
        xchg    al, ah
657
        xchg    al, ah
655
        mov     [server_port], ax
658
        mov     [server_port], ax
656
    @@:
659
    @@:
657
 
660
 
658
        mcall   socket, AF_INET4, SOCK_STREAM, 0
661
        mcall   socket, AF_INET4, SOCK_STREAM, 0
659
        mov     [socketnum], eax
662
        mov     [socketnum], eax
660
        mcall   connect, [socketnum], sockaddr1, 18
663
        mcall   connect, [socketnum], sockaddr1, 18
661
 
664
 
662
        ret
665
        ret
663
 
666
 
664
 
667
 
665
;****************************************************************************
668
;****************************************************************************
666
;    Function
669
;    Function
667
;       parse_url
670
;       parse_url
668
;
671
;
669
;   Description
672
;   Description
670
;       parses the full url typed in by the user into a web address ( that
673
;       parses the full url typed in by the user into a web address ( that
671
;       can be turned into an IP address by DNS ) and the page to display
674
;       can be turned into an IP address by DNS ) and the page to display
672
;       DNS will be used to translate the web address into an IP address, if
675
;       DNS will be used to translate the web address into an IP address, if
673
;       needed.
676
;       needed.
674
;       url is at document_user and will be space terminated.
677
;       url is at document_user and will be space terminated.
675
;       web address goes to webAddr and is space terminated.
678
;       web address goes to webAddr and is space terminated.
676
;       ip address goes to server_ip
679
;       ip address goes to server_ip
677
;       page goes to document and is space terminated.
680
;       page goes to document and is space terminated.
678
;
681
;
679
;       Supported formats:
682
;       Supported formats:
680
;       address
683
;       address
681
;        is optional, removed and ignored - only http supported
684
;        is optional, removed and ignored - only http supported
682
;       
is required. It can be an ip address or web address
685
;       
is required. It can be an ip address or web address
683
;        is optional and must start with a leading / character
686
;        is optional and must start with a leading / character
684
;
687
;
685
;****************************************************************************
688
;****************************************************************************
686
parse_url:
689
parse_url:
687
; First, reset destination variables
690
; First, reset destination variables
688
        mov     al, ' '
691
        mov     al, ' '
689
        mov     edi, document
692
        mov     edi, document
690
        mov     ecx, URLMAXLEN
693
        mov     ecx, URLMAXLEN
691
        rep     stosb
694
        rep     stosb
692
        mov     edi, webAddr
695
        mov     edi, webAddr
693
        mov     ecx, URLMAXLEN
696
        mov     ecx, URLMAXLEN
694
        rep     stosb
697
        rep     stosb
695
 
698
 
696
        mov     al, '/'
699
        mov     al, '/'
697
        mov     [document], al
700
        mov     [document], al
698
 
701
 
699
        mov     esi, document_user
702
        mov     esi, document_user
700
; remove any leading protocol text
703
; remove any leading protocol text
701
        mov     ecx, URLMAXLEN
704
        mov     ecx, URLMAXLEN
702
        mov     ax, '//'
705
        mov     ax, '//'
703
 
706
 
704
pu_000:
707
pu_000:
705
        cmp     [esi], byte ' '         ; end of text?
708
        cmp     [esi], byte ' '         ; end of text?
706
        je      pu_002                  ; yep, so not found
709
        je      pu_002                  ; yep, so not found
707
        cmp     [esi], ax
710
        cmp     [esi], ax
708
        je      pu_001                  ; Found it, so esi+2 is start
711
        je      pu_001                  ; Found it, so esi+2 is start
709
        inc     esi
712
        inc     esi
710
        loop    pu_000
713
        loop    pu_000
711
 
714
 
712
pu_002:
715
pu_002:
713
; not found, so reset esi to start
716
; not found, so reset esi to start
714
        mov     esi, document_user-2
717
        mov     esi, document_user-2
715
 
718
 
716
pu_001:
719
pu_001:
717
        add     esi, 2
720
        add     esi, 2
718
        mov     ebx, esi ; save address of start of web address
721
        mov     ebx, esi ; save address of start of web address
719
        mov     edi, document_user + URLMAXLEN   ; end of string
722
        mov     edi, document_user + URLMAXLEN   ; end of string
720
; look for page delimiter - it's a '/' character
723
; look for page delimiter - it's a '/' character
721
pu_003:
724
pu_003:
722
        cmp     [esi], byte ' '  ; end of text?
725
        cmp     [esi], byte ' '  ; end of text?
723
        je      pu_004          ; yep, so none found
726
        je      pu_004          ; yep, so none found
724
        cmp     esi, edi         ; end of string?
727
        cmp     esi, edi         ; end of string?
725
        je      pu_004          ; yep, so none found
728
        je      pu_004          ; yep, so none found
726
        cmp     [esi], byte '/'  ; delimiter?
729
        cmp     [esi], byte '/'  ; delimiter?
727
        je      pu_005          ; yep - process it
730
        je      pu_005          ; yep - process it
728
        inc     esi
731
        inc     esi
729
        jmp     pu_003
732
        jmp     pu_003
730
 
733
 
731
pu_005:
734
pu_005:
732
; copy page to document address
735
; copy page to document address
733
; esi = delimiter
736
; esi = delimiter
734
        push    esi
737
        push    esi
735
        mov     ecx, edi         ; end of document_user
738
        mov     ecx, edi         ; end of document_user
736
        mov     edi, document
739
        mov     edi, document
737
 
740
 
738
pu_006:
741
pu_006:
739
        movsb
742
        movsb
740
        cmp     esi, ecx
743
        cmp     esi, ecx
741
        je      pu_007          ; end of string?
744
        je      pu_007          ; end of string?
742
        cmp     [esi], byte ' '  ; end of text
745
        cmp     [esi], byte ' '  ; end of text
743
;       je      pu_007          ; äçåí-àññåìáëåð
746
;       je      pu_007          ; äçåí-àññåìáëåð
744
;       jmp     pu_006          ; íå íàäî ïëîäèòü ñóùíîñòè ïî íàïðàñíó
747
;       jmp     pu_006          ; íå íàäî ïëîäèòü ñóùíîñòè ïî íàïðàñíó
745
        jne     pu_006
748
        jne     pu_006
746
 
749
 
747
pu_007:
750
pu_007:
748
        pop     esi     ; point esi to '/' delimiter
751
        pop     esi     ; point esi to '/' delimiter
749
 
752
 
750
pu_004:
753
pu_004:
751
; copy web address to webAddr
754
; copy web address to webAddr
752
; start in ebx, end in esi-1
755
; start in ebx, end in esi-1
753
        mov     ecx, esi
756
        mov     ecx, esi
754
        mov     esi, ebx
757
        mov     esi, ebx
755
        mov     edi, webAddr
758
        mov     edi, webAddr
756
  @@:
759
  @@:
757
        movsb
760
        movsb
758
        cmp     esi, ecx
761
        cmp     esi, ecx
759
        jne     @r
762
        jne     @r
760
        mov     byte [edi], 0
763
        mov     byte [edi], 0
761
 
764
 
762
pu_009:
765
pu_009:
763
; For debugging, display resulting strings
766
; For debugging, display resulting strings
764
        DEBUGF  2, "Downloadng %s\n", document_user
767
        DEBUGF  2, "Downloadng %s\n", document_user
765
 
768
 
766
; Look up the ip address, or was it specified?
769
; Look up the ip address, or was it specified?
767
        mov     al, [proxyAddr]
770
        mov     al, [proxyAddr]
768
        cmp     al, 0
771
        cmp     al, 0
769
        jnz     pu_015
772
        jnz     pu_015
770
        mov     al, [webAddr]
773
        mov     al, [webAddr]
771
pu_015:
774
pu_015:
772
        cmp     al, '0'
775
        cmp     al, '0'
773
        jb      pu_010  ; Resolve address
776
        jb      pu_010  ; Resolve address
774
        cmp     al, '9'
777
        cmp     al, '9'
775
        ja      pu_010  ; Resolve address
778
        ja      pu_010  ; Resolve address
776
 
779
 
777
        DEBUGF  1, "GotIP\n"
780
        DEBUGF  1, "GotIP\n"
778
 
781
 
779
; Convert address
782
; Convert address
780
; If proxy is given, get proxy address instead of server
783
; If proxy is given, get proxy address instead of server
781
        mov     esi, proxyAddr-1
784
        mov     esi, proxyAddr-1
782
        cmp     byte[esi+1], 0
785
        cmp     byte[esi+1], 0
783
        jne     pu_020
786
        jne     pu_020
784
        mov     esi, webAddr-1
787
        mov     esi, webAddr-1
785
 
788
 
786
pu_020:
789
pu_020:
787
        mov     edi, server_ip
790
        mov     edi, server_ip
788
        xor     eax, eax
791
        xor     eax, eax
789
 
792
 
790
ip1:
793
ip1:
791
        inc     esi
794
        inc     esi
792
        cmp     [esi], byte '0'
795
        cmp     [esi], byte '0'
793
        jb      ip2
796
        jb      ip2
794
        cmp     [esi], byte '9'
797
        cmp     [esi], byte '9'
795
        ja      ip2
798
        ja      ip2
796
        imul    eax, 10
799
        imul    eax, 10
797
        movzx   ebx, byte [esi]
800
        movzx   ebx, byte [esi]
798
        sub     ebx, 48
801
        sub     ebx, 48
799
        add     eax, ebx
802
        add     eax, ebx
800
        jmp     ip1
803
        jmp     ip1
801
 
804
 
802
ip2:
805
ip2:
803
        mov     [edi], al
806
        mov     [edi], al
804
        xor     eax, eax
807
        xor     eax, eax
805
        inc     edi
808
        inc     edi
806
        cmp     edi, server_ip+3
809
        cmp     edi, server_ip+3
807
        jbe     ip1
810
        jbe     ip1
808
 
811
 
809
        ret
812
        ret
810
 
813
 
811
pu_010:
814
pu_010:
812
        DEBUGF  1, "Resolving %s\n", webAddr
815
        DEBUGF  1, "Resolving %s\n", webAddr
813
 
816
 
814
; resolve name
817
; resolve name
815
        push    esp     ; reserve stack place
818
        push    esp     ; reserve stack place
816
        push    esp     ; fourth parameter
819
        push    esp     ; fourth parameter
817
        push    0       ; third parameter
820
        push    0       ; third parameter
818
        push    0       ; second parameter
821
        push    0       ; second parameter
819
        push    webAddr
822
        push    webAddr
820
        call    [getaddrinfo]
823
        call    [getaddrinfo]
821
        pop     esi
824
        pop     esi
822
; TODO: handle error
825
; TODO: handle error
823
;        test    eax, eax
826
;        test    eax, eax
824
;        jnz     .fail_dns
827
;        jnz     .fail_dns
825
 
828
 
826
; fill in ip
829
; fill in ip
827
        mov     eax, [esi + addrinfo.ai_addr]
830
        mov     eax, [esi + addrinfo.ai_addr]
828
        mov     eax, [eax + sockaddr_in.sin_addr]
831
        mov     eax, [eax + sockaddr_in.sin_addr]
829
        mov     [server_ip], eax
832
        mov     [server_ip], eax
830
 
833
 
831
; free allocated memory
834
; free allocated memory
832
        push    esi
835
        push    esi
833
        call    [freeaddrinfo]
836
        call    [freeaddrinfo]
834
 
837
 
835
        DEBUGF  1, "Resolved to %u.%u.%u.%u\n", [server_ip]:1, [server_ip + 1]:1, [server_ip + 2]:1, [server_ip + 3]:1
838
        DEBUGF  1, "Resolved to %u.%u.%u.%u\n", [server_ip]:1, [server_ip + 1]:1, [server_ip + 2]:1, [server_ip + 3]:1
836
 
839
 
837
        ret
840
        ret
838
 
841
 
839
;***************************************************************************
842
;***************************************************************************
840
;   Function
843
;   Function
841
;       append_proxy_auth_header
844
;       append_proxy_auth_header
842
;
845
;
843
;   Description
846
;   Description
844
;       Append header to HTTP request for proxy authentification
847
;       Append header to HTTP request for proxy authentification
845
;
848
;
846
;***************************************************************************
849
;***************************************************************************
847
append_proxy_auth_header:
850
append_proxy_auth_header:
848
        mov     esi, proxy_auth_basic
851
        mov     esi, proxy_auth_basic
849
        mov     ecx, proxy_auth_basic_end - proxy_auth_basic
852
        mov     ecx, proxy_auth_basic_end - proxy_auth_basic
850
        rep     movsb
853
        rep     movsb
851
; base64-encode string :
854
; base64-encode string :
852
        mov     esi, proxyUser
855
        mov     esi, proxyUser
853
 
856
 
854
apah000:
857
apah000:
855
        lodsb
858
        lodsb
856
        test    al, al
859
        test    al, al
857
        jz      apah001
860
        jz      apah001
858
        call    encode_base64_byte
861
        call    encode_base64_byte
859
        jmp     apah000
862
        jmp     apah000
860
 
863
 
861
apah001:
864
apah001:
862
        mov     al, ':'
865
        mov     al, ':'
863
        call    encode_base64_byte
866
        call    encode_base64_byte
864
        mov     esi, proxyPassword
867
        mov     esi, proxyPassword
865
 
868
 
866
apah002:
869
apah002:
867
        lodsb
870
        lodsb
868
        test    al, al
871
        test    al, al
869
        jz      apah003
872
        jz      apah003
870
        call    encode_base64_byte
873
        call    encode_base64_byte
871
        jmp     apah002
874
        jmp     apah002
872
 
875
 
873
apah003:
876
apah003:
874
        call    encode_base64_final
877
        call    encode_base64_final
875
        ret
878
        ret
876
 
879
 
877
encode_base64_byte:
880
encode_base64_byte:
878
        inc     ecx
881
        inc     ecx
879
        shl     edx, 8
882
        shl     edx, 8
880
        mov     dl, al
883
        mov     dl, al
881
        cmp     ecx, 3
884
        cmp     ecx, 3
882
        je      ebb001
885
        je      ebb001
883
        ret
886
        ret
884
 
887
 
885
ebb001:
888
ebb001:
886
        shl     edx, 8
889
        shl     edx, 8
887
        inc     ecx
890
        inc     ecx
888
 
891
 
889
ebb002:
892
ebb002:
890
        rol     edx, 6
893
        rol     edx, 6
891
        xor     eax, eax
894
        xor     eax, eax
892
        xchg    al, dl
895
        xchg    al, dl
893
        mov     al, [base64_table+eax]
896
        mov     al, [base64_table+eax]
894
        stosb
897
        stosb
895
        loop    ebb002
898
        loop    ebb002
896
        ret
899
        ret
897
 
900
 
898
encode_base64_final:
901
encode_base64_final:
899
        mov     al, 0
902
        mov     al, 0
900
        test    ecx, ecx
903
        test    ecx, ecx
901
        jz      ebf000
904
        jz      ebf000
902
        call    encode_base64_byte
905
        call    encode_base64_byte
903
        test    ecx, ecx
906
        test    ecx, ecx
904
        jz      ebf001
907
        jz      ebf001
905
        call    encode_base64_byte
908
        call    encode_base64_byte
906
        mov     byte [edi-2], '='
909
        mov     byte [edi-2], '='
907
 
910
 
908
ebf001:
911
ebf001:
909
        mov     byte [edi-1], '='
912
        mov     byte [edi-1], '='
910
 
913
 
911
ebf000:
914
ebf000:
912
        ret
915
        ret
913
 
916
 
914
;   *********************************************
917
;   *********************************************
915
;   *******  WINDOW DEFINITIONS AND DRAW ********
918
;   *******  WINDOW DEFINITIONS AND DRAW ********
916
;   *********************************************
919
;   *********************************************
917
 
920
 
918
draw_window:
921
draw_window:
919
 
922
 
920
        mcall   12, 1
923
        mcall   12, 1
921
 
924
 
922
        mcall   48, 3, sc, 40 ;get system colors
925
        mcall   48, 3, sc, 40 ;get system colors
923
 
926
 
924
        mov     edx, [sc.work]
927
        mov     edx, [sc.work]
925
        or      edx, 0x34000000
928
        or      edx, 0x34000000
926
        mcall   0, <50, 370>, <350, 140>, , 0, title   ;draw window
929
        mcall   0, <50, 370>, <350, 140>, , 0, title   ;draw window
927
        
930
        
928
        mov     ecx, [sc.work_text]
931
        mov     ecx, [sc.work_text]
929
        or      ecx, 80000000h
932
        or      ecx, 80000000h
930
        mcall   4, <14, 14>, , type_pls ;"URL:"
933
        mcall   4, <14, 14>, , type_pls ;"URL:"
931
 
934
 
932
        edit_boxes_set_sys_color edit1, editboxes_end, sc
935
        edit_boxes_set_sys_color edit1, editboxes_end, sc
933
        stdcall [edit_box_draw], edit1
936
        stdcall [edit_box_draw], edit1
934
 
937
 
935
; RELOAD
938
; RELOAD
936
        mcall   8, <90, 68>, <54, 16>, 22, [sc.work_button]
939
        mcall   8, <90, 68>, <54, 16>, 22, [sc.work_button]
937
; STOP
940
; STOP
938
        mcall   , <166, 50>, <54, 16>, 24
941
        mcall   , <166, 50>, <54, 16>, 24
939
; SAVE
942
; SAVE
940
        mcall   , <224, 54>, , 26
943
        mcall   , <224, 54>, , 26
941
; BUTTON TEXT
944
; BUTTON TEXT
942
        mov     ecx, [sc.work_button_text]
945
        mov     ecx, [sc.work_button_text]
943
        or      ecx, 80000000h
946
        or      ecx, 80000000h
944
        mcall   4, <102, 59>, , button_text
947
        mcall   4, <102, 59>, , button_text
945
 
948
 
946
        mcall   12, 2 ; end window redraw
949
        mcall   12, 2 ; end window redraw
947
 
950
 
948
        ret
951
        ret
949
 
952
 
950
 
953
 
951
;-----------------------------------------------------------------------------
954
;-----------------------------------------------------------------------------
952
; Data area
955
; Data area
953
;-----------------------------------------------------------------------------
956
;-----------------------------------------------------------------------------
954
align   4
957
align   4
955
@IMPORT:
958
@IMPORT:
956
 
959
 
957
library libini, 'libini.obj', \
960
library libini, 'libini.obj', \
958
        box_lib, 'box_lib.obj', \
961
        box_lib, 'box_lib.obj', \
959
        network, 'network.obj'
962
        network, 'network.obj'
960
 
963
 
961
import  libini, \
964
import  libini, \
962
        ini.get_str, 'ini_get_str', \
965
        ini.get_str, 'ini_get_str', \
963
        ini.get_int, 'ini_get_int'
966
        ini.get_int, 'ini_get_int'
964
 
967
 
965
import  box_lib, \
968
import  box_lib, \
966
        edit_box_draw, 'edit_box', \
969
        edit_box_draw, 'edit_box', \
967
        edit_box_key, 'edit_box_key', \
970
        edit_box_key, 'edit_box_key', \
968
        edit_box_mouse, 'edit_box_mouse'
971
        edit_box_mouse, 'edit_box_mouse'
969
 
972
 
970
import  network,\
973
import  network,\
971
        getaddrinfo,    'getaddrinfo',\
974
        getaddrinfo,    'getaddrinfo',\
972
        freeaddrinfo,   'freeaddrinfo',\
975
        freeaddrinfo,   'freeaddrinfo',\
973
        inet_ntoa,      'inet_ntoa'
976
        inet_ntoa,      'inet_ntoa'
974
 
977
 
975
;---------------------------------------------------------------------
978
;---------------------------------------------------------------------
976
fileinfo        dd 2, 0, 0
979
fileinfo        dd 2, 0, 0
977
final_size      dd 0
980
final_size      dd 0
978
final_buffer    dd 0
981
final_buffer    dd 0
979
                db '/rd/1/.download', 0
982
                db '/rd/1/.download', 0
980
        
983
        
981
body_pos        dd 0
984
body_pos        dd 0
982
buf_size        dd 0
985
buf_size        dd 0
983
buf_ptr         dd 0
986
buf_ptr         dd 0
984
 
987
 
985
deba            dd 0
988
deba            dd 0
986
                db 0
989
                db 0
987
 
990
 
988
;---------------------------------------------------------------------
991
;---------------------------------------------------------------------
989
 
992
 
990
mouse_dd        dd 0
993
mouse_dd        dd 0
991
edit1           edit_box 295, 48, 10, 0xffffff, 0xff, 0x80ff, 0, 0x8000, URLMAXLEN, document_user, mouse_dd, ed_focus+ed_always_focus, 7, 7
994
edit1           edit_box 295, 48, 10, 0xffffff, 0xff, 0x80ff, 0, 0x8000, URLMAXLEN, document_user, mouse_dd, ed_focus+ed_always_focus, 7, 7
992
editboxes_end:
995
editboxes_end:
993
 
996
 
994
;---------------------------------------------------------------------
997
;---------------------------------------------------------------------
995
 
998
 
996
include_debug_strings
999
include_debug_strings
997
 
1000
 
998
;---------------------------------------------------------------------
1001
;---------------------------------------------------------------------
999
 
1002
 
1000
type_pls        db 'URL:', 0
1003
type_pls        db 'URL:', 0
1001
button_text     db 'DOWNLOAD     STOP     RESAVE', 0
1004
button_text     db 'DOWNLOAD     STOP     RESAVE', 0
1002
download_complete db 'File saved as /rd/1/.download', 0
1005
download_complete db 'File saved as /rd/1/.download', 0
1003
title           db 'HTTP Downloader', 0
1006
title           db 'HTTP Downloader', 0
1004
 
1007
 
1005
;---------------------------------------------------------------------
1008
;---------------------------------------------------------------------
1006
s_contentlength db 'Content-Length:'
1009
s_contentlength db 'Content-Length:'
1007
len_contentlength = 15
1010
len_contentlength = 15
1008
 
1011
 
1009
s_chunked       db 'Transfer-Encoding: chunked'
1012
s_chunked       db 'Transfer-Encoding: chunked'
1010
len_chunked     = $ - s_chunked
1013
len_chunked     = $ - s_chunked
1011
 
1014
 
1012
string0:        db 'GET '
1015
string0:        db 'GET '
1013
 
1016
 
1014
stringh                 db ' HTTP/1.1', 13, 10, 'Host: '
1017
stringh                 db ' HTTP/1.1', 13, 10, 'Host: '
1015
stringh_end:
1018
stringh_end:
1016
proxy_auth_basic        db 13, 10, 'Proxy-Authorization: Basic '
1019
proxy_auth_basic        db 13, 10, 'Proxy-Authorization: Basic '
1017
proxy_auth_basic_end:
1020
proxy_auth_basic_end:
1018
connclose               db 13, 10, 'User-Agent: Kolibrios Downloader', 13, 10, 'Connection: Close', 13, 10, 13, 10
1021
connclose               db 13, 10, 'User-Agent: Kolibrios Downloader', 13, 10, 'Connection: Close', 13, 10, 13, 10
1019
connclose_end:
1022
connclose_end:
1020
 
1023
 
1021
base64_table    db 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'
1024
base64_table    db 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'
1022
                db '0123456789+/'
1025
                db '0123456789+/'
1023
 
1026
 
1024
inifile         db '/sys/settings/network.ini', 0
1027
inifile         db '/sys/settings/network.ini', 0
1025
 
1028
 
1026
sec_proxy:
1029
sec_proxy:
1027
key_proxy       db 'proxy', 0
1030
key_proxy       db 'proxy', 0
1028
key_proxyport   db 'port', 0
1031
key_proxyport   db 'port', 0
1029
key_user        db 'user', 0
1032
key_user        db 'user', 0
1030
key_password    db 'password', 0
1033
key_password    db 'password', 0
1031
 
1034
 
1032
sockaddr1:
1035
sockaddr1:
1033
                dw AF_INET4
1036
                dw AF_INET4
1034
server_port     dw 0x5000       ; 80
1037
server_port     dw 0x5000       ; 80
1035
server_ip       dd 0
1038
server_ip       dd 0
1036
                rb 10
1039
                rb 10
1037
 
1040
 
1038
proxyPort       dd 80
1041
proxyPort       dd 80
1039
 
1042
 
1040
shared_name     dd 0
1043
shared_name     dd 0
1041
 
1044
 
1042
;---------------------------------------------------------------------
1045
;---------------------------------------------------------------------
1043
document_user   db 'http://', 0
1046
document_user   db 'http://', 0
1044
;---------------------------------------------------------------------
1047
;---------------------------------------------------------------------
1045
IM_END:
1048
IM_END:
1046
;---------------------------------------------------------------------
1049
;---------------------------------------------------------------------
1047
                rb URLMAXLEN-(IM_END - document_user)
1050
                rb URLMAXLEN-(IM_END - document_user)
1048
;---------------------------------------------------------------------
1051
;---------------------------------------------------------------------
1049
                sc system_colors
1052
                sc system_colors
1050
;---------------------------------------------------------------------
1053
;---------------------------------------------------------------------
1051
align 4
1054
align 4
1052
document        rb URLMAXLEN
1055
document        rb URLMAXLEN
1053
;---------------------------------------------------------------------
1056
;---------------------------------------------------------------------
1054
align 4
1057
align 4
1055
webAddr         rb URLMAXLEN+1
1058
webAddr         rb URLMAXLEN+1
1056
;---------------------------------------------------------------------
1059
;---------------------------------------------------------------------
1057
pos             dd ?
1060
pos             dd ?
1058
socketnum       dd ?
1061
socketnum       dd ?
1059
is_chunked      dd ?
1062
is_chunked      dd ?
1060
prev_chunk_end  dd ?
1063
prev_chunk_end  dd ?
1061
cur_chunk_size  dd ?
1064
cur_chunk_size  dd ?
1062
;---------------------------------------------------------------------
1065
;---------------------------------------------------------------------
1063
 
1066
 
1064
params          rb 1024
1067
params          rb 1024
1065
 
1068
 
1066
request         rb 256
1069
request         rb 256
1067
 
1070
 
1068
proxyAddr       rb 256
1071
proxyAddr       rb 256
1069
proxyUser       rb 256
1072
proxyUser       rb 256
1070
proxyPassword   rb 256
1073
proxyPassword   rb 256
1071
 
1074
 
1072
I_END:
1075
I_END: