Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
129 mikedld 1
; System function 70 - files with long names (LFN)
2
; diamond, 2006
3
 
4
iglobal
5
; in this table names must be in lowercase
6
rootdirs:
7
        db      2,'rd'
8
        dd      fs_OnRamdisk
9
        dd      fs_NextRamdisk
10
        db      7,'ramdisk'
11
        dd      fs_OnRamdisk
12
        dd      fs_NextRamdisk
13
        db      2,'fd'
14
        dd      fs_OnFloppy
15
        dd      fs_NextFloppy
16
        db      10,'floppydisk'
17
        dd      fs_OnFloppy
18
        dd      fs_NextFloppy
19
        db      3,'hd0'
20
        dd      fs_OnHd0
21
        dd      fs_NextHd0
22
        db      3,'hd1'
23
        dd      fs_OnHd1
24
        dd      fs_NextHd1
25
        db      3,'hd2'
26
        dd      fs_OnHd2
27
        dd      fs_NextHd2
28
        db      3,'hd3'
29
        dd      fs_OnHd3
30
        dd      fs_NextHd3
31
;**********************************************
32
        db      3,'cd0'
33
        dd      fs_OnCd0
34
        dd      fs_NextCd
35
        db      3,'cd1'
36
        dd      fs_OnCd1
37
        dd      fs_NextCd
38
        db      3,'cd2'
39
        dd      fs_OnCd2
40
        dd      fs_NextCd
41
        db      3,'cd3'
42
        dd      fs_OnCd3
43
        dd      fs_NextCd
384 mikedld 44
;***********************************************
129 mikedld 45
        db      0
46
 
47
 
48
virtual_root_query:
49
        dd      fs_HasRamdisk
50
        db      'rd',0
51
        dd      fs_HasFloppy
52
        db      'fd',0
53
        dd      fs_HasHd0
54
        db      'hd0',0
55
        dd      fs_HasHd1
56
        db      'hd1',0
57
        dd      fs_HasHd2
58
        db      'hd2',0
59
        dd      fs_HasHd3
60
        db      'hd3',0
61
;**********************************************
62
        dd      fs_HasCd0
63
        db      'cd0',0
64
        dd      fs_HasCd1
65
        db      'cd1',0
66
        dd      fs_HasCd2
67
        db      'cd2',0
68
        dd      fs_HasCd3
69
        db      'cd3',0
70
;**********************************************
71
        dd      0
72
endg
73
 
74
file_system_lfn:
75
; in: eax->fileinfo block
76
; operation codes:
77
; 0 : read file
78
; 1 : read folder
79
; 2 : create/rewrite file
133 diamond 80
; 3 : write/append to file
81
; 4 : set end of file
129 mikedld 82
; 5 : get file/directory attributes structure
83
; 6 : set file/directory attributes structure
84
; 7 : start application
384 mikedld 85
; 8 : delete file
86
; 9 : create directory
129 mikedld 87
 
88
        add     eax, std_application_base_address
89
; parse file name
90
        xchg    ebx, eax
91
        lea     esi, [ebx+20]
92
        mov     ebp, esi        ; for 'start app' function full path must be known
93
        lodsb
94
        test    al, al
95
        jnz     @f
96
        mov     esi, [esi]
97
        add     esi, std_application_base_address
98
        mov     ebp, esi
99
        lodsb
100
@@:
384 mikedld 101
        cmp dword [ebx], 7
102
        jne @F
103
        mov edx, [ebx+4]
104
        mov ebx, [ebx+8]
105
        test ebx, ebx
106
        jz .l1
107
        add ebx, new_app_base
108
.l1:
109
        call fs_execute  ; ebp, ebx, edx
110
        mov [esp+36], eax
111
        ret
112
@@:
129 mikedld 113
        cmp     al, '/'
114
        jz      @f
115
.notfound:
116
        mov     dword [esp+36], 5       ; file not found
117
        ret
118
@@:
119
        cmp     byte [esi], 0
120
        jz      .rootdir
121
        mov     edi, rootdirs-8
122
        xor     ecx, ecx
123
        push    esi
124
.scan1:
125
        pop     esi
126
        add     edi, ecx
127
        scasd
128
        scasd
129
        mov     cl, byte [edi]
130
        jecxz   .notfound
131
        inc     edi
132
        push    esi
133
@@:
134
        lodsb
135
        or      al, 20h
136
        scasb
137
        loopz   @b
138
        jnz     .scan1
139
        lodsb
140
        cmp     al, '/'
141
        jz      .found1
142
        test    al, al
143
        jnz     .scan1
144
        pop     eax
145
; directory /xxx
146
.maindir:
147
        cmp     dword [ebx], 1
148
        jnz     .access_denied
149
        xor     eax, eax
150
        mov     ebp, [ebx+12]
151
        mov     edx, [ebx+16]
152
        add     edx, std_application_base_address
153
        push    dword [ebx+4]   ; first block
154
        mov     ebx, [ebx+8]    ; flags
155
        mov     esi, [edi+4]
156
; ebx=flags, [esp]=first block, ebp=number of blocks, edx=return area, esi='Next' handler
157
        mov     edi, edx
158
        mov     ecx, 32/4
159
        rep     stosd
160
        mov     byte [edx], 1   ; version
161
.maindir_loop:
162
        call    esi
163
        jc      .maindir_done
164
        inc     dword [edx+8]
165
        dec     dword [esp]
166
        jns     .maindir_loop
167
        dec     ebp
168
        js      .maindir_loop
169
        inc     dword [edx+4]
170
        mov     dword [edi], 0x10       ; attributes: folder
171
        mov     dword [edi+4], 1        ; name type: UNICODE
172
        push    eax
173
        xor     eax, eax
174
        add     edi, 8
175
        mov     ecx, 40/4-2
176
        rep     stosd
177
        pop     eax
178
        push    eax edx
179
; convert number in eax to decimal UNICODE string
180
        push    edi
181
        push    -'0'
182
        mov     cl, 10
183
@@:
184
        xor     edx, edx
185
        div     ecx
186
        push    edx
187
        test    eax, eax
188
        jnz     @b
189
@@:
190
        pop     eax
191
        add     al, '0'
192
        stosb
193
        test    bl, 1           ; UNICODE name?
194
        jz      .ansi2
195
        mov     byte [edi], 0
196
        inc     edi
197
.ansi2:
198
        test    al, al
199
        jnz     @b
200
        mov     byte [edi-1], 0
201
        pop     edi
202
; UNICODE name length is 520 bytes, ANSI - 264
203
        add     edi, 520
204
        test    bl, 1
205
        jnz     @f
206
        sub     edi, 520-264
207
@@:
208
        pop     edx eax
209
        jmp     .maindir_loop
210
.maindir_done:
211
        pop     eax
212
        mov     ebx, [edx+4]
213
        xor     eax, eax
214
        dec     ebp
215
        js      @f
216
        mov     al, ERROR_END_OF_FILE
217
@@:
218
        mov     [esp+36], eax
219
        mov     [esp+24], ebx
220
        ret
221
; directory /
222
.rootdir:
223
        cmp     dword [ebx], 1  ; read folder?
224
        jz      .readroot
225
.access_denied:
226
        mov     dword [esp+36], 10      ; access denied
227
        ret
228
 
229
.readroot:
230
; virtual root folder - special handler
231
        mov     esi, virtual_root_query
232
        mov     ebp, [ebx+12]
233
        mov     edx, [ebx+16]
234
        add     edx, std_application_base_address
235
        push    dword [ebx+4]   ; first block
236
        mov     ebx, [ebx+8]    ; flags
237
        xor     eax, eax
238
; eax=0, [esp]=first block, ebx=flags, ebp=number of blocks, edx=return area
239
        mov     edi, edx
240
        mov     ecx, 32/4
241
        rep     stosd
242
        mov     byte [edx], 1   ; version
243
.readroot_loop:
244
        cmp     dword [esi], eax
245
        jz      .readroot_done
246
        call    dword [esi]
247
        add     esi, 4
248
        test    eax, eax
249
        jnz     @f
250
.readroot_next:
251
        or      ecx, -1
252
        xchg    esi, edi
253
        repnz   scasb
254
        xchg    esi, edi
255
        jmp     .readroot_loop
256
@@:
257
        xor     eax, eax
258
        inc     dword [edx+8]
259
        dec     dword [esp]
260
        jns     .readroot_next
261
        dec     ebp
262
        js      .readroot_next
263
        inc     dword [edx+4]
264
        mov     dword [edi], 0x10       ; attributes: folder
265
        mov     dword [edi+4], 1        ; name type: UNICODE
266
        add     edi, 8
267
        mov     ecx, 40/4-2
268
        rep     stosd
269
        push    edi
270
@@:
271
        lodsb
272
        stosb
273
        test    bl, 1
274
        jz      .ansi
275
        mov     byte [edi], 0
276
        inc     edi
277
.ansi:
278
        test    eax, eax
279
        jnz     @b
280
        pop     edi
281
        add     edi, 520
282
        test    bl, 1
283
        jnz     .readroot_loop
284
        sub     edi, 520-264
285
        jmp     .readroot_loop
286
.readroot_done:
287
        pop     eax
288
        mov     ebx, [edx+4]
289
        xor     eax, eax
290
        dec     ebp
291
        js      @f
292
        mov     al, ERROR_END_OF_FILE
293
@@:
294
        mov     [esp+36], eax
295
        mov     [esp+24], ebx
296
        ret
297
 
298
.found1:
299
        pop     eax
300
        cmp     byte [esi], 0
301
        jz      .maindir
302
; read partition number
303
        xor     ecx, ecx
304
        xor     eax, eax
305
@@:
306
        lodsb
307
        cmp     al, '/'
308
        jz      .done1
309
        test    al, al
310
        jz      .done1
311
        sub     al, '0'
312
        cmp     al, 9
313
        ja      .notfound
314
        imul    ecx, 10
315
        add     ecx, eax
316
        jmp     @b
317
.done1:
318
        test    ecx, ecx
319
        jz      .notfound
320
        test    al, al
321
        jnz     @f
322
        dec     esi
323
@@:
324
; now [edi] contains handler address, ecx - partition number,
325
; esi points to ASCIIZ string - rest of name
326
        jmp     dword [edi]
327
 
328
; handlers for devices
329
; in: ecx = 0 => query virtual directory /xxx
330
; in: ecx = partition number
331
;     esi -> relative (for device) name
332
;     ebx -> fileinfo
333
; out: [esp+36]=image of eax, [esp+24]=image of ebx
334
 
335
fs_OnRamdisk:
336
        cmp     ecx, 1
337
        jnz     file_system_lfn.notfound
338
        mov     eax, [ebx]
339
        cmp     eax, fs_NumRamdiskServices
340
        jae     .not_impl
341
        mov     ecx, [ebx+12]
342
        mov     edx, [ebx+16]
343
        add     edx, std_application_base_address
344
        add     ebx, 4
345
        call    dword [fs_RamdiskServices + eax*4]
346
        mov     [esp+36], eax
347
        mov     [esp+24], ebx
348
        ret
349
.not_impl:
350
        mov     dword [esp+36], 2       ; not implemented
351
        ret
352
 
353
fs_NotImplemented:
354
        mov     eax, 2
355
        ret
356
 
357
fs_RamdiskServices:
358
        dd      fs_RamdiskRead
359
        dd      fs_RamdiskReadFolder
360
        dd      fs_RamdiskRewrite
131 diamond 361
        dd      fs_RamdiskWrite
133 diamond 362
        dd      fs_RamdiskSetFileEnd
129 mikedld 363
        dd      fs_RamdiskGetFileInfo
364
        dd      fs_RamdiskSetFileInfo
384 mikedld 365
        dd      0 ;fs_RamdiskExecute
366
        dd      fs_RamdiskDelete
367
        dd      fs_RamdiskCreateFolder
129 mikedld 368
fs_NumRamdiskServices = ($ - fs_RamdiskServices)/4
369
 
370
fs_OnFloppy:
371
        cmp     ecx, 2
372
        ja      file_system_lfn.notfound
373
        mov     eax, [ebx]
374
        cmp     eax, fs_NumFloppyServices
375
        jae     fs_OnRamdisk.not_impl
376
        call    reserve_flp
377
        mov     [flp_number], cl
378
        mov     ecx, [ebx+12]
379
        mov     edx, [ebx+16]
380
        add     edx, std_application_base_address
381
        add     ebx, 4
382
        call    dword [fs_FloppyServices + eax*4]
383
        and     [flp_status], 0
384
        mov     [esp+36], eax
385
        mov     [esp+24], ebx
386
        ret
387
 
388
fs_FloppyServices:
389
        dd      fs_FloppyRead
390
        dd      fs_FloppyReadFolder
391
        dd      fs_FloppyRewrite
131 diamond 392
        dd      fs_FloppyWrite
133 diamond 393
        dd      fs_FloppySetFileEnd
129 mikedld 394
        dd      fs_FloppyGetFileInfo
395
        dd      fs_FloppySetFileInfo
384 mikedld 396
        dd      0 ;fs_FloppyExecute
397
        dd      fs_FloppyDelete
398
        dd      fs_FloppyCreateFolder
129 mikedld 399
fs_NumFloppyServices = ($ - fs_FloppyServices)/4
400
 
401
fs_OnHd0:
402
        call    reserve_hd1
403
        mov     [hdbase], 0x1F0
404
        mov     [hdid], 0
405
        push    1
406
        jmp     fs_OnHd
407
fs_OnHd1:
408
        call    reserve_hd1
409
        mov     [hdbase], 0x1F0
410
        mov     [hdid], 0x10
411
        push    2
412
        jmp     fs_OnHd
413
fs_OnHd2:
414
        call    reserve_hd1
415
        mov     [hdbase], 0x170
416
        mov     [hdid], 0
417
        push    3
418
        jmp     fs_OnHd
419
fs_OnHd3:
420
        call    reserve_hd1
421
        mov     [hdbase], 0x170
422
        mov     [hdid], 0x10
423
        push    4
424
fs_OnHd:
425
        call    reserve_hd_channel
426
        pop     eax
427
        mov     [hdpos], eax
428
        cmp     ecx, 0x100
429
        jae     .nf
430
        cmp     cl, [0x40001+eax]
431
        jbe     @f
432
.nf:
433
        call    free_hd_channel
434
        and     [hd1_status], 0
435
        mov     dword [esp+36], 5       ; not found
436
        ret
437
@@:
438
        mov     [fat32part], ecx
439
        push    ebx esi
440
        call    choice_necessity_partition_1
441
        pop     esi ebx
442
        mov     ecx, [ebx+12]
443
        mov     edx, [ebx+16]
444
        add     edx, std_application_base_address
445
        mov     eax, [ebx]
446
        cmp     eax, fs_NumHdServices
447
        jae     .not_impl
448
        add     ebx, 4
449
        call    dword [fs_HdServices + eax*4]
450
        call    free_hd_channel
451
        and     [hd1_status], 0
452
        mov     [esp+36], eax
453
        mov     [esp+24], ebx
454
        ret
455
.not_impl:
456
        call    free_hd_channel
457
        and     [hd1_status], 0
458
        mov     dword [esp+36], 2       ; not implemented
459
        ret
460
 
461
fs_HdServices:
462
        dd      fs_HdRead
463
        dd      fs_HdReadFolder
464
        dd      fs_HdRewrite
131 diamond 465
        dd      fs_HdWrite
133 diamond 466
        dd      fs_HdSetFileEnd
129 mikedld 467
        dd      fs_HdGetFileInfo
468
        dd      fs_HdSetFileInfo
384 mikedld 469
        dd      0 ;fs_HdExecute
470
        dd      fs_HdDelete
471
        dd      fs_HdCreateFolder
129 mikedld 472
fs_NumHdServices = ($ - fs_HdServices)/4
473
 
474
;*******************************************************
475
fs_OnCd0:
476
        call    reserve_cd
477
        mov  [ChannelNumber],1
478
        mov  [DiskNumber],0
479
        push    6
480
        jmp     fs_OnCd
481
fs_OnCd1:
482
        call    reserve_cd
483
        mov  [ChannelNumber],1
484
        mov  [DiskNumber],1
485
        push    4
486
        jmp     fs_OnCd
487
fs_OnCd2:
488
        call    reserve_cd
489
        mov  [ChannelNumber],2
490
        mov  [DiskNumber],0
491
        push    2
492
        jmp     fs_OnCd
493
fs_OnCd3:
494
        call    reserve_cd
495
        mov  [ChannelNumber],2
496
        mov  [DiskNumber],1
497
        push    0
498
fs_OnCd:
499
        call    reserve_cd_channel
500
        pop     eax
501
        mov     [hdpos], eax
502
        cmp     ecx, 0x100
503
        jae     .nf
133 diamond 504
        push    ecx ebx
129 mikedld 505
        mov     cl,al
506
        mov     bl,[0x40001]
507
        shr     bl,cl
508
        test    bl,2
133 diamond 509
        pop     ebx ecx
129 mikedld 510
 
511
        jnz     @f
512
.nf:
513
        call    free_cd_channel
514
        and    [cd_status], 0
515
        mov     dword [esp+36], 5       ; not found
516
        ret
517
@@:
518
        mov     ecx, [ebx+12]
519
        mov     edx, [ebx+16]
520
        add     edx, std_application_base_address
521
        mov     eax, [ebx]
522
        cmp     eax,fs_NumCdServices
523
        jae      .not_impl
524
        add     ebx, 4
525
        call    dword [fs_CdServices + eax*4]
526
        call    free_cd_channel
527
        and     [cd_status], 0
528
        mov     [esp+36], eax
529
        mov     [esp+24], ebx
530
        ret
531
.not_impl:
532
        call    free_cd_channel
533
        and     [cd_status], 0
534
        mov     dword [esp+36], 2       ; not implemented
535
        ret
536
 
537
fs_CdServices:
538
        dd      fs_CdRead
539
        dd      fs_CdReadFolder
540
        dd      fs_NotImplemented
541
        dd      fs_NotImplemented
542
        dd      fs_NotImplemented
543
        dd      fs_CdGetFileInfo
544
        dd      fs_NotImplemented
545
        dd      fs_CdExecute
546
fs_NumCdServices = ($ - fs_CdServices)/4
547
 
548
;*******************************************************
549
 
550
fs_HasRamdisk:
551
        mov     al, 1   ; we always have ramdisk
552
        ret
553
 
554
fs_HasFloppy:
384 mikedld 555
        cmp     byte [DRIVE_DATA], 0
129 mikedld 556
        setnz   al
557
        ret
558
 
559
fs_HasHd0:
384 mikedld 560
        mov     al, [DRIVE_DATA+1]
129 mikedld 561
        and     al, 11000000b
562
        cmp     al, 01000000b
563
        setz    al
564
        ret
565
fs_HasHd1:
384 mikedld 566
        mov     al, [DRIVE_DATA+1]
129 mikedld 567
        and     al, 00110000b
568
        cmp     al, 00010000b
569
        setz    al
570
        ret
571
fs_HasHd2:
384 mikedld 572
        mov     al, [DRIVE_DATA+1]
129 mikedld 573
        and     al, 00001100b
574
        cmp     al, 00000100b
575
        setz    al
576
        ret
577
fs_HasHd3:
384 mikedld 578
        mov     al, [DRIVE_DATA+1]
129 mikedld 579
        and     al, 00000011b
580
        cmp     al, 00000001b
581
        setz    al
582
        ret
583
 
584
;*******************************************************
585
fs_HasCd0:
384 mikedld 586
        mov     al, [DRIVE_DATA+1]
129 mikedld 587
        and     al, 11000000b
588
        cmp     al, 10000000b
589
        setz    al
590
        ret
591
fs_HasCd1:
384 mikedld 592
        mov     al, [DRIVE_DATA+1]
129 mikedld 593
        and     al, 00110000b
594
        cmp     al, 00100000b
595
        setz    al
596
        ret
597
fs_HasCd2:
384 mikedld 598
        mov     al, [DRIVE_DATA+1]
129 mikedld 599
        and     al, 00001100b
600
        cmp     al, 00001000b
601
        setz    al
602
        ret
603
fs_HasCd3:
384 mikedld 604
        mov     al, [DRIVE_DATA+1]
129 mikedld 605
        and     al, 00000011b
606
        cmp     al, 00000010b
607
        setz    al
608
        ret
384 mikedld 609
;*******************************************************
129 mikedld 610
 
611
; fs_NextXXX functions:
612
; in: eax = partition number, from which start to scan
613
; out: CF=1 => no more partitions
614
;      CF=0 => eax=next partition number
615
 
616
fs_NextRamdisk:
617
; we always have /rd/1
618
        test    eax, eax
619
        stc
620
        jnz     @f
621
        mov     al, 1
622
        clc
623
@@:
624
        ret
625
 
626
fs_NextFloppy:
384 mikedld 627
; we have /fd/1 iff (([DRIVE_DATA] and 0xF0) != 0) and /fd/2 iff (([DRIVE_DATA] and 0x0F) != 0)
628
        test    byte [DRIVE_DATA], 0xF0
129 mikedld 629
        jz      .no1
630
        test    eax, eax
631
        jnz     .no1
632
        inc     eax
633
        ret     ; CF cleared
634
.no1:
384 mikedld 635
        test    byte [DRIVE_DATA], 0x0F
129 mikedld 636
        jz      .no2
637
        cmp     al, 2
638
        jae     .no2
639
        mov     al, 2
640
        clc
641
        ret
642
.no2:
643
        stc
644
        ret
645
 
646
; on hdx, we have partitions from 1 to [0x40002+x]
647
fs_NextHd0:
648
        push    0
649
        jmp     fs_NextHd
650
fs_NextHd1:
651
        push    1
652
        jmp     fs_NextHd
653
fs_NextHd2:
654
        push    2
655
        jmp     fs_NextHd
656
fs_NextHd3:
657
        push    3
658
fs_NextHd:
659
        pop     ecx
384 mikedld 660
        movzx   ecx, byte [DRIVE_DATA+2+ecx]
129 mikedld 661
        cmp     eax, ecx
662
        jae     fs_NextFloppy.no2
663
        inc     eax
664
        clc
665
        ret
384 mikedld 666
 
129 mikedld 667
;*******************************************************
668
fs_NextCd:
669
; we always have /cdX/1
670
        test    eax, eax
671
        stc
672
        jnz     @f
673
        mov     al, 1
674
        clc
675
@@:
676
        ret
677
;*******************************************************
678