Rev 1297 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 1297 | Rev 1301 | ||
---|---|---|---|
1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
2 | ; |
2 | ; |
3 | ; FTPS |
3 | ; FTPS |
4 | ; FTP Server |
4 | ; FTP Server |
5 | ; |
5 | ; |
6 | ; Compile with FASM for Menuet |
6 | ; Compile with FASM for Menuet |
7 | ; |
7 | ; |
8 | 8 | ||
9 | ; note: telnet == 23, ftp cmd == 21, data on 20 |
9 | ; note: telnet == 23, ftp cmd == 21, data on 20 |
10 | 10 | ||
11 | use32 |
11 | use32 |
12 | 12 | ||
13 | org 0x0 |
13 | org 0x0 |
14 | 14 | ||
15 | db 'MENUET01' ; 8 byte id |
15 | db 'MENUET01' ; 8 byte id |
16 | dd 1 ; header version |
16 | dd 1 ; header version |
17 | dd START ; program start |
17 | dd START ; program start |
18 | dd I_END ; program image size |
18 | dd I_END ; program image size |
19 | dd 0x170000 ; required amount of memory |
19 | dd 0x170000 ; required amount of memory |
20 | dd 0x7FFF0 ; esp = 0x7FFF0 |
20 | dd 0x7FFF0 ; esp = 0x7FFF0 |
21 | dd 0, 0 ; no params, no path |
21 | dd 0, 0 ; no params, no path |
22 | 22 | ||
23 | include 'macros.inc' |
23 | include 'macros.inc' |
24 | ; Various states of client connection |
24 | ; Various states of client connection |
25 | USER_NONE equ 0 ; Awaiting a connection |
25 | USER_NONE equ 0 ; Awaiting a connection |
26 | USER_CONNECTED equ 1 ; User just connected, prompt given |
26 | USER_CONNECTED equ 1 ; User just connected, prompt given |
27 | USER_USERNAME equ 2 ; User given username |
27 | USER_USERNAME equ 2 ; User given username |
28 | USER_LOGGED_IN equ 3 ; User given password |
28 | USER_LOGGED_IN equ 3 ; User given password |
29 | 29 | ||
30 | 30 | ||
31 | 31 | ||
32 | 32 | ||
33 | 33 | ||
34 | START: ; start of execution |
34 | START: ; start of execution |
35 | ; Clear the screen memory |
35 | ; Clear the screen memory |
36 | mov eax, ' ' |
36 | mov eax, ' ' |
37 | mov edi,text |
37 | mov edi,text |
38 | mov ecx,80*30 /4 |
38 | mov ecx,80*30 /4 |
39 | cld |
39 | cld |
40 | rep stosd |
40 | rep stosd |
41 | 41 | ||
42 | call draw_window |
42 | call draw_window |
43 | 43 | ||
44 | ; init the receive buffer pointer |
44 | ; init the receive buffer pointer |
45 | mov [buffptr], buff |
45 | mov [buffptr], buff |
46 | 46 | ||
47 | ; Init FTP server state machine |
47 | ; Init FTP server state machine |
48 | mov [state], USER_NONE |
48 | mov [state], USER_NONE |
49 | 49 | ||
50 | ; Open the listening socket |
50 | ; Open the listening socket |
51 | call connect |
51 | call connect |
52 | 52 | ||
53 | still: |
53 | still: |
54 | ; check connection status |
54 | ; check connection status |
55 | mov eax,53 |
55 | mov eax,53 |
56 | mov ebx,6 ; Get socket status |
56 | mov ebx,6 ; Get socket status |
57 | mov ecx,[CmdSocket] |
57 | mov ecx,[CmdSocket] |
58 | mcall |
58 | mcall |
59 | 59 | ||
60 | mov ebx, [CmdSocketStatus] |
60 | mov ebx, [CmdSocketStatus] |
61 | mov [CmdSocketStatus], eax |
61 | mov [CmdSocketStatus], eax |
62 | 62 | ||
63 | cmp eax, ebx |
63 | cmp eax, ebx |
64 | je waitev |
64 | je waitev |
65 | 65 | ||
66 | ; If the socket closed by remote host, open it again. |
66 | ; If the socket closed by remote host, open it again. |
67 | cmp eax, 7 |
67 | cmp eax, 7 |
68 | je con |
68 | je con |
69 | 69 | ||
70 | ; If socket closed by Reset, open it again |
70 | ; If socket closed by Reset, open it again |
71 | cmp eax, 11 |
71 | cmp eax, 11 |
72 | je con |
72 | je con |
73 | 73 | ||
74 | ; If a user has just connected, start by outputting welcome msg |
74 | ; If a user has just connected, start by outputting welcome msg |
75 | cmp eax, 4 |
75 | cmp eax, 4 |
76 | jne noc |
76 | jne noc |
77 | 77 | ||
78 | mov esi, loginStr0 |
78 | mov esi, loginStr0 |
79 | mov edx, loginStr0_end - loginStr0 |
79 | mov edx, loginStr0_end - loginStr0 |
80 | call outputStr |
80 | call outputStr |
81 | 81 | ||
82 | mov [state], USER_CONNECTED |
82 | mov [state], USER_CONNECTED |
83 | jmp noc |
83 | jmp noc |
84 | 84 | ||
85 | 85 | ||
86 | con: |
86 | con: |
87 | ; Need to call disconnect, since a remote close does not fully |
87 | ; Need to call disconnect, since a remote close does not fully |
88 | ; close the socket |
88 | ; close the socket |
89 | call disconnect |
89 | call disconnect |
90 | mov eax,5 |
90 | mov eax,5 |
91 | mov ebx,10 ; Delay for 100ms |
91 | mov ebx,10 ; Delay for 100ms |
92 | mcall |
92 | mcall |
93 | call connect |
93 | call connect |
94 | jmp noc |
94 | jmp noc |
95 | 95 | ||
96 | noc: |
96 | noc: |
97 | ; Display the changed connected status |
97 | ; Display the changed connected status |
98 | call draw_window |
98 | call draw_window |
99 | 99 | ||
100 | waitev: |
100 | waitev: |
101 | mov eax,23 ; wait here for event |
101 | mov eax,23 ; wait here for event |
102 | mov ebx,1 ; Delay for up to 1s |
102 | mov ebx,1 ; Delay for up to 1s |
103 | mcall |
103 | mcall |
104 | 104 | ||
105 | cmp eax,1 ; redraw request ? |
105 | cmp eax,1 ; redraw request ? |
106 | je red |
106 | je red |
107 | cmp eax,2 ; key in buffer ? |
107 | cmp eax,2 ; key in buffer ? |
108 | je key |
108 | je key |
109 | cmp eax,3 ; button in buffer ? |
109 | cmp eax,3 ; button in buffer ? |
110 | je button |
110 | je button |
111 | 111 | ||
112 | ; any data from the socket? |
112 | ; any data from the socket? |
113 | 113 | ||
114 | mov eax, 53 |
114 | mov eax, 53 |
115 | mov ebx, 2 ; Get # of bytes in input queue |
115 | mov ebx, 2 ; Get # of bytes in input queue |
116 | mov ecx, [CmdSocket] |
116 | mov ecx, [CmdSocket] |
117 | mcall |
117 | mcall |
118 | test eax, eax |
118 | test eax, eax |
119 | jz still |
119 | jz still |
120 | 120 | ||
121 | read_input: |
121 | read_input: |
122 | mov eax, 53 |
122 | mov eax, 53 |
123 | mov ebx, 3 ; Get a byte from socket in bl |
123 | mov ebx, 3 ; Get a byte from socket in bl |
124 | mov ecx, [CmdSocket] |
124 | mov ecx, [CmdSocket] |
125 | mcall |
125 | mcall |
126 | 126 | ||
127 | call ftpRxCmdData ; process incoming ftp command |
127 | call ftpRxCmdData ; process incoming ftp command |
128 | 128 | ||
129 | ; Keep processing data until there is no more to process |
129 | ; Keep processing data until there is no more to process |
130 | mov eax, 53 |
130 | mov eax, 53 |
131 | mov ebx, 2 ; Get # of bytes in input queue |
131 | mov ebx, 2 ; Get # of bytes in input queue |
132 | mov ecx, [CmdSocket] |
132 | mov ecx, [CmdSocket] |
133 | mcall |
133 | mcall |
134 | cmp eax, 0 |
134 | cmp eax, 0 |
135 | jne read_input |
135 | jne read_input |
136 | 136 | ||
137 | ; Now redraw the text text field. |
137 | ; Now redraw the text text field. |
138 | ; Probably not required, since ftp requires no |
138 | ; Probably not required, since ftp requires no |
139 | ; console i/o. |
139 | ; console i/o. |
140 | ; Leave in for now, for debugging. |
140 | ; Leave in for now, for debugging. |
141 | ; (fall through to "red:") |
141 | ; (fall through to "red:") |
142 | ; call draw_text |
142 | ; call draw_text |
143 | ; jmp still |
143 | ; jmp still |
144 | 144 | ||
145 | red: ; REDRAW WINDOW |
145 | red: ; REDRAW WINDOW |
146 | call draw_window |
146 | call draw_window |
147 | jmp still |
147 | jmp still |
148 | 148 | ||
149 | key: ; KEY |
149 | key: ; KEY |
150 | mov eax,2 ; get but ignore |
150 | mov eax,2 ; get but ignore |
151 | mcall |
151 | mcall |
152 | jmp still |
152 | jmp still |
153 | 153 | ||
154 | button: |
154 | button: |
155 | mov eax,17 |
155 | mov eax,17 |
156 | mcall |
156 | mcall |
157 | cmp ah,1 |
157 | cmp ah,1 |
158 | jne still |
158 | jne still |
159 | 159 | ||
160 | ; Exit button pressed, so close socket and quit |
160 | ; Exit button pressed, so close socket and quit |
161 | mov eax,53 |
161 | mov eax,53 |
162 | mov ebx,8 |
162 | mov ebx,8 |
163 | mov ecx,[CmdSocket] |
163 | mov ecx,[CmdSocket] |
164 | mcall |
164 | mcall |
165 | 165 | ||
166 | ; ... terminate program |
166 | ; ... terminate program |
167 | or eax,-1 |
167 | or eax,-1 |
168 | mcall |
168 | mcall |
169 | jmp still |
169 | jmp still |
170 | 170 | ||
171 | 171 | ||
172 | 172 | ||
173 | ; ********************************************* |
173 | ; ********************************************* |
174 | ; ******* WINDOW DEFINITIONS AND DRAW ******** |
174 | ; ******* WINDOW DEFINITIONS AND DRAW ******** |
175 | ; ********************************************* |
175 | ; ********************************************* |
176 | draw_window: |
176 | draw_window: |
177 | pusha |
177 | pusha |
178 | 178 | ||
179 | mov eax,12 |
179 | mov eax,12 |
180 | mov ebx,1 |
180 | mov ebx,1 |
181 | mcall |
181 | mcall |
182 | 182 | ||
183 | xor eax,eax ; DRAW WINDOW |
183 | xor eax,eax ; DRAW WINDOW |
184 | mov ebx,100*65536+491 + 8 +15 |
184 | mov ebx,100*65536+491 + 8 +15 |
185 | mov ecx,100*65536+270 + 20 ; 20 for status bar |
185 | mov ecx,100*65536+270 + 20 ; 20 for status bar |
186 | mov edx,0x14000000 |
186 | mov edx,0x14000000 |
187 | mov edi,labelt |
187 | mov edi,labelt |
188 | mcall |
188 | mcall |
189 | 189 | ||
190 | ; draw status bar |
190 | ; draw status bar |
191 | mov eax, 13 |
191 | mov eax, 13 |
192 | mov ebx, 4*65536+484 + 8 +15 |
192 | mov ebx, 4*65536+484 + 8 +15 |
193 | mov ecx, 270*65536 + 3 |
193 | mov ecx, 270*65536 + 3 |
194 | mov edx, 0x00557799 |
194 | mov edx, 0x00557799 |
195 | mcall |
195 | mcall |
196 | 196 | ||
197 | 197 | ||
198 | mov esi,contlen-contt ; display connected status |
198 | mov esi,contlen-contt ; display connected status |
199 | mov edx, contt |
199 | mov edx, contt |
200 | cmp [CmdSocketStatus], 4 ; 4 is connected |
200 | cmp [CmdSocketStatus], 4 ; 4 is connected |
201 | je pcon |
201 | je pcon |
202 | mov esi,discontlen-discontt |
202 | mov esi,discontlen-discontt |
203 | mov edx, discontt |
203 | mov edx, discontt |
204 | pcon: |
204 | pcon: |
205 | 205 | ||
206 | mov eax,4 ; status text |
206 | mov eax,4 ; status text |
207 | mov ebx,380*65536+276 |
207 | mov ebx,380*65536+276 |
208 | mov ecx,0x00ffffff |
208 | mov ecx,0x00ffffff |
209 | mcall |
209 | mcall |
210 | 210 | ||
211 | ; Draw the text on the screen, clearing it first |
211 | ; Draw the text on the screen, clearing it first |
212 | ; This can go when we loose debuggin info. |
212 | ; This can go when we loose debuggin info. |
213 | xor eax,eax |
213 | xor eax,eax |
214 | mov edi,text+80*30 |
214 | mov edi,text+80*30 |
215 | mov ecx,80*30 /4 |
215 | mov ecx,80*30 /4 |
216 | cld |
216 | cld |
217 | rep stosd |
217 | rep stosd |
218 | 218 | ||
219 | call draw_text |
219 | call draw_text |
220 | 220 | ||
221 | mov eax,12 |
221 | mov eax,12 |
222 | mov ebx,2 |
222 | mov ebx,2 |
223 | mcall |
223 | mcall |
224 | 224 | ||
225 | popa |
225 | popa |
226 | 226 | ||
227 | ret |
227 | ret |
228 | 228 | ||
229 | 229 | ||
230 | ;*************************************************************************** |
230 | ;*************************************************************************** |
231 | ; Function |
231 | ; Function |
232 | ; draw_text |
232 | ; draw_text |
233 | ; |
233 | ; |
234 | ; Description |
234 | ; Description |
235 | ; Updates the text on the screen. This is part of the debugging code |
235 | ; Updates the text on the screen. This is part of the debugging code |
236 | ; |
236 | ; |
237 | ; Inputs |
237 | ; Inputs |
238 | ; Character to add in bl |
238 | ; Character to add in bl |
239 | ; |
239 | ; |
240 | ;*************************************************************************** |
240 | ;*************************************************************************** |
241 | draw_text: |
241 | draw_text: |
242 | 242 | ||
243 | pusha |
243 | pusha |
244 | 244 | ||
245 | mov esi,text |
245 | mov esi,text |
246 | mov eax,0 |
246 | mov eax,0 |
247 | mov ebx,0 |
247 | mov ebx,0 |
248 | newletter: |
248 | newletter: |
249 | mov cl,[esi] |
249 | mov cl,[esi] |
250 | cmp cl,[esi+30*80] |
250 | cmp cl,[esi+30*80] |
251 | jz noletter |
251 | jz noletter |
252 | yesletter: |
252 | yesletter: |
253 | mov [esi+30*80],cl |
253 | mov [esi+30*80],cl |
254 | 254 | ||
255 | ; erase character |
255 | ; erase character |
256 | 256 | ||
257 | pusha |
257 | pusha |
258 | mov edx, 0 ; bg colour |
258 | mov edx, 0 ; bg colour |
259 | mov ecx, ebx |
259 | mov ecx, ebx |
260 | add ecx, 26 |
260 | add ecx, 26 |
261 | shl ecx, 16 |
261 | shl ecx, 16 |
262 | mov cx, 9 |
262 | mov cx, 9 |
263 | mov ebx, eax |
263 | mov ebx, eax |
264 | add ebx, 6 |
264 | add ebx, 6 |
265 | shl ebx, 16 |
265 | shl ebx, 16 |
266 | mov bx, 6 |
266 | mov bx, 6 |
267 | mov eax, 13 |
267 | mov eax, 13 |
268 | mcall |
268 | mcall |
269 | popa |
269 | popa |
270 | 270 | ||
271 | ; draw character |
271 | ; draw character |
272 | 272 | ||
273 | pusha |
273 | pusha |
274 | mov ecx, 0x00ffffff |
274 | mov ecx, 0x00ffffff |
275 | push bx |
275 | push bx |
276 | mov ebx,eax |
276 | mov ebx,eax |
277 | add ebx,6 |
277 | add ebx,6 |
278 | shl ebx,16 |
278 | shl ebx,16 |
279 | pop bx |
279 | pop bx |
280 | add bx,26 |
280 | add bx,26 |
281 | mov eax,4 |
281 | mov eax,4 |
282 | mov edx,esi |
282 | mov edx,esi |
283 | mov esi,1 |
283 | mov esi,1 |
284 | mcall |
284 | mcall |
285 | popa |
285 | popa |
286 | 286 | ||
287 | noletter: |
287 | noletter: |
288 | 288 | ||
289 | add esi,1 |
289 | add esi,1 |
290 | add eax,6 |
290 | add eax,6 |
291 | cmp eax,80*6 |
291 | cmp eax,80*6 |
292 | jb newletter |
292 | jb newletter |
293 | mov eax,0 |
293 | mov eax,0 |
294 | add ebx,10 |
294 | add ebx,10 |
295 | cmp ebx,24*10 |
295 | cmp ebx,24*10 |
296 | jb newletter |
296 | jb newletter |
297 | 297 | ||
298 | popa |
298 | popa |
299 | ret |
299 | ret |
300 | 300 | ||
301 | 301 | ||
302 | 302 | ||
303 | ;*************************************************************************** |
303 | ;*************************************************************************** |
304 | ; Function |
304 | ; Function |
305 | ; ftpRxCmdData |
305 | ; ftpRxCmdData |
306 | ; |
306 | ; |
307 | ; Description |
307 | ; Description |
308 | ; Prcoesses incoming command data, calling a handler for each command. |
308 | ; Prcoesses incoming command data, calling a handler for each command. |
309 | ; Commands are built up in buff before being processed. |
309 | ; Commands are built up in buff before being processed. |
310 | ; |
310 | ; |
311 | ; Inputs |
311 | ; Inputs |
312 | ; Character to add in bl |
312 | ; Character to add in bl |
313 | ; |
313 | ; |
314 | ;*************************************************************************** |
314 | ;*************************************************************************** |
315 | ftpRxCmdData: |
315 | ftpRxCmdData: |
316 | ; Quit if we are not connected |
316 | ; Quit if we are not connected |
317 | ;( This case shouldn't be necessary, but be safe ) |
317 | ;( This case shouldn't be necessary, but be safe ) |
318 | mov al, [state] |
318 | mov al, [state] |
319 | cmp al, USER_NONE |
319 | cmp al, USER_NONE |
320 | je frcd_exit |
320 | je frcd_exit |
321 | 321 | ||
322 | ; Store the incoming character |
322 | ; Store the incoming character |
323 | mov esi, [buffptr] |
323 | mov esi, [buffptr] |
324 | mov [esi], bl |
324 | mov [esi], bl |
325 | inc esi |
325 | inc esi |
326 | mov [buffptr], esi |
326 | mov [buffptr], esi |
327 | 327 | ||
328 | ; For debugging, show the data coming in |
328 | ; For debugging, show the data coming in |
329 | pusha |
329 | pusha |
330 | call printChar |
330 | call printChar |
331 | popa |
331 | popa |
332 | 332 | ||
333 | ; Do we have an end of line? (LF) |
333 | ; Do we have an end of line? (LF) |
334 | ; if not, just exit |
334 | ; if not, just exit |
335 | cmp bl, 0x0a |
335 | cmp bl, 0x0a |
336 | jne frcd_exit |
336 | jne frcd_exit |
337 | 337 | ||
338 | ; OK we have a complete command. |
338 | ; OK we have a complete command. |
339 | ; Process, and send response |
339 | ; Process, and send response |
340 | 340 | ||
341 | ; There are a number of states involved in ftp, |
341 | ; There are a number of states involved in ftp, |
342 | ; to do with logging in. |
342 | ; to do with logging in. |
343 | 343 | ||
344 | mov al, [state] |
344 | mov al, [state] |
345 | cmp al, USER_CONNECTED |
345 | cmp al, USER_CONNECTED |
346 | jne fs001 |
346 | jne fs001 |
347 | 347 | ||
348 | ; This should be the username |
348 | ; This should be the username |
349 | 349 | ||
350 | ; TODO validate username |
350 | ; TODO validate username |
351 | 351 | ||
352 | ; OK, username accepted - ask for password |
352 | ; OK, username accepted - ask for password |
353 | mov esi, loginStr1 |
353 | mov esi, loginStr1 |
354 | mov edx, loginStr1_end - loginStr1 |
354 | mov edx, loginStr1_end - loginStr1 |
355 | call outputStr |
355 | call outputStr |
356 | 356 | ||
357 | mov [state], USER_USERNAME |
357 | mov [state], USER_USERNAME |
358 | 358 | ||
359 | ; init the receive buffer pointer |
359 | ; init the receive buffer pointer |
360 | mov [buffptr], buff |
360 | mov [buffptr], buff |
361 | 361 | ||
362 | jmp frcd_exit |
362 | jmp frcd_exit |
363 | 363 | ||
364 | fs001: |
364 | fs001: |
365 | cmp al, USER_USERNAME |
365 | cmp al, USER_USERNAME |
366 | jne fs002 |
366 | jne fs002 |
367 | 367 | ||
368 | ; This should be the password |
368 | ; This should be the password |
369 | 369 | ||
370 | ; TODO validate password |
370 | ; TODO validate password |
371 | 371 | ||
372 | ; OK, password accepted - show they are logged in |
372 | ; OK, password accepted - show they are logged in |
373 | mov esi, loginStr2 |
373 | mov esi, loginStr2 |
374 | mov edx, loginStr2_end - loginStr2 |
374 | mov edx, loginStr2_end - loginStr2 |
375 | call outputStr |
375 | call outputStr |
376 | 376 | ||
377 | mov [state], USER_LOGGED_IN |
377 | mov [state], USER_LOGGED_IN |
378 | 378 | ||
379 | ; init the receive buffer pointer |
379 | ; init the receive buffer pointer |
380 | mov [buffptr], buff |
380 | mov [buffptr], buff |
381 | 381 | ||
382 | jmp frcd_exit |
382 | jmp frcd_exit |
383 | 383 | ||
384 | fs002: |
384 | fs002: |
385 | cmp al, USER_LOGGED_IN |
385 | cmp al, USER_LOGGED_IN |
386 | jne fs003 |
386 | jne fs003 |
387 | 387 | ||
388 | ; This should be a cmd |
388 | ; This should be a cmd |
389 | call findCmd |
389 | call findCmd |
390 | mov eax, [cmdPtr] |
390 | mov eax, [cmdPtr] |
391 | cmp eax, 0 |
391 | cmp eax, 0 |
392 | 392 | ||
393 | je fs002b |
393 | je fs002b |
394 | 394 | ||
395 | call [cmdPtr] |
395 | call [cmdPtr] |
396 | 396 | ||
397 | fs002a: |
397 | fs002a: |
398 | ; init the receive buffer pointer |
398 | ; init the receive buffer pointer |
399 | mov [buffptr], buff |
399 | mov [buffptr], buff |
400 | 400 | ||
401 | jmp frcd_exit |
401 | jmp frcd_exit |
402 | 402 | ||
403 | fs002b: |
403 | fs002b: |
404 | ; an unsupported command was entered. |
404 | ; an unsupported command was entered. |
405 | ; Tell user that the command is not supported |
405 | ; Tell user that the command is not supported |
406 | 406 | ||
407 | mov esi, unsupStr |
407 | mov esi, unsupStr |
408 | mov edx, unsupStr_end - unsupStr |
408 | mov edx, unsupStr_end - unsupStr |
409 | call outputStr |
409 | call outputStr |
410 | 410 | ||
411 | jmp fs002a |
411 | jmp fs002a |
412 | 412 | ||
413 | fs003: |
413 | fs003: |
414 | frcd_exit: |
414 | frcd_exit: |
415 | ret |
415 | ret |
416 | 416 | ||
417 | 417 | ||
418 | 418 | ||
419 | ;*************************************************************************** |
419 | ;*************************************************************************** |
420 | ; Function |
420 | ; Function |
421 | ; outputStr |
421 | ; outputStr |
422 | ; |
422 | ; |
423 | ; Description |
423 | ; Description |
424 | ; Sends a string over the 'Command' socket |
424 | ; Sends a string over the 'Command' socket |
425 | ; |
425 | ; |
426 | ; Inputs |
426 | ; Inputs |
427 | ; String in esi |
427 | ; String in esi |
428 | ; Length in edx |
428 | ; Length in edx |
429 | ; |
429 | ; |
430 | ;*************************************************************************** |
430 | ;*************************************************************************** |
431 | outputStr: |
431 | outputStr: |
432 | push esi |
432 | push esi |
433 | push edx |
433 | push edx |
434 | mov eax,53 |
434 | mov eax,53 |
435 | mov ebx,7 |
435 | mov ebx,7 |
436 | mov ecx,[CmdSocket] |
436 | mov ecx,[CmdSocket] |
437 | mcall |
437 | mcall |
438 | pop edx |
438 | pop edx |
439 | pop esi |
439 | pop esi |
440 | 440 | ||
441 | cmp eax, 0 |
441 | cmp eax, 0 |
442 | je os_exit |
442 | je os_exit |
443 | 443 | ||
444 | ; The TCP/IP transmit queue is full; Wait a bit, then retry |
444 | ; The TCP/IP transmit queue is full; Wait a bit, then retry |
445 | pusha |
445 | pusha |
446 | mov eax,5 |
446 | mov eax,5 |
447 | mov ebx,1 ; Delay for up 100ms |
447 | mov ebx,1 ; Delay for up 10ms |
448 | mcall |
448 | mcall |
449 | popa |
449 | popa |
450 | jmp outputStr |
450 | jmp outputStr |
451 | os_exit: |
451 | os_exit: |
452 | ret |
452 | ret |
453 | 453 | ||
454 | 454 | ||
455 | 455 | ||
456 | ;*************************************************************************** |
456 | ;*************************************************************************** |
457 | ; Function |
457 | ; Function |
458 | ; outputDataStr |
458 | ; outputDataStr |
459 | ; |
459 | ; |
460 | ; Description |
460 | ; Description |
461 | ; Sends a string over the 'Data' socket |
461 | ; Sends a string over the 'Data' socket |
462 | ; |
462 | ; |
463 | ; Inputs |
463 | ; Inputs |
464 | ; String in esi |
464 | ; String in esi |
465 | ; Length in edx |
465 | ; Length in edx |
466 | ; |
466 | ; |
467 | ;*************************************************************************** |
467 | ;*************************************************************************** |
468 | outputDataStr: |
468 | outputDataStr: |
469 | push esi |
469 | push esi |
470 | push edx |
470 | push edx |
471 | mov eax,53 |
471 | mov eax,53 |
472 | mov ebx,7 |
472 | mov ebx,7 |
473 | mov ecx,[DataSocket] |
473 | mov ecx,[DataSocket] |
474 | mcall |
474 | mcall |
475 | pop edx |
475 | pop edx |
476 | pop esi |
476 | pop esi |
477 | 477 | ||
478 | cmp eax, 0 |
478 | cmp eax, 0 |
479 | je ods_exit |
479 | je ods_exit |
480 | 480 | ||
481 | ; The TCP/IP transmit queue is full; Wait a bit, then retry |
481 | ; The TCP/IP transmit queue is full; Wait a bit, then retry |
482 | pusha |
482 | pusha |
483 | mov eax,5 |
483 | mov eax,5 |
484 | mov ebx,20 ; Delay for upto 200ms |
484 | mov ebx,1 ; Delay for up 10ms |
485 | mcall |
485 | mcall |
486 | popa |
486 | popa |
487 | jmp outputDataStr |
487 | jmp outputDataStr |
488 | ods_exit: |
488 | ods_exit: |
489 | ret |
489 | ret |
490 | 490 | ||
491 | 491 | ||
492 | 492 | ||
493 | ;*************************************************************************** |
493 | ;*************************************************************************** |
494 | ; Function |
494 | ; Function |
495 | ; printChar |
495 | ; printChar |
496 | ; |
496 | ; |
497 | ; Description |
497 | ; Description |
498 | ; Writes a character to the screen; Used to display the data coming |
498 | ; Writes a character to the screen; Used to display the data coming |
499 | ; in from the user. Really only useful for debugging. |
499 | ; in from the user. Really only useful for debugging. |
500 | ; |
500 | ; |
501 | ; Inputs |
501 | ; Inputs |
502 | ; Character in bl |
502 | ; Character in bl |
503 | ; |
503 | ; |
504 | ;*************************************************************************** |
504 | ;*************************************************************************** |
505 | printChar: |
505 | printChar: |
506 | cmp bl,13 ; BEGINNING OF LINE |
506 | cmp bl,13 ; BEGINNING OF LINE |
507 | jne nobol |
507 | jne nobol |
508 | mov ecx,[pos] |
508 | mov ecx,[pos] |
509 | add ecx,1 |
509 | add ecx,1 |
510 | boll1: |
510 | boll1: |
511 | sub ecx,1 |
511 | sub ecx,1 |
512 | mov eax,ecx |
512 | mov eax,ecx |
513 | xor edx,edx |
513 | xor edx,edx |
514 | mov ebx,80 |
514 | mov ebx,80 |
515 | div ebx |
515 | div ebx |
516 | cmp edx,0 |
516 | cmp edx,0 |
517 | jne boll1 |
517 | jne boll1 |
518 | mov [pos],ecx |
518 | mov [pos],ecx |
519 | jmp newdata |
519 | jmp newdata |
520 | nobol: |
520 | nobol: |
521 | 521 | ||
522 | cmp bl,10 ; LINE DOWN |
522 | cmp bl,10 ; LINE DOWN |
523 | jne nolf |
523 | jne nolf |
524 | addx1: |
524 | addx1: |
525 | add [pos],dword 1 |
525 | add [pos],dword 1 |
526 | mov eax,[pos] |
526 | mov eax,[pos] |
527 | xor edx,edx |
527 | xor edx,edx |
528 | mov ecx,80 |
528 | mov ecx,80 |
529 | div ecx |
529 | div ecx |
530 | cmp edx,0 |
530 | cmp edx,0 |
531 | jnz addx1 |
531 | jnz addx1 |
532 | mov eax,[pos] |
532 | mov eax,[pos] |
533 | jmp cm1 |
533 | jmp cm1 |
534 | nolf: |
534 | nolf: |
535 | 535 | ||
536 | cmp bl,8 ; BACKSPACE |
536 | cmp bl,8 ; BACKSPACE |
537 | jne nobasp |
537 | jne nobasp |
538 | mov eax,[pos] |
538 | mov eax,[pos] |
539 | dec eax |
539 | dec eax |
540 | mov [pos],eax |
540 | mov [pos],eax |
541 | mov [eax+text],byte 32 |
541 | mov [eax+text],byte 32 |
542 | mov [eax+text+60*80],byte 0 |
542 | mov [eax+text+60*80],byte 0 |
543 | jmp newdata |
543 | jmp newdata |
544 | nobasp: |
544 | nobasp: |
545 | 545 | ||
546 | cmp bl,15 ; CHARACTER |
546 | cmp bl,15 ; CHARACTER |
547 | jbe newdata |
547 | jbe newdata |
548 | putcha: |
548 | putcha: |
549 | mov eax,[pos] |
549 | mov eax,[pos] |
550 | mov [eax+text],bl |
550 | mov [eax+text],bl |
551 | mov eax,[pos] |
551 | mov eax,[pos] |
552 | add eax,1 |
552 | add eax,1 |
553 | cm1: |
553 | cm1: |
554 | mov ebx,[scroll+4] |
554 | mov ebx,[scroll+4] |
555 | imul ebx,80 |
555 | imul ebx,80 |
556 | cmp eax,ebx |
556 | cmp eax,ebx |
557 | jb noeaxz |
557 | jb noeaxz |
558 | mov esi,text+80 |
558 | mov esi,text+80 |
559 | mov edi,text |
559 | mov edi,text |
560 | mov ecx,ebx |
560 | mov ecx,ebx |
561 | cld |
561 | cld |
562 | rep movsb |
562 | rep movsb |
563 | mov eax,ebx |
563 | mov eax,ebx |
564 | sub eax,80 |
564 | sub eax,80 |
565 | noeaxz: |
565 | noeaxz: |
566 | mov [pos],eax |
566 | mov [pos],eax |
567 | newdata: |
567 | newdata: |
568 | ret |
568 | ret |
569 | 569 | ||
570 | 570 | ||
571 | ;*************************************************************************** |
571 | ;*************************************************************************** |
572 | ; Function |
572 | ; Function |
573 | ; disconnect |
573 | ; disconnect |
574 | ; |
574 | ; |
575 | ; Description |
575 | ; Description |
576 | ; Closes the command socket |
576 | ; Closes the command socket |
577 | ; |
577 | ; |
578 | ; Inputs |
578 | ; Inputs |
579 | ; None |
579 | ; None |
580 | ; |
580 | ; |
581 | ;*************************************************************************** |
581 | ;*************************************************************************** |
582 | disconnect: |
582 | disconnect: |
583 | mov eax, 53 ; Stack Interface |
583 | mov eax, 53 ; Stack Interface |
584 | mov ebx,8 ; Close TCP socket |
584 | mov ebx,8 ; Close TCP socket |
585 | mov ecx,[CmdSocket] |
585 | mov ecx,[CmdSocket] |
586 | mcall |
586 | mcall |
587 | ret |
587 | ret |
588 | 588 | ||
589 | 589 | ||
590 | 590 | ||
591 | ;*************************************************************************** |
591 | ;*************************************************************************** |
592 | ; Function |
592 | ; Function |
593 | ; disconnectData |
593 | ; disconnectData |
594 | ; |
594 | ; |
595 | ; Description |
595 | ; Description |
596 | ; Closes the data socket |
596 | ; Closes the data socket |
597 | ; |
597 | ; |
598 | ; Inputs |
598 | ; Inputs |
599 | ; None |
599 | ; None |
600 | ; |
600 | ; |
601 | ;*************************************************************************** |
601 | ;*************************************************************************** |
602 | disconnectData: |
602 | disconnectData: |
603 | ; This delay would be better done by allowing the socket code |
603 | ; This delay would be better done by allowing the socket code |
604 | ; to wait for all data to pass through the stack before closing |
604 | ; to wait for all data to pass through the stack before closing |
605 | pusha |
605 | pusha |
606 | mov eax,5 |
606 | mov eax,5 |
607 | mov ebx,10 ; Delay for 100ms |
607 | mov ebx,10 ; Delay for 100ms |
608 | mcall |
608 | mcall |
609 | popa |
609 | popa |
610 | 610 | ||
611 | mov eax, 53 ; Stack Interface |
611 | mov eax, 53 ; Stack Interface |
612 | mov ebx,8 ; Close TCP socket |
612 | mov ebx,8 ; Close TCP socket |
613 | mov ecx,[DataSocket] |
613 | mov ecx,[DataSocket] |
614 | mcall |
614 | mcall |
615 | ret |
615 | ret |
616 | 616 | ||
617 | 617 | ||
618 | 618 | ||
619 | 619 | ||
620 | ;*************************************************************************** |
620 | ;*************************************************************************** |
621 | ; Function |
621 | ; Function |
622 | ; connect |
622 | ; connect |
623 | ; |
623 | ; |
624 | ; Description |
624 | ; Description |
625 | ; Opens the command socket |
625 | ; Opens the command socket |
626 | ; |
626 | ; |
627 | ; Inputs |
627 | ; Inputs |
628 | ; None |
628 | ; None |
629 | ; |
629 | ; |
630 | ;*************************************************************************** |
630 | ;*************************************************************************** |
631 | connect: |
631 | connect: |
632 | pusha |
632 | pusha |
633 | 633 | ||
634 | mov eax, 53 ; Stack Interface |
634 | mov eax, 53 ; Stack Interface |
635 | mov ebx, 5 ; Open TCP socket |
635 | mov ebx, 5 ; Open TCP socket |
636 | mov esi, 0 ; No remote IP address |
636 | mov esi, 0 ; No remote IP address |
637 | mov edx, 0 ; No remote port |
637 | mov edx, 0 ; No remote port |
638 | mov ecx, 21 ; ftp command port id |
638 | mov ecx, 21 ; ftp command port id |
639 | mov edi, 0 ; passive open |
639 | mov edi, 0 ; passive open |
640 | mcall |
640 | mcall |
641 | mov [CmdSocket], eax |
641 | mov [CmdSocket], eax |
642 | 642 | ||
643 | popa |
643 | popa |
644 | 644 | ||
645 | ret |
645 | ret |
646 | 646 | ||
647 | 647 | ||
648 | 648 | ||
649 | ;*************************************************************************** |
649 | ;*************************************************************************** |
650 | ; Function |
650 | ; Function |
651 | ; connectData |
651 | ; connectData |
652 | ; |
652 | ; |
653 | ; Description |
653 | ; Description |
654 | ; Opens the data socket |
654 | ; Opens the data socket |
655 | ; |
655 | ; |
656 | ; Inputs |
656 | ; Inputs |
657 | ; None |
657 | ; None |
658 | ; |
658 | ; |
659 | ;*************************************************************************** |
659 | ;*************************************************************************** |
660 | connectData: |
660 | connectData: |
661 | pusha |
661 | pusha |
662 | 662 | ||
663 | mov eax, 53 ; Stack Interface |
663 | mov eax, 53 ; Stack Interface |
664 | mov ebx, 5 ; Open TCP socket |
664 | mov ebx, 5 ; Open TCP socket |
665 | mov esi, [DataIP] ; remote IP address |
665 | mov esi, [DataIP] ; remote IP address |
666 | mov edx, [DataPort] ; remote port |
666 | mov edx, [DataPort] ; remote port |
667 | mov ecx, 0 ; ftp data port id |
667 | mov ecx, 0 ; ftp data port id |
668 | mov edi, 1 ; active open |
668 | mov edi, 1 ; active open |
669 | mcall |
669 | mcall |
670 | mov [DataSocket], eax |
670 | mov [DataSocket], eax |
671 | 671 | ||
672 | popa |
672 | popa |
673 | 673 | ||
674 | ret |
674 | ret |
675 | 675 | ||
676 | 676 | ||
677 | 677 | ||
678 | 678 | ||
679 | ;*************************************************************************** |
679 | ;*************************************************************************** |
680 | ; Function |
680 | ; Function |
681 | ; findCmd |
681 | ; findCmd |
682 | ; |
682 | ; |
683 | ; Description |
683 | ; Description |
684 | ; Scans the command string for a valid command. The command string |
684 | ; Scans the command string for a valid command. The command string |
685 | ; is in the global variable buff. |
685 | ; is in the global variable buff. |
686 | ; |
686 | ; |
687 | ; Returns result in cmdPtr. This will be zero if none found |
687 | ; Returns result in cmdPtr. This will be zero if none found |
688 | ; |
688 | ; |
689 | ; Inputs |
689 | ; Inputs |
690 | ; None |
690 | ; None |
691 | ; |
691 | ; |
692 | ;*************************************************************************** |
692 | ;*************************************************************************** |
693 | findCmd: |
693 | findCmd: |
694 | ; Setup to return 'none' in cmdPtr, if we find no cmd |
694 | ; Setup to return 'none' in cmdPtr, if we find no cmd |
695 | mov eax, 0 |
695 | mov eax, 0 |
696 | mov [cmdPtr], eax |
696 | mov [cmdPtr], eax |
697 | cld |
697 | cld |
698 | mov esi, buff |
698 | mov esi, buff |
699 | mov edi, CMDList |
699 | mov edi, CMDList |
700 | 700 | ||
701 | fc000: |
701 | fc000: |
702 | cmp [edi], byte 0 ; Are we at the end of the CMDList? |
702 | cmp [edi], byte 0 ; Are we at the end of the CMDList? |
703 | je fc_exit |
703 | je fc_exit |
704 | 704 | ||
705 | fc000a: |
705 | fc000a: |
706 | cmpsb |
706 | cmpsb |
707 | 707 | ||
708 | je fc_nextbyte |
708 | je fc_nextbyte |
709 | 709 | ||
710 | ; Command is different - move to the next entry in cmd table |
710 | ; Command is different - move to the next entry in cmd table |
711 | mov esi, buff |
711 | mov esi, buff |
712 | 712 | ||
713 | fc001: |
713 | fc001: |
714 | ; skip to the next command in the list |
714 | ; skip to the next command in the list |
715 | cmp [edi], byte 0 |
715 | cmp [edi], byte 0 |
716 | je fc002 |
716 | je fc002 |
717 | inc edi |
717 | inc edi |
718 | jmp fc001 |
718 | jmp fc001 |
719 | fc002: |
719 | fc002: |
720 | add edi, 5 |
720 | add edi, 5 |
721 | jmp fc000 |
721 | jmp fc000 |
722 | 722 | ||
723 | fc_nextbyte: |
723 | fc_nextbyte: |
724 | ; Have we reached the end of the CMD text? |
724 | ; Have we reached the end of the CMD text? |
725 | cmp [edi], byte 0 |
725 | cmp [edi], byte 0 |
726 | je fc_got ; Yes - so we have a match |
726 | je fc_got ; Yes - so we have a match |
727 | jmp fc000a ; No - loop back |
727 | jmp fc000a ; No - loop back |
728 | 728 | ||
729 | fc_got: |
729 | fc_got: |
730 | ; Copy the function pointer for the selected command |
730 | ; Copy the function pointer for the selected command |
731 | inc edi |
731 | inc edi |
732 | mov eax, [edi] |
732 | mov eax, [edi] |
733 | mov [cmdPtr], eax |
733 | mov [cmdPtr], eax |
734 | 734 | ||
735 | fc_exit: |
735 | fc_exit: |
736 | ret |
736 | ret |
737 | 737 | ||
738 | 738 | ||
739 | 739 | ||
740 | ;*************************************************************************** |
740 | ;*************************************************************************** |
741 | ; Function |
741 | ; Function |
742 | ; decStr2Byte |
742 | ; decStr2Byte |
743 | ; |
743 | ; |
744 | ; Description |
744 | ; Description |
745 | ; Converts the decimal string pointed to by esi to a byte |
745 | ; Converts the decimal string pointed to by esi to a byte |
746 | ; |
746 | ; |
747 | ; Inputs |
747 | ; Inputs |
748 | ; string ptr in esi |
748 | ; string ptr in esi |
749 | ; |
749 | ; |
750 | ; Outputs |
750 | ; Outputs |
751 | ; esi points to next character not in string |
751 | ; esi points to next character not in string |
752 | ; eax holds result ( 0..255) |
752 | ; eax holds result ( 0..255) |
753 | ; |
753 | ; |
754 | ;*************************************************************************** |
754 | ;*************************************************************************** |
755 | decStr2Byte: |
755 | decStr2Byte: |
756 | xor eax, eax |
756 | xor eax, eax |
757 | xor ebx, ebx |
757 | xor ebx, ebx |
758 | mov ecx, 3 |
758 | mov ecx, 3 |
759 | 759 | ||
760 | dsb001: |
760 | dsb001: |
761 | mov bl, [esi] |
761 | mov bl, [esi] |
762 | 762 | ||
763 | cmp bl, '0' |
763 | cmp bl, '0' |
764 | jb dsb_exit |
764 | jb dsb_exit |
765 | cmp bl, '9' |
765 | cmp bl, '9' |
766 | ja dsb_exit |
766 | ja dsb_exit |
767 | 767 | ||
768 | imul eax, 10 |
768 | imul eax, 10 |
769 | add eax, ebx |
769 | add eax, ebx |
770 | sub eax, '0' |
770 | sub eax, '0' |
771 | inc esi |
771 | inc esi |
772 | loop dsb001 |
772 | loop dsb001 |
773 | 773 | ||
774 | dsb_exit: |
774 | dsb_exit: |
775 | ret |
775 | ret |
776 | 776 | ||
777 | 777 | ||
778 | 778 | ||
779 | ;*************************************************************************** |
779 | ;*************************************************************************** |
780 | ; Function |
780 | ; Function |
781 | ; parsePortStr |
781 | ; parsePortStr |
782 | ; |
782 | ; |
783 | ; Description |
783 | ; Description |
784 | ; Converts the parameters of the PORT command, and stores them in the |
784 | ; Converts the parameters of the PORT command, and stores them in the |
785 | ; appropriate variables. |
785 | ; appropriate variables. |
786 | ; |
786 | ; |
787 | ; Inputs |
787 | ; Inputs |
788 | ; None ( string in global variable buff ) |
788 | ; None ( string in global variable buff ) |
789 | ; |
789 | ; |
790 | ; Outputs |
790 | ; Outputs |
791 | ; None |
791 | ; None |
792 | ; |
792 | ; |
793 | ;*************************************************************************** |
793 | ;*************************************************************************** |
794 | parsePortStr: |
794 | parsePortStr: |
795 | ; skip past the PORT text to get the the parameters. The command format |
795 | ; skip past the PORT text to get the the parameters. The command format |
796 | ; is |
796 | ; is |
797 | ; PORT i,i,i,i,p,p,0x0d,0x0a |
797 | ; PORT i,i,i,i,p,p,0x0d,0x0a |
798 | ; where i and p are decimal byte values, high byte first. |
798 | ; where i and p are decimal byte values, high byte first. |
799 | xor eax, eax |
799 | xor eax, eax |
800 | mov [DataIP], eax |
800 | mov [DataIP], eax |
801 | mov [DataPort], eax |
801 | mov [DataPort], eax |
802 | mov esi, buff + 4 ; Start at first space character |
802 | mov esi, buff + 4 ; Start at first space character |
803 | 803 | ||
804 | pps001: |
804 | pps001: |
805 | cmp [esi], byte ' ' ; Look for first non space character |
805 | cmp [esi], byte ' ' ; Look for first non space character |
806 | jne pps002 |
806 | jne pps002 |
807 | inc esi |
807 | inc esi |
808 | jmp pps001 |
808 | jmp pps001 |
809 | 809 | ||
810 | pps002: |
810 | pps002: |
811 | call decStr2Byte |
811 | call decStr2Byte |
812 | add [DataIP], eax |
812 | add [DataIP], eax |
813 | ror dword [DataIP], 8 |
813 | ror dword [DataIP], 8 |
814 | inc esi |
814 | inc esi |
815 | call decStr2Byte |
815 | call decStr2Byte |
816 | add [DataIP], eax |
816 | add [DataIP], eax |
817 | ror dword [DataIP], 8 |
817 | ror dword [DataIP], 8 |
818 | inc esi |
818 | inc esi |
819 | call decStr2Byte |
819 | call decStr2Byte |
820 | add [DataIP], eax |
820 | add [DataIP], eax |
821 | ror dword [DataIP], 8 |
821 | ror dword [DataIP], 8 |
822 | inc esi |
822 | inc esi |
823 | call decStr2Byte |
823 | call decStr2Byte |
824 | add [DataIP], eax |
824 | add [DataIP], eax |
825 | ror dword [DataIP], 8 |
825 | ror dword [DataIP], 8 |
826 | inc esi |
826 | inc esi |
827 | call decStr2Byte |
827 | call decStr2Byte |
828 | add [DataPort], eax |
828 | add [DataPort], eax |
829 | shl [DataPort], 8 |
829 | shl [DataPort], 8 |
830 | inc esi |
830 | inc esi |
831 | call decStr2Byte |
831 | call decStr2Byte |
832 | add [DataPort], eax |
832 | add [DataPort], eax |
833 | 833 | ||
834 | ret |
834 | ret |
835 | 835 | ||
836 | 836 | ||
837 | 837 | ||
838 | ;*************************************************************************** |
838 | ;*************************************************************************** |
839 | ; Function |
839 | ; Function |
840 | ; sendDir |
840 | ; sendDir |
841 | ; |
841 | ; |
842 | ; Description |
842 | ; Description |
843 | ; Transmits the directory listing over the data connection. |
843 | ; Transmits the directory listing over the data connection. |
844 | ; The data connection is already open. |
844 | ; The data connection is already open. |
845 | ; |
845 | ; |
846 | ; Inputs |
846 | ; Inputs |
847 | ; None |
847 | ; None |
848 | ; |
848 | ; |
849 | ; Outputs |
849 | ; Outputs |
850 | ; None |
850 | ; None |
851 | ; |
851 | ; |
852 | ;*************************************************************************** |
852 | ;*************************************************************************** |
853 | sendDir: |
853 | sendDir: |
854 | mov ebx, dirinfoblock |
854 | mov ebx, dirinfoblock |
855 | and dword [ebx+4], 0 ; start from zero block |
855 | and dword [ebx+4], 0 ; start from zero block |
856 | sd001: |
856 | sd001: |
857 | ; Read the next DirBlocksPerCall (=16) blocks |
857 | ; Read the next DirBlocksPerCall (=16) blocks |
858 | mov eax, 70 |
858 | mov eax, 70 |
859 | mcall |
859 | mcall |
860 | ; Did we read anything? |
860 | ; Did we read anything? |
861 | test eax, eax |
861 | test eax, eax |
862 | jz @f |
862 | jz @f |
863 | cmp eax, 6 |
863 | cmp eax, 6 |
864 | jnz sd_exit |
864 | jnz sd_exit |
865 | @@: |
865 | @@: |
866 | test ebx, ebx |
866 | test ebx, ebx |
867 | jz sd_exit |
867 | jz sd_exit |
868 | ; Parse these blocks. There could be up to 16 files specified |
868 | ; Parse these blocks. There could be up to 16 files specified |
869 | mov esi, text + 0x1300 + 0x20 |
869 | mov esi, text + 0x1300 + 0x20 |
870 | sd002: |
870 | sd002: |
871 | dec ebx |
871 | dec ebx |
872 | js sd004 |
872 | js sd004 |
873 | push ebx |
873 | push ebx |
874 | ; OK, lets parse the entry. Ignore volume entries |
874 | ; OK, lets parse the entry. Ignore volume entries |
875 | test byte [esi], 8 |
875 | test byte [esi], 8 |
876 | jnz sd003 |
876 | jnz sd003 |
877 | ; Valid file or directory. Start to compose the string we will send |
877 | ; Valid file or directory. Start to compose the string we will send |
878 | mov edi, dirStr |
878 | mov edi, dirStr |
879 | ; If we have been called as a result of an NLST command, we only display |
879 | ; If we have been called as a result of an NLST command, we only display |
880 | ; the filename |
880 | ; the filename |
881 | cmp [buff], byte 'N' |
881 | cmp [buff], byte 'N' |
882 | jz sd006 |
882 | jz sd006 |
883 | 883 | ||
884 | mov [edi], byte '-' |
884 | mov [edi], byte '-' |
885 | test byte [esi], 10h |
885 | test byte [esi], 10h |
886 | jz @f |
886 | jz @f |
887 | mov [edi], byte 'd' |
887 | mov [edi], byte 'd' |
888 | @@: |
888 | @@: |
889 | ; Ok, now copy across the directory listing text that will be constant |
889 | ; Ok, now copy across the directory listing text that will be constant |
890 | ; ( I dont bother looking at the read only or archive bits ) |
890 | ; ( I dont bother looking at the read only or archive bits ) |
891 | 891 | ||
892 | mov ebx, tmplStr |
892 | mov ebx, tmplStr |
893 | @@: |
893 | @@: |
894 | inc edi |
894 | inc edi |
895 | mov al, [ebx] |
895 | mov al, [ebx] |
896 | test al, al |
896 | test al, al |
897 | jz @f |
897 | jz @f |
898 | mov [edi], al |
898 | mov [edi], al |
899 | inc ebx |
899 | inc ebx |
900 | jmp @b |
900 | jmp @b |
901 | @@: |
901 | @@: |
902 | ; point to the last character of the string; |
902 | ; point to the last character of the string; |
903 | ; We will write the file size here, backwards |
903 | ; We will write the file size here, backwards |
904 | push edi ; Remember where the string ends |
904 | push edi ; Remember where the string ends |
905 | 905 | ||
906 | dec edi |
906 | dec edi |
907 | ; eax holds the number |
907 | ; eax holds the number |
908 | mov eax, [esi+32] |
908 | mov eax, [esi+32] |
909 | mov ebx, 10 |
909 | mov ebx, 10 |
910 | @@: |
910 | @@: |
911 | xor edx, edx |
911 | xor edx, edx |
912 | div ebx |
912 | div ebx |
913 | add dl, '0' |
913 | add dl, '0' |
914 | mov [edi], dl |
914 | mov [edi], dl |
915 | dec edi |
915 | dec edi |
916 | test eax, eax |
916 | test eax, eax |
917 | jnz @b |
917 | jnz @b |
918 | 918 | ||
919 | pop edi |
919 | pop edi |
920 | ; now create the time & date fields |
920 | ; now create the time & date fields |
921 | ;timeStr: db ' Jan 1 2000 ',0 |
921 | ;timeStr: db ' Jan 1 2000 ',0 |
922 | mov al, ' ' |
922 | mov al, ' ' |
923 | stosb |
923 | stosb |
924 | movzx eax, byte [esi+28+1] |
924 | movzx eax, byte [esi+28+1] |
925 | mov eax, dword [months + (eax-1)*4] |
925 | mov eax, dword [months + (eax-1)*4] |
926 | stosd |
926 | stosd |
927 | mov al, byte [esi+28] |
927 | mov al, byte [esi+28] |
928 | aam |
928 | aam |
929 | test ah, ah |
929 | test ah, ah |
930 | jz sd005a |
930 | jz sd005a |
931 | xchg al, ah |
931 | xchg al, ah |
932 | add ax, '00' |
932 | add ax, '00' |
933 | jmp sd005b |
933 | jmp sd005b |
934 | sd005a: |
934 | sd005a: |
935 | add al, '0' |
935 | add al, '0' |
936 | mov ah, ' ' |
936 | mov ah, ' ' |
937 | sd005b: |
937 | sd005b: |
938 | stosw |
938 | stosw |
939 | mov al, ' ' |
939 | mov al, ' ' |
940 | mov ecx, 6 |
940 | mov ecx, 6 |
941 | rep stosb |
941 | rep stosb |
942 | push edi |
942 | push edi |
943 | movzx eax, word [esi+28+2] |
943 | movzx eax, word [esi+28+2] |
944 | @@: |
944 | @@: |
945 | xor edx, edx |
945 | xor edx, edx |
946 | div ebx |
946 | div ebx |
947 | add dl, '0' |
947 | add dl, '0' |
948 | mov [edi], dl |
948 | mov [edi], dl |
949 | dec edi |
949 | dec edi |
950 | test eax, eax |
950 | test eax, eax |
951 | jnz @b |
951 | jnz @b |
952 | pop edi |
952 | pop edi |
953 | inc edi |
953 | inc edi |
954 | mov al, ' ' |
954 | mov al, ' ' |
955 | stosb |
955 | stosb |
956 | sd006: |
956 | sd006: |
957 | ; ** End of copying |
957 | ; ** End of copying |
958 | 958 | ||
959 | ; now copy the filename across |
959 | ; now copy the filename across |
960 | lea ebx, [esi+40] |
960 | lea ebx, [esi+40] |
961 | @@: |
961 | @@: |
962 | mov al, [ebx] |
962 | mov al, [ebx] |
963 | inc ebx |
963 | inc ebx |
964 | test al, al |
964 | test al, al |
965 | jz @f |
965 | jz @f |
966 | stosb |
966 | stosb |
967 | jmp @b |
967 | jmp @b |
968 | @@: |
968 | @@: |
969 | terminate: |
969 | terminate: |
970 | ; Now terminate the line by putting CRLF sequence in |
970 | ; Now terminate the line by putting CRLF sequence in |
971 | mov al, 0x0D |
971 | mov al, 0x0D |
972 | stosb |
972 | stosb |
973 | mov al, 0x0A |
973 | mov al, 0x0A |
974 | stosb |
974 | stosb |
975 | ; Send the completed line to the user over data socket |
975 | ; Send the completed line to the user over data socket |
976 | push esi |
976 | push esi |
977 | mov esi, dirStr |
977 | mov esi, dirStr |
978 | mov edx, edi |
978 | mov edx, edi |
979 | sub edx, esi |
979 | sub edx, esi |
980 | call outputDataStr |
980 | call outputDataStr |
981 | pop esi |
981 | pop esi |
982 | 982 | ||
983 | sd003: ; Move to next entry in the block |
983 | sd003: ; Move to next entry in the block |
984 | pop ebx |
984 | pop ebx |
985 | add esi, 304 |
985 | add esi, 304 |
986 | jmp sd002 |
986 | jmp sd002 |
987 | sd004: |
987 | sd004: |
988 | mov ebx, dirinfoblock |
988 | mov ebx, dirinfoblock |
989 | add dword [ebx+4], DirBlocksPerCall |
989 | add dword [ebx+4], DirBlocksPerCall |
990 | jmp sd001 |
990 | jmp sd001 |
991 | 991 | ||
992 | sd_exit: |
992 | sd_exit: |
993 | ret |
993 | ret |
994 | 994 | ||
995 | 995 | ||
996 | 996 | ||
997 | 997 | ||
998 | 998 | ||
999 | ;*************************************************************************** |
999 | ;*************************************************************************** |
1000 | ; Function |
1000 | ; Function |
1001 | ; setupFilePath |
1001 | ; setupFilePath |
1002 | ; |
1002 | ; |
1003 | ; Description |
1003 | ; Description |
1004 | ; Copies the file name from the input request string into the |
1004 | ; Copies the file name from the input request string into the |
1005 | ; file descriptor |
1005 | ; file descriptor |
1006 | ; |
1006 | ; |
1007 | ; Inputs |
1007 | ; Inputs |
1008 | ; None |
1008 | ; None |
1009 | ; |
1009 | ; |
1010 | ; Outputs |
1010 | ; Outputs |
1011 | ; None |
1011 | ; None |
1012 | ; |
1012 | ; |
1013 | ;*************************************************************************** |
1013 | ;*************************************************************************** |
1014 | setupFilePath: |
1014 | setupFilePath: |
1015 | mov esi, buff + 4 ; Point to (1 before) first character of file |
1015 | mov esi, buff + 4 ; Point to (1 before) first character of file |
1016 | 1016 | ||
1017 | ; Skip any trailing spaces or / character |
1017 | ; Skip any trailing spaces or / character |
1018 | sfp001: |
1018 | sfp001: |
1019 | inc esi |
1019 | inc esi |
1020 | cmp [esi], byte ' ' |
1020 | cmp [esi], byte ' ' |
1021 | je sfp001 |
1021 | je sfp001 |
1022 | cmp [esi], byte '/' |
1022 | cmp [esi], byte '/' |
1023 | je sfp001 |
1023 | je sfp001 |
1024 | 1024 | ||
1025 | ; esi points to start of filename. |
1025 | ; esi points to start of filename. |
1026 | 1026 | ||
1027 | 1027 | ||
1028 | ; Copy across the directory path '/' |
1028 | ; Copy across the directory path '/' |
1029 | ; into the fileinfoblock |
1029 | ; into the fileinfoblock |
1030 | mov edi, filename |
1030 | mov edi, filename |
1031 | mov dword [edi], '/RD/' |
1031 | mov dword [edi], '/RD/' |
1032 | mov word [edi+4], '1/' |
1032 | mov word [edi+4], '1/' |
1033 | add edi, 6 |
1033 | add edi, 6 |
1034 | 1034 | ||
1035 | ; Copy across the filename |
1035 | ; Copy across the filename |
1036 | sfp002: |
1036 | sfp002: |
1037 | cld |
1037 | cld |
1038 | movsb |
1038 | movsb |
1039 | cmp [esi], byte 0x0d |
1039 | cmp [esi], byte 0x0d |
1040 | jne sfp002 |
1040 | jne sfp002 |
1041 | mov [edi], byte 0 |
1041 | mov [edi], byte 0 |
1042 | ret |
1042 | ret |
1043 | 1043 | ||
1044 | 1044 | ||
1045 | 1045 | ||
1046 | 1046 | ||
1047 | ;*************************************************************************** |
1047 | ;*************************************************************************** |
1048 | ; Function |
1048 | ; Function |
1049 | ; sendFile |
1049 | ; sendFile |
1050 | ; |
1050 | ; |
1051 | ; Description |
1051 | ; Description |
1052 | ; Transmits the requested file over the open data socket |
1052 | ; Transmits the requested file over the open data socket |
1053 | ; The file to send is named in the buff string |
1053 | ; The file to send is named in the buff string |
1054 | ; |
1054 | ; |
1055 | ; Inputs |
1055 | ; Inputs |
1056 | ; None |
1056 | ; None |
1057 | ; |
1057 | ; |
1058 | ; Outputs |
1058 | ; Outputs |
1059 | ; None |
1059 | ; None |
1060 | ; |
1060 | ; |
1061 | ;*************************************************************************** |
1061 | ;*************************************************************************** |
1062 | sendFile: |
1062 | sendFile: |
1063 | call setupFilePath |
1063 | call setupFilePath |
1064 | 1064 | ||
1065 | ; init fileblock descriptor, for file read |
1065 | ; init fileblock descriptor, for file read |
1066 | mov ebx, fileinfoblock |
1066 | mov ebx, fileinfoblock |
1067 | and dword [ebx], 0 ; read cmd |
1067 | and dword [ebx], 0 ; read cmd |
1068 | and dword [ebx+4], 0 ; first block |
1068 | and dword [ebx+4], 0 ; first block |
- | 1069 | mov dword [ebx+12], 0x400 ; block size |
|
1069 | 1070 | ||
1070 | sf002a: |
1071 | sf002a: |
1071 | ; now read the file.. |
1072 | ; now read the file.. |
1072 | mov eax,70 |
1073 | mov eax,70 |
1073 | mcall |
1074 | mcall |
1074 | test eax, eax |
1075 | test eax, eax |
1075 | jz @f |
1076 | jz @f |
1076 | cmp eax, 6 |
1077 | cmp eax, 6 |
1077 | jnz sf_exit |
1078 | jnz sf_exit |
1078 | @@: |
1079 | @@: |
1079 | push eax |
1080 | push eax |
1080 | mov esi, text + 0x1300 |
1081 | mov esi, text + 0x1300 |
1081 | mov edx, ebx |
1082 | mov edx, ebx |
1082 | call outputDataStr |
1083 | call outputDataStr |
1083 | pop eax |
1084 | pop eax |
1084 | test eax, eax |
1085 | test eax, eax |
1085 | jnz sf_exit |
1086 | jnz sf_exit |
1086 | ; wait a bit |
1087 | ; wait a bit |
1087 | mov eax, 5 |
1088 | mov eax, 5 |
1088 | mov ebx, 10 |
1089 | mov ebx, 1 |
1089 | mcall |
1090 | mcall |
1090 | mov ebx, fileinfoblock |
1091 | mov ebx, fileinfoblock |
1091 | add dword [ebx+4], edx |
1092 | add dword [ebx+4], edx |
1092 | jmp sf002a |
1093 | jmp sf002a |
1093 | 1094 | ||
1094 | sf_exit: |
1095 | sf_exit: |
1095 | ret |
1096 | ret |
1096 | 1097 | ||
1097 | 1098 | ||
1098 | ;*************************************************************************** |
1099 | ;*************************************************************************** |
1099 | ; Function |
1100 | ; Function |
1100 | ; getFile |
1101 | ; getFile |
1101 | ; |
1102 | ; |
1102 | ; Description |
1103 | ; Description |
1103 | ; Receives the specified file over the open data socket |
1104 | ; Receives the specified file over the open data socket |
1104 | ; The file to receive is named in the buff string |
1105 | ; The file to receive is named in the buff string |
1105 | ; |
1106 | ; |
1106 | ; Inputs |
1107 | ; Inputs |
1107 | ; None |
1108 | ; None |
1108 | ; |
1109 | ; |
1109 | ; Outputs |
1110 | ; Outputs |
1110 | ; None |
1111 | ; None |
1111 | ; |
1112 | ; |
1112 | ;*************************************************************************** |
1113 | ;*************************************************************************** |
1113 | getFile: |
1114 | getFile: |
1114 | call setupFilePath |
1115 | call setupFilePath |
1115 | 1116 | ||
1116 | ; init fileblock descriptor, for file write |
1117 | ; init fileblock descriptor, for file write |
1117 | xor eax, eax |
1118 | xor eax, eax |
1118 | mov [fsize], eax ; Start filelength at 0 |
1119 | mov [fsize], eax ; Start filelength at 0 |
1119 | mov [fileinfoblock+4], eax ; set to 0 |
1120 | mov [fileinfoblock+4], eax ; set to 0 |
1120 | inc eax |
1121 | inc eax |
1121 | inc eax |
1122 | inc eax |
1122 | mov [fileinfoblock], eax ; write cmd |
1123 | mov [fileinfoblock], eax ; write cmd |
1123 | 1124 | ||
1124 | ; Read data from the socket until the socket closes |
1125 | ; Read data from the socket until the socket closes |
1125 | ; loop |
1126 | ; loop |
1126 | ; loop |
1127 | ; loop |
1127 | ; read byte from socket |
1128 | ; read byte from socket |
1128 | ; write byte to file buffer |
1129 | ; write byte to file buffer |
1129 | ; until no more bytes in socket |
1130 | ; until no more bytes in socket |
1130 | ; sleep 100ms |
1131 | ; sleep 100ms |
1131 | ; until socket no longer connected |
1132 | ; until socket no longer connected |
1132 | ; write file to ram |
1133 | ; write file to ram |
1133 | 1134 | ||
1134 | gf000: |
1135 | gf000: |
1135 | mov eax, 53 |
1136 | mov eax, 53 |
1136 | mov ebx, 2 ; Get # of bytes in input queue |
1137 | mov ebx, 2 ; Get # of bytes in input queue |
1137 | mov ecx, [DataSocket] |
1138 | mov ecx, [DataSocket] |
1138 | mcall |
1139 | mcall |
1139 | test eax, eax |
1140 | test eax, eax |
1140 | je gf_sleep |
1141 | je gf_sleep |
1141 | 1142 | ||
1142 | mov eax, 53 |
1143 | mov eax, 53 |
1143 | mov ebx, 3 ; Get a byte from socket in bl |
1144 | mov ebx, 11 ; Get a bytes from socket |
1144 | mov ecx, [DataSocket] |
1145 | mov ecx, [DataSocket] |
1145 | mcall ; returned data in bl |
- | |
1146 | - | ||
1147 | mov esi, text + 0x1300 |
1146 | mov edx, text + 0x1300 |
1148 | add esi, dword [fsize] |
1147 | add edx, dword [fsize] |
1149 | mov [esi], bl |
1148 | mcall ; returned data len in eax |
1150 | inc dword [fsize] |
1149 | add dword [fsize], eax |
1151 | - | ||
1152 | ; dummy, write to screen |
- | |
1153 | ;call printChar |
- | |
1154 | 1150 | ||
1155 | jmp gf000 |
1151 | jmp gf000 |
1156 | 1152 | ||
1157 | gf_sleep: |
1153 | gf_sleep: |
1158 | ; Check to see if socket closed... |
1154 | ; Check to see if socket closed... |
1159 | mov eax,53 |
1155 | mov eax,53 |
1160 | mov ebx,6 ; Get socket status |
1156 | mov ebx,6 ; Get socket status |
1161 | mov ecx,[DataSocket] |
1157 | mov ecx,[DataSocket] |
1162 | mcall |
1158 | mcall |
1163 | 1159 | ||
1164 | cmp eax, 7 |
1160 | cmp eax, 7 |
1165 | jne gf001 ; still open, so just sleep a bit |
1161 | jne gf001 ; still open, so just sleep a bit |
1166 | 1162 | ||
1167 | ; Finished, so write the file |
1163 | ; Finished, so write the file |
1168 | mov eax, [fsize] |
1164 | mov eax, [fsize] |
1169 | mov [fileinfoblock+12], eax |
1165 | mov [fileinfoblock+12], eax |
1170 | mov eax,70 |
1166 | mov eax,70 |
1171 | mov ebx,fileinfoblock |
1167 | mov ebx,fileinfoblock |
1172 | mcall |
1168 | mcall |
1173 | 1169 | ||
1174 | ret ; Finished |
1170 | ret ; Finished |
1175 | 1171 | ||
1176 | gf001: |
1172 | gf001: |
1177 | ; wait a bit |
1173 | ; wait a bit |
1178 | mov eax,5 |
1174 | mov eax,5 |
1179 | mov ebx,10 ; Delay for up 100ms |
1175 | mov ebx,1 ; Delay for up 10ms |
1180 | mcall |
1176 | mcall |
1181 | jmp gf000 ; try for more data |
1177 | jmp gf000 ; try for more data |
1182 | 1178 | ||
1183 | 1179 | ||
1184 | 1180 | ||
1185 | 1181 | ||
1186 | 1182 | ||
1187 | ;*************************************************************************** |
1183 | ;*************************************************************************** |
1188 | ; COMMAND HANDLERS FOLLOW |
1184 | ; COMMAND HANDLERS FOLLOW |
1189 | ; |
1185 | ; |
1190 | ; These handlers implement the functionality of each supported FTP Command |
1186 | ; These handlers implement the functionality of each supported FTP Command |
1191 | ; |
1187 | ; |
1192 | ;*************************************************************************** |
1188 | ;*************************************************************************** |
1193 | 1189 | ||
1194 | cmdPWD: |
1190 | cmdPWD: |
1195 | ; OK, show the directory name text |
1191 | ; OK, show the directory name text |
1196 | mov esi, ramdir |
1192 | mov esi, ramdir |
1197 | mov edx, ramdir_end - ramdir |
1193 | mov edx, ramdir_end - ramdir |
1198 | call outputStr |
1194 | call outputStr |
1199 | 1195 | ||
1200 | ; TODO give real directory |
1196 | ; TODO give real directory |
1201 | 1197 | ||
1202 | ret |
1198 | ret |
1203 | 1199 | ||
1204 | 1200 | ||
1205 | cmdCWD: |
1201 | cmdCWD: |
1206 | ; Only / is valid for the ramdisk |
1202 | ; Only / is valid for the ramdisk |
1207 | cmp [buff+5], byte 0x0d |
1203 | cmp [buff+5], byte 0x0d |
1208 | jne ccwd_000 |
1204 | jne ccwd_000 |
1209 | 1205 | ||
1210 | ; OK, show the directory name text |
1206 | ; OK, show the directory name text |
1211 | mov esi, chdir |
1207 | mov esi, chdir |
1212 | mov edx, chdir_end - chdir |
1208 | mov edx, chdir_end - chdir |
1213 | jmp ccwd_001 |
1209 | jmp ccwd_001 |
1214 | 1210 | ||
1215 | ccwd_000: |
1211 | ccwd_000: |
1216 | ; Tell user there is no such directory |
1212 | ; Tell user there is no such directory |
1217 | mov esi, noFileStr |
1213 | mov esi, noFileStr |
1218 | mov edx, noFileStr_end - noFileStr |
1214 | mov edx, noFileStr_end - noFileStr |
1219 | 1215 | ||
1220 | ccwd_001: |
1216 | ccwd_001: |
1221 | call outputStr |
1217 | call outputStr |
1222 | 1218 | ||
1223 | ret |
1219 | ret |
1224 | 1220 | ||
1225 | 1221 | ||
1226 | cmdQUIT: |
1222 | cmdQUIT: |
1227 | ; The remote end will do the close; We just |
1223 | ; The remote end will do the close; We just |
1228 | ; say goodbye. |
1224 | ; say goodbye. |
1229 | mov esi, byeStr |
1225 | mov esi, byeStr |
1230 | mov edx, byeStr_end - byeStr |
1226 | mov edx, byeStr_end - byeStr |
1231 | call outputStr |
1227 | call outputStr |
1232 | ret |
1228 | ret |
1233 | 1229 | ||
1234 | 1230 | ||
1235 | cmdABOR: |
1231 | cmdABOR: |
1236 | 1232 | ||
1237 | ; Close port |
1233 | ; Close port |
1238 | call disconnectData |
1234 | call disconnectData |
1239 | 1235 | ||
1240 | mov esi, abortStr |
1236 | mov esi, abortStr |
1241 | mov edx, abortStr_end - abortStr |
1237 | mov edx, abortStr_end - abortStr |
1242 | call outputStr |
1238 | call outputStr |
1243 | 1239 | ||
1244 | ret |
1240 | ret |
1245 | 1241 | ||
1246 | cmdPORT: |
1242 | cmdPORT: |
1247 | ; TODO |
1243 | ; TODO |
1248 | ; Copy the IP and port values to DataIP and DataPort |
1244 | ; Copy the IP and port values to DataIP and DataPort |
1249 | 1245 | ||
1250 | call parsePortStr |
1246 | call parsePortStr |
1251 | 1247 | ||
1252 | ; Indicate the command was accepted |
1248 | ; Indicate the command was accepted |
1253 | mov esi, cmdOKStr |
1249 | mov esi, cmdOKStr |
1254 | mov edx, cmdOKStr_end - cmdOKStr |
1250 | mov edx, cmdOKStr_end - cmdOKStr |
1255 | call outputStr |
1251 | call outputStr |
1256 | ret |
1252 | ret |
1257 | 1253 | ||
1258 | cmdnoop: |
1254 | cmdnoop: |
1259 | ; Indicate the command was accepted |
1255 | ; Indicate the command was accepted |
1260 | mov esi, cmdOKStr |
1256 | mov esi, cmdOKStr |
1261 | mov edx, cmdOKStr_end - cmdOKStr |
1257 | mov edx, cmdOKStr_end - cmdOKStr |
1262 | call outputStr |
1258 | call outputStr |
1263 | ret |
1259 | ret |
1264 | 1260 | ||
1265 | 1261 | ||
1266 | cmdTYPE: |
1262 | cmdTYPE: |
1267 | ; TODO |
1263 | ; TODO |
1268 | ; Note the type field selected - reject if needed. |
1264 | ; Note the type field selected - reject if needed. |
1269 | 1265 | ||
1270 | ; Indicate the command was accepted |
1266 | ; Indicate the command was accepted |
1271 | mov esi, cmdOKStr |
1267 | mov esi, cmdOKStr |
1272 | mov edx, cmdOKStr_end - cmdOKStr |
1268 | mov edx, cmdOKStr_end - cmdOKStr |
1273 | call outputStr |
1269 | call outputStr |
1274 | ret |
1270 | ret |
1275 | 1271 | ||
1276 | cmdsyst: |
1272 | cmdsyst: |
1277 | ; Indicate the system type |
1273 | ; Indicate the system type |
1278 | mov esi, systStr |
1274 | mov esi, systStr |
1279 | mov edx, systStr_end - systStr |
1275 | mov edx, systStr_end - systStr |
1280 | call outputStr |
1276 | call outputStr |
1281 | ret |
1277 | ret |
1282 | 1278 | ||
1283 | 1279 | ||
1284 | cmdDELE: |
1280 | cmdDELE: |
1285 | call setupFilePath |
1281 | call setupFilePath |
1286 | 1282 | ||
1287 | mov ebx, fileinfoblock |
1283 | mov ebx, fileinfoblock |
1288 | mov dword [ebx], 8 |
1284 | mov dword [ebx], 8 |
1289 | and dword [ebx+4], 0 |
1285 | and dword [ebx+4], 0 |
1290 | push dword [ebx+12] |
1286 | push dword [ebx+12] |
1291 | push dword [ebx+16] |
1287 | push dword [ebx+16] |
1292 | and dword [ebx+12], 0 |
1288 | and dword [ebx+12], 0 |
1293 | and dword [ebx+16], 0 |
1289 | and dword [ebx+16], 0 |
1294 | mov eax, 70 |
1290 | mov eax, 70 |
1295 | mcall |
1291 | mcall |
1296 | pop dword [ebx+16] |
1292 | pop dword [ebx+16] |
1297 | pop dword [ebx+12] |
1293 | pop dword [ebx+12] |
1298 | 1294 | ||
1299 | test eax, eax |
1295 | test eax, eax |
1300 | jne cmdDele_err |
1296 | jne cmdDele_err |
1301 | 1297 | ||
1302 | mov esi, delokStr |
1298 | mov esi, delokStr |
1303 | mov edx, delokStr_end - delokStr |
1299 | mov edx, delokStr_end - delokStr |
1304 | call outputStr |
1300 | call outputStr |
1305 | 1301 | ||
1306 | jmp cmdDele_exit |
1302 | jmp cmdDele_exit |
1307 | 1303 | ||
1308 | cmdDele_err: |
1304 | cmdDele_err: |
1309 | mov esi, noFileStr |
1305 | mov esi, noFileStr |
1310 | mov edx, noFileStr_end - noFileStr |
1306 | mov edx, noFileStr_end - noFileStr |
1311 | call outputStr |
1307 | call outputStr |
1312 | 1308 | ||
1313 | 1309 | ||
1314 | cmdDele_exit: |
1310 | cmdDele_exit: |
1315 | ret |
1311 | ret |
1316 | 1312 | ||
1317 | 1313 | ||
1318 | cmdNLST: |
1314 | cmdNLST: |
1319 | cmdLIST: |
1315 | cmdLIST: |
1320 | ; Indicate the command was accepted |
1316 | ; Indicate the command was accepted |
1321 | mov esi, startStr |
1317 | mov esi, startStr |
1322 | mov edx, startStr_end - startStr |
1318 | mov edx, startStr_end - startStr |
1323 | call outputStr |
1319 | call outputStr |
1324 | 1320 | ||
1325 | call connectData |
1321 | call connectData |
1326 | 1322 | ||
1327 | ; Wait for socket to establish |
1323 | ; Wait for socket to establish |
1328 | 1324 | ||
1329 | cl001: |
1325 | cl001: |
1330 | ; wait a bit |
1326 | ; wait a bit |
1331 | mov eax,5 |
1327 | mov eax,5 |
1332 | mov ebx,10 ; Delay for up 100ms |
1328 | mov ebx,10 ; Delay for up 100ms |
1333 | mcall |
1329 | mcall |
1334 | 1330 | ||
1335 | ; check connection status |
1331 | ; check connection status |
1336 | mov eax,53 |
1332 | mov eax,53 |
1337 | mov ebx,6 ; Get socket status |
1333 | mov ebx,6 ; Get socket status |
1338 | mov ecx,[DataSocket] |
1334 | mov ecx,[DataSocket] |
1339 | mcall |
1335 | mcall |
1340 | 1336 | ||
1341 | cmp eax, 4 |
1337 | cmp eax, 4 |
1342 | jne cl001 |
1338 | jne cl001 |
1343 | 1339 | ||
1344 | ; send directory listing |
1340 | ; send directory listing |
1345 | call sendDir |
1341 | call sendDir |
1346 | 1342 | ||
1347 | ; Close port |
1343 | ; Close port |
1348 | call disconnectData |
1344 | call disconnectData |
1349 | 1345 | ||
1350 | mov esi, endStr |
1346 | mov esi, endStr |
1351 | mov edx, endStr_end - endStr |
1347 | mov edx, endStr_end - endStr |
1352 | call outputStr |
1348 | call outputStr |
1353 | ret |
1349 | ret |
1354 | 1350 | ||
1355 | cmdRETR: |
1351 | cmdRETR: |
1356 | ; Indicate the command was accepted |
1352 | ; Indicate the command was accepted |
1357 | mov esi, startStr |
1353 | mov esi, startStr |
1358 | mov edx, startStr_end - startStr |
1354 | mov edx, startStr_end - startStr |
1359 | call outputStr |
1355 | call outputStr |
1360 | 1356 | ||
1361 | call connectData |
1357 | call connectData |
1362 | 1358 | ||
1363 | ; Wait for socket to establish |
1359 | ; Wait for socket to establish |
1364 | 1360 | ||
1365 | cr001: |
1361 | cr001: |
1366 | ; wait a bit |
1362 | ; wait a bit |
1367 | mov eax,5 |
1363 | mov eax,5 |
1368 | mov ebx,10 ; Delay for up 100ms |
1364 | mov ebx,10 ; Delay for up 100ms |
1369 | mcall |
1365 | mcall |
1370 | 1366 | ||
1371 | ; check connection status |
1367 | ; check connection status |
1372 | mov eax,53 |
1368 | mov eax,53 |
1373 | mov ebx,6 ; Get socket status |
1369 | mov ebx,6 ; Get socket status |
1374 | mov ecx,[DataSocket] |
1370 | mov ecx,[DataSocket] |
1375 | mcall |
1371 | mcall |
1376 | 1372 | ||
1377 | cmp eax, 4 |
1373 | cmp eax, 4 |
1378 | jne cr001 |
1374 | jne cr001 |
1379 | 1375 | ||
1380 | ; send data to remote user |
1376 | ; send data to remote user |
1381 | call sendFile |
1377 | call sendFile |
1382 | 1378 | ||
1383 | ; Close port |
1379 | ; Close port |
1384 | call disconnectData |
1380 | call disconnectData |
1385 | 1381 | ||
1386 | mov esi, endStr |
1382 | mov esi, endStr |
1387 | mov edx, endStr_end - endStr |
1383 | mov edx, endStr_end - endStr |
1388 | call outputStr |
1384 | call outputStr |
1389 | 1385 | ||
1390 | 1386 | ||
1391 | ret |
1387 | ret |
1392 | 1388 | ||
1393 | 1389 | ||
1394 | cmdSTOR: |
1390 | cmdSTOR: |
1395 | ; Indicate the command was accepted |
1391 | ; Indicate the command was accepted |
1396 | mov esi, storStr |
1392 | mov esi, storStr |
1397 | mov edx, storStr_end - storStr |
1393 | mov edx, storStr_end - storStr |
1398 | call outputStr |
1394 | call outputStr |
1399 | 1395 | ||
1400 | call connectData |
1396 | call connectData |
1401 | 1397 | ||
1402 | ; Wait for socket to establish |
1398 | ; Wait for socket to establish |
1403 | 1399 | ||
1404 | cs001: |
1400 | cs001: |
1405 | ; wait a bit |
1401 | ; wait a bit |
1406 | mov eax,5 |
1402 | mov eax,5 |
1407 | mov ebx,10 ; Delay for up 100ms |
1403 | mov ebx,10 ; Delay for up 100ms |
1408 | mcall |
1404 | mcall |
1409 | 1405 | ||
1410 | ; check connection status |
1406 | ; check connection status |
1411 | mov eax,53 |
1407 | mov eax,53 |
1412 | mov ebx,6 ; Get socket status |
1408 | mov ebx,6 ; Get socket status |
1413 | mov ecx,[DataSocket] |
1409 | mov ecx,[DataSocket] |
1414 | mcall |
1410 | mcall |
1415 | 1411 | ||
1416 | cmp eax, 4 |
1412 | cmp eax, 4 |
1417 | je @f |
1413 | je @f |
1418 | cmp eax, 7 |
1414 | cmp eax, 7 |
1419 | jne cs001 |
1415 | jne cs001 |
1420 | @@: |
1416 | @@: |
1421 | 1417 | ||
1422 | ; get data file from remote user |
1418 | ; get data file from remote user |
1423 | call getFile |
1419 | call getFile |
1424 | 1420 | ||
1425 | mov esi, endStr |
1421 | mov esi, endStr |
1426 | mov edx, endStr_end - endStr |
1422 | mov edx, endStr_end - endStr |
1427 | call outputStr |
1423 | call outputStr |
1428 | 1424 | ||
1429 | ; Close port |
1425 | ; Close port |
1430 | call disconnectData |
1426 | call disconnectData |
1431 | 1427 | ||
1432 | ret |
1428 | ret |
1433 | 1429 | ||
1434 | 1430 | ||
1435 | 1431 | ||
1436 | ; DATA AREA |
1432 | ; DATA AREA |
1437 | 1433 | ||
1438 | ; This is the list of supported commands, and the function to call |
1434 | ; This is the list of supported commands, and the function to call |
1439 | ; The list end with a NULL. |
1435 | ; The list end with a NULL. |
1440 | CMDList: |
1436 | CMDList: |
1441 | db 'pwd',0 |
1437 | db 'pwd',0 |
1442 | dd cmdPWD |
1438 | dd cmdPWD |
1443 | 1439 | ||
1444 | db 'PWD',0 |
1440 | db 'PWD',0 |
1445 | dd cmdPWD |
1441 | dd cmdPWD |
1446 | 1442 | ||
1447 | db 'XPWD',0 |
1443 | db 'XPWD',0 |
1448 | dd cmdPWD |
1444 | dd cmdPWD |
1449 | 1445 | ||
1450 | db 'xpwd',0 |
1446 | db 'xpwd',0 |
1451 | dd cmdPWD |
1447 | dd cmdPWD |
1452 | 1448 | ||
1453 | db 'QUIT',0 |
1449 | db 'QUIT',0 |
1454 | dd cmdQUIT |
1450 | dd cmdQUIT |
1455 | 1451 | ||
1456 | db 'quit',0 |
1452 | db 'quit',0 |
1457 | dd cmdQUIT |
1453 | dd cmdQUIT |
1458 | 1454 | ||
1459 | db 'PORT',0 |
1455 | db 'PORT',0 |
1460 | dd cmdPORT |
1456 | dd cmdPORT |
1461 | 1457 | ||
1462 | db 'port',0 |
1458 | db 'port',0 |
1463 | dd cmdPORT |
1459 | dd cmdPORT |
1464 | 1460 | ||
1465 | db 'LIST',0 |
1461 | db 'LIST',0 |
1466 | dd cmdLIST |
1462 | dd cmdLIST |
1467 | 1463 | ||
1468 | db 'list',0 |
1464 | db 'list',0 |
1469 | dd cmdLIST |
1465 | dd cmdLIST |
1470 | 1466 | ||
1471 | db 'NLST',0 |
1467 | db 'NLST',0 |
1472 | dd cmdNLST |
1468 | dd cmdNLST |
1473 | 1469 | ||
1474 | db 'nlst',0 |
1470 | db 'nlst',0 |
1475 | dd cmdNLST |
1471 | dd cmdNLST |
1476 | 1472 | ||
1477 | db 'TYPE',0 |
1473 | db 'TYPE',0 |
1478 | dd cmdTYPE |
1474 | dd cmdTYPE |
1479 | 1475 | ||
1480 | db 'type',0 |
1476 | db 'type',0 |
1481 | dd cmdTYPE |
1477 | dd cmdTYPE |
1482 | 1478 | ||
1483 | db 'syst',0 |
1479 | db 'syst',0 |
1484 | dd cmdsyst |
1480 | dd cmdsyst |
1485 | 1481 | ||
1486 | db 'noop',0 |
1482 | db 'noop',0 |
1487 | dd cmdnoop |
1483 | dd cmdnoop |
1488 | 1484 | ||
1489 | db 'CWD',0 |
1485 | db 'CWD',0 |
1490 | dd cmdCWD |
1486 | dd cmdCWD |
1491 | 1487 | ||
1492 | db 'cwd',0 |
1488 | db 'cwd',0 |
1493 | dd cmdCWD |
1489 | dd cmdCWD |
1494 | 1490 | ||
1495 | db 'RETR',0 |
1491 | db 'RETR',0 |
1496 | dd cmdRETR |
1492 | dd cmdRETR |
1497 | 1493 | ||
1498 | db 'retr',0 |
1494 | db 'retr',0 |
1499 | dd cmdRETR |
1495 | dd cmdRETR |
1500 | 1496 | ||
1501 | db 'DELE',0 |
1497 | db 'DELE',0 |
1502 | dd cmdDELE |
1498 | dd cmdDELE |
1503 | 1499 | ||
1504 | db 'dele',0 |
1500 | db 'dele',0 |
1505 | dd cmdDELE |
1501 | dd cmdDELE |
1506 | 1502 | ||
1507 | db 'stor',0 |
1503 | db 'stor',0 |
1508 | dd cmdSTOR |
1504 | dd cmdSTOR |
1509 | 1505 | ||
1510 | db 'STOR',0 |
1506 | db 'STOR',0 |
1511 | dd cmdSTOR |
1507 | dd cmdSTOR |
1512 | 1508 | ||
1513 | db 'ABOR',0 |
1509 | db 'ABOR',0 |
1514 | dd cmdABOR |
1510 | dd cmdABOR |
1515 | 1511 | ||
1516 | db 'abor',0 |
1512 | db 'abor',0 |
1517 | dd cmdABOR |
1513 | dd cmdABOR |
1518 | 1514 | ||
1519 | db 0xff,0xf4,0xff,0xf2,'ABOR',0 |
1515 | db 0xff,0xf4,0xff,0xf2,'ABOR',0 |
1520 | dd cmdABOR |
1516 | dd cmdABOR |
1521 | 1517 | ||
1522 | db 0 |
1518 | db 0 |
1523 | 1519 | ||
1524 | 1520 | ||
1525 | cmdPtr dd 0 |
1521 | cmdPtr dd 0 |
1526 | CmdSocket dd 0x0 |
1522 | CmdSocket dd 0x0 |
1527 | CmdSocketStatus dd 0x0 |
1523 | CmdSocketStatus dd 0x0 |
1528 | DataSocket dd 0x0 |
1524 | DataSocket dd 0x0 |
1529 | DataSocketStatus dd 0x0 |
1525 | DataSocketStatus dd 0x0 |
1530 | DataPort dd 0x00 |
1526 | DataPort dd 0x00 |
1531 | DataIP dd 0x00 |
1527 | DataIP dd 0x00 |
1532 | pos dd 80 * 1 |
1528 | pos dd 80 * 1 |
1533 | scroll dd 1 |
1529 | scroll dd 1 |
1534 | dd 24 |
1530 | dd 24 |
1535 | 1531 | ||
1536 | labelt db 'FTP Server v0.1',0 |
1532 | labelt db 'FTP Server v0.1',0 |
1537 | contt db 'Connected' |
1533 | contt db 'Connected' |
1538 | contlen: |
1534 | contlen: |
1539 | discontt db 'Disconnected' |
1535 | discontt db 'Disconnected' |
1540 | discontlen: |
1536 | discontlen: |
1541 | 1537 | ||
1542 | cmdOKStr: db '200 Command OK',0x0d,0x0a |
1538 | cmdOKStr: db '200 Command OK',0x0d,0x0a |
1543 | cmdOKStr_end: |
1539 | cmdOKStr_end: |
1544 | 1540 | ||
1545 | loginStr0: db '220- Menuet FTP Server v0.1',0x0d,0x0a |
1541 | loginStr0: db '220- Menuet FTP Server v0.1',0x0d,0x0a |
1546 | db '220 Username and Password required',0x0d,0x0a |
1542 | db '220 Username and Password required',0x0d,0x0a |
1547 | loginStr0_end: |
1543 | loginStr0_end: |
1548 | 1544 | ||
1549 | loginStr1: db '331 Password now required',0x0d,0x0a |
1545 | loginStr1: db '331 Password now required',0x0d,0x0a |
1550 | loginStr1_end: |
1546 | loginStr1_end: |
1551 | 1547 | ||
1552 | loginStr2: db '230 You are now logged in.',0x0d,0x0a |
1548 | loginStr2: db '230 You are now logged in.',0x0d,0x0a |
1553 | loginStr2_end: |
1549 | loginStr2_end: |
1554 | 1550 | ||
1555 | byeStr: db '221 Bye bye!',0x0d,0x0a |
1551 | byeStr: db '221 Bye bye!',0x0d,0x0a |
1556 | byeStr_end: |
1552 | byeStr_end: |
1557 | 1553 | ||
1558 | systStr: db '215 UNIX system type',0x0d,0x0a |
1554 | systStr: db '215 UNIX system type',0x0d,0x0a |
1559 | systStr_end: |
1555 | systStr_end: |
1560 | 1556 | ||
1561 | ramdir: db '257 "/"',0x0d,0x0a |
1557 | ramdir: db '257 "/"',0x0d,0x0a |
1562 | ramdir_end: |
1558 | ramdir_end: |
1563 | 1559 | ||
1564 | chdir: db '200 directory changed to /',0x0d,0x0a |
1560 | chdir: db '200 directory changed to /',0x0d,0x0a |
1565 | chdir_end: |
1561 | chdir_end: |
1566 | 1562 | ||
1567 | unsupStr: db '500 Unsupported command',0x0d,0x0a |
1563 | unsupStr: db '500 Unsupported command',0x0d,0x0a |
1568 | unsupStr_end: |
1564 | unsupStr_end: |
1569 | 1565 | ||
1570 | noFileStr: db '550 No such file',0x0d,0x0a |
1566 | noFileStr: db '550 No such file',0x0d,0x0a |
1571 | noFileStr_end: |
1567 | noFileStr_end: |
1572 | 1568 | ||
1573 | delokStr: db '250 DELE command successful',0x0d,0x0a |
1569 | delokStr: db '250 DELE command successful',0x0d,0x0a |
1574 | delokStr_end: |
1570 | delokStr_end: |
1575 | 1571 | ||
1576 | startStr: db '150 Here it comes...',0x0d,0x0a |
1572 | startStr: db '150 Here it comes...',0x0d,0x0a |
1577 | startStr_end: |
1573 | startStr_end: |
1578 | 1574 | ||
1579 | storStr: db '150 Connecting for STOR',0x0d,0x0a |
1575 | storStr: db '150 Connecting for STOR',0x0d,0x0a |
1580 | storStr_end: |
1576 | storStr_end: |
1581 | 1577 | ||
1582 | endStr: db '226 Transfer OK, Closing connection',0x0d,0x0a |
1578 | endStr: db '226 Transfer OK, Closing connection',0x0d,0x0a |
1583 | endStr_end: |
1579 | endStr_end: |
1584 | 1580 | ||
1585 | abortStr: db '225 Abort successful',0x0d,0x0a |
1581 | abortStr: db '225 Abort successful',0x0d,0x0a |
1586 | abortStr_end: |
1582 | abortStr_end: |
1587 | 1583 | ||
1588 | ; This is the buffer used for building up a directory listing line |
1584 | ; This is the buffer used for building up a directory listing line |
1589 | dirStr: times 128 db 0 |
1585 | dirStr: times 128 db 0 |
1590 | 1586 | ||
1591 | ; This is template string used in building up a directory listing line |
1587 | ; This is template string used in building up a directory listing line |
1592 | tmplStr: db 'rw-rw-rw- 1 0 0 ',0 |
1588 | tmplStr: db 'rw-rw-rw- 1 0 0 ',0 |
1593 | 1589 | ||
1594 | months: |
1590 | months: |
1595 | dd 'Jan ','Feb ','Mar ','Apr ','May ','Jun ' |
1591 | dd 'Jan ','Feb ','Mar ','Apr ','May ','Jun ' |
1596 | dd 'Jul ','Aug ','Sep ','Oct ','Nov ','Dec ' |
1592 | dd 'Jul ','Aug ','Sep ','Oct ','Nov ','Dec ' |
1597 | 1593 | ||
1598 | fileinfoblock: |
1594 | fileinfoblock: |
1599 | dd 0x00 |
1595 | dd 0x00 |
1600 | dd 0x00 |
1596 | dd 0x00 |
1601 | dd 0x00 |
1597 | dd 0x00 |
1602 | dd 0x200 ; bytes to read |
1598 | dd 0x200 ; bytes to read |
1603 | dd text + 0x1300 ; data area |
1599 | dd text + 0x1300 ; data area |
1604 | filename: times 256 db 0 |
1600 | filename: times 256 db 0 |
1605 | 1601 | ||
1606 | ; The following lines define data for reading a directory block |
1602 | ; The following lines define data for reading a directory block |
1607 | DirBlocksPerCall = 16 |
1603 | DirBlocksPerCall = 16 |
1608 | dirinfoblock: |
1604 | dirinfoblock: |
1609 | dd 1 |
1605 | dd 1 |
1610 | dd 0x00 |
1606 | dd 0x00 |
1611 | dd 0x00 |
1607 | dd 0x00 |
1612 | dd DirBlocksPerCall |
1608 | dd DirBlocksPerCall |
1613 | dd text + 0x1300 ; data area |
1609 | dd text + 0x1300 ; data area |
1614 | ; The 'filename' for a directory listing |
1610 | ; The 'filename' for a directory listing |
1615 | dirpath db '/sys',0 |
1611 | dirpath db '/sys',0 |
1616 | 1612 | ||
1617 | fsize: dd 0 |
1613 | fsize: dd 0 |
1618 | 1614 | ||
1619 | state db 0 |
1615 | state db 0 |
1620 | buffptr dd 0 |
1616 | buffptr dd 0 |
1621 | buff: times 256 db 0 ; Could put this after iend |
1617 | buff: times 256 db 0 ; Could put this after iend |
1622 | 1618 | ||
1623 | ; Ram use at the end of the application: |
1619 | ; Ram use at the end of the application: |
1624 | ; text : 2400 bytes for screen memory |
1620 | ; text : 2400 bytes for screen memory |
1625 | ; text + 0x1300 : file data area |
1621 | ; text + 0x1300 : file data area |
1626 | text: |
1622 | text: |
1627 | I_END: |
1623 | I_END: |