Subversion Repositories Kolibri OS

Rev

Rev 2089 | Rev 2455 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) KolibriOS team 2004-2008. All rights reserved. ;;
  4. ;; Distributed under terms of the GNU General Public License    ;;
  5. ;;                                                              ;;
  6. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  7.  
  8. $Revision: 2288 $
  9.  
  10.  
  11. uglobal
  12. cd_current_pointer_of_input    dd  0
  13. cd_current_pointer_of_input_2  dd  0
  14. cd_mem_location                dd  0
  15. cd_counter_block               dd  0
  16. IDE_Channel_1                  db  0
  17. IDE_Channel_2                  db  0
  18. endg
  19.  
  20. reserve_cd:
  21.  
  22.         cli
  23.         cmp     [cd_status], 0
  24.         je      reserve_ok2
  25.  
  26.         sti
  27.         call    change_task
  28.         jmp     reserve_cd
  29.  
  30.   reserve_ok2:
  31.  
  32.         push    eax
  33.         mov     eax, [CURRENT_TASK]
  34.         shl     eax, 5
  35.         mov     eax, [eax+CURRENT_TASK+TASKDATA.pid]
  36.         mov     [cd_status], eax
  37.         pop     eax
  38.         sti
  39.         ret
  40.  
  41. reserve_cd_channel:
  42.         cmp     [ChannelNumber], 1
  43.         jne     .IDE_Channel_2
  44. .IDE_Channel_1:
  45.         cli
  46.         cmp     [IDE_Channel_1], 0
  47.         je      .reserve_ok_1
  48.         sti
  49.         call    change_task
  50.         jmp     .IDE_Channel_1
  51. .IDE_Channel_2:
  52.         cli
  53.         cmp     [IDE_Channel_2], 0
  54.         je      .reserve_ok_2
  55.         sti
  56.         call    change_task
  57.         jmp     .IDE_Channel_2
  58. .reserve_ok_1:
  59.         mov     [IDE_Channel_1], 1
  60.         sti
  61.         ret
  62. .reserve_ok_2:
  63.         mov     [IDE_Channel_2], 1
  64.         sti
  65.         ret
  66.  
  67. free_cd_channel:
  68.         cmp     [ChannelNumber], 1
  69.         jne     .IDE_Channel_2
  70. .IDE_Channel_1:
  71.         mov     [IDE_Channel_1], 0
  72.         sti
  73.         ret
  74. .IDE_Channel_2:
  75.         mov     [IDE_Channel_2], 0
  76.         sti
  77.         ret
  78.  
  79. uglobal
  80. cd_status dd 0
  81. endg
  82.  
  83. ;----------------------------------------------------------------
  84. ;
  85. ;  fs_CdRead - LFN variant for reading CD disk
  86. ;
  87. ;  esi  points to filename /dir1/dir2/.../dirn/file,0
  88. ;  ebx  pointer to 64-bit number = first wanted byte, 0+
  89. ;       may be ebx=0 - start from first byte
  90. ;  ecx  number of bytes to read, 0+
  91. ;  edx  mem location to return data
  92. ;
  93. ;  ret ebx = bytes read or 0xffffffff file not found
  94. ;      eax = 0 ok read or other = errormsg
  95. ;
  96. ;--------------------------------------------------------------
  97. fs_CdRead:
  98.         push    edi
  99.         cmp     byte [esi], 0
  100.         jnz     @f
  101. .noaccess:
  102.         pop     edi
  103. .noaccess_2:
  104.         or      ebx, -1
  105.         mov     eax, ERROR_ACCESS_DENIED
  106.         ret
  107.  
  108. .noaccess_3:
  109.         pop     eax edx ecx edi
  110.         jmp     .noaccess_2
  111.  
  112. @@:
  113.         call    cd_find_lfn
  114.         jnc     .found
  115.         pop     edi
  116.         cmp     [DevErrorCode], 0
  117.         jne     .noaccess_2
  118.         or      ebx, -1
  119.         mov     eax, ERROR_FILE_NOT_FOUND
  120.         ret
  121.  
  122. .found:
  123.         mov     edi, [cd_current_pointer_of_input]
  124.         test    byte [edi+25], 10b; do not allow read directories
  125.         jnz     .noaccess
  126.         test    ebx, ebx
  127.         jz      .l1
  128.         cmp     dword [ebx+4], 0
  129.         jz      @f
  130.         xor     ebx, ebx
  131. .reteof:
  132.         mov     eax, 6; end of file
  133.         pop     edi
  134.         ret
  135. @@:
  136.         mov     ebx, [ebx]
  137. .l1:
  138.         push    ecx edx
  139.         push    0
  140.         mov     eax, [edi+10] ; ðåàëüíûé ðàçìåð ôàéëîâîé ñåêöèè
  141.         sub     eax, ebx
  142.         jb      .eof
  143.         cmp     eax, ecx
  144.         jae     @f
  145.         mov     ecx, eax
  146.         mov     byte [esp], 6
  147. @@:
  148.         mov     eax, [edi+2]
  149.         mov     [CDSectorAddress], eax
  150. ; now eax=cluster, ebx=position, ecx=count, edx=buffer for data
  151. .new_sector:
  152.         test    ecx, ecx
  153.         jz      .done
  154.         sub     ebx, 2048
  155.         jae     .next
  156.         add     ebx, 2048
  157.         jnz     .incomplete_sector
  158.         cmp     ecx, 2048
  159.         jb      .incomplete_sector
  160. ; we may read and memmove complete sector
  161.         mov     [CDDataBuf_pointer], edx
  162.         call    ReadCDWRetr; ÷èòàåì ñåêòîð ôàéëà
  163.         cmp     [DevErrorCode], 0
  164.         jne     .noaccess_3
  165.         add     edx, 2048
  166.         sub     ecx, 2048
  167. .next:
  168.         inc     dword [CDSectorAddress]
  169.         jmp     .new_sector
  170. .incomplete_sector:
  171. ; we must read and memmove incomplete sector
  172.         mov     [CDDataBuf_pointer], CDDataBuf
  173.         call    ReadCDWRetr; ÷èòàåì ñåêòîð ôàéëà
  174.         cmp     [DevErrorCode], 0
  175.         jne     .noaccess_3
  176.         push    ecx
  177.         add     ecx, ebx
  178.         cmp     ecx, 2048
  179.         jbe     @f
  180.         mov     ecx, 2048
  181. @@:
  182.         sub     ecx, ebx
  183.         push    edi esi ecx
  184.         mov     edi, edx
  185.         lea     esi, [CDDataBuf + ebx]
  186.         cld
  187.         rep movsb
  188.         pop     ecx esi edi
  189.         add     edx, ecx
  190.         sub     [esp], ecx
  191.         pop     ecx
  192.         xor     ebx, ebx
  193.         jmp     .next
  194.  
  195. .done:
  196.         mov     ebx, edx
  197.         pop     eax edx ecx edi
  198.         sub     ebx, edx
  199.         ret
  200. .eof:
  201.         mov     ebx, edx
  202.         pop     eax edx ecx
  203.         sub     ebx, edx
  204.         jmp     .reteof
  205.  
  206. ;----------------------------------------------------------------
  207. ;
  208. ;  fs_CdReadFolder - LFN variant for reading CD disk folder
  209. ;
  210. ;  esi  points to filename  /dir1/dir2/.../dirn/file,0
  211. ;  ebx  pointer to structure 32-bit number = first wanted block, 0+
  212. ;                          & flags (bitfields)
  213. ; flags: bit 0: 0=ANSI names, 1=UNICODE names
  214. ;  ecx  number of blocks to read, 0+
  215. ;  edx  mem location to return data
  216. ;
  217. ;  ret ebx = blocks read or 0xffffffff folder not found
  218. ;      eax = 0 ok read or other = errormsg
  219. ;
  220. ;--------------------------------------------------------------
  221. fs_CdReadFolder:
  222.         push    edi
  223.         call    cd_find_lfn
  224.         jnc     .found
  225.         pop     edi
  226.         cmp     [DevErrorCode], 0
  227.         jne     .noaccess_1
  228.         or      ebx, -1
  229.         mov     eax, ERROR_FILE_NOT_FOUND
  230.         ret
  231. .found:
  232.         mov     edi, [cd_current_pointer_of_input]
  233.         test    byte [edi+25], 10b    ; do not allow read directories
  234.         jnz     .found_dir
  235.         pop     edi
  236. .noaccess_1:
  237.         or      ebx, -1
  238.         mov     eax, ERROR_ACCESS_DENIED
  239.         ret
  240. .found_dir:
  241.         mov     eax, [edi+2]    ; eax=cluster
  242.         mov     [CDSectorAddress], eax
  243.         mov     eax, [edi+10]   ; ðàçìåð äèðåêòðîðèè
  244. .doit:
  245. ; init header
  246.         push    eax ecx
  247.         mov     edi, edx
  248.         mov     ecx, 32/4
  249.         xor     eax, eax
  250.         rep stosd
  251.         pop     ecx eax
  252.         mov     byte [edx], 1   ; version
  253.         mov     [cd_mem_location], edx
  254.         add     [cd_mem_location], 32
  255. ; íà÷èíàåì ïåðåáðîñêó ÁÄÂÊ â ÓÑÂÊ
  256. ;.mainloop:
  257.         mov     [cd_counter_block], dword 0
  258.         dec     dword [CDSectorAddress]
  259.         push    ecx
  260. .read_to_buffer:
  261.         inc     dword [CDSectorAddress]
  262.         mov     [CDDataBuf_pointer], CDDataBuf
  263.         call    ReadCDWRetr         ; ÷èòàåì ñåêòîð äèðåêòîðèè
  264.         cmp     [DevErrorCode], 0
  265.         jne     .noaccess_1
  266.         call    .get_names_from_buffer
  267.         sub     eax, 2048
  268. ; äèðåêòîðèÿ çàêîí÷èëàñü?
  269.         ja      .read_to_buffer
  270.         mov     edi, [cd_counter_block]
  271.         mov     [edx+8], edi
  272.         mov     edi, [ebx]
  273.         sub     [edx+4], edi
  274.         xor     eax, eax
  275.         dec     ecx
  276.         js      @f
  277.         mov     al, ERROR_END_OF_FILE
  278. @@:
  279.         pop     ecx edi
  280.         mov     ebx, [edx+4]
  281.         ret
  282.  
  283. .get_names_from_buffer:
  284.         mov     [cd_current_pointer_of_input_2], CDDataBuf
  285.         push    eax esi edi edx
  286. .get_names_from_buffer_1:
  287.         call    cd_get_name
  288.         jc      .end_buffer
  289.         inc     dword [cd_counter_block]
  290.         mov     eax, [cd_counter_block]
  291.         cmp     [ebx], eax
  292.         jae     .get_names_from_buffer_1
  293.         test    ecx, ecx
  294.         jz      .get_names_from_buffer_1
  295.         mov     edi, [cd_counter_block]
  296.         mov     [edx+4], edi
  297.         dec     ecx
  298.         mov     esi, ebp
  299.         mov     edi, [cd_mem_location]
  300.         add     edi, 40
  301.         test    dword [ebx+4], 1; 0=ANSI, 1=UNICODE
  302.         jnz     .unicode
  303. ;    jmp  .unicode
  304. .ansi:
  305.         cmp     [cd_counter_block], 2
  306.         jbe     .ansi_parent_directory
  307.         cld
  308.         lodsw
  309.         xchg    ah, al
  310.         call    uni2ansi_char
  311.         cld
  312.         stosb
  313. ; ïðîâåðêà êîíöà ôàéëà
  314.         mov     ax, [esi]
  315.         cmp     ax, word 3B00h; ñåïàðàòîð êîíöà ôàéëà ';'
  316.         je      .cd_get_parameters_of_file_1
  317. ; ïðîâåðêà äëÿ ôàéëîâ íå çàêàí÷èâàþùèõñÿ ñåïàðàòîðîì
  318.         movzx   eax, byte [ebp-33]
  319.         add     eax, ebp
  320.         sub     eax, 34
  321.         cmp     esi, eax
  322.         je      .cd_get_parameters_of_file_1
  323. ; ïðîâåðêà êîíöà ïàïêè
  324.         movzx   eax, byte [ebp-1]
  325.         add     eax, ebp
  326.         cmp     esi, eax
  327.         jb      .ansi
  328. .cd_get_parameters_of_file_1:
  329.         mov     [edi], byte 0
  330.         call    cd_get_parameters_of_file
  331.         add     [cd_mem_location], 304
  332.         jmp     .get_names_from_buffer_1
  333.  
  334. .ansi_parent_directory:
  335.         cmp     [cd_counter_block], 2
  336.         je      @f
  337.         mov     [edi], byte '.'
  338.         inc     edi
  339.         jmp     .cd_get_parameters_of_file_1
  340. @@:
  341.         mov     [edi], word '..'
  342.         add     edi, 2
  343.         jmp     .cd_get_parameters_of_file_1
  344.  
  345. .unicode:
  346.         cmp     [cd_counter_block], 2
  347.         jbe     .unicode_parent_directory
  348.         cld
  349.         movsw
  350. ; ïðîâåðêà êîíöà ôàéëà
  351.         mov     ax, [esi]
  352.         cmp     ax, word 3B00h; ñåïàðàòîð êîíöà ôàéëà ';'
  353.         je      .cd_get_parameters_of_file_2
  354. ; ïðîâåðêà äëÿ ôàéëîâ íå çàêàí÷èâàþùèõñÿ ñåïàðàòîðîì
  355.         movzx   eax, byte [ebp-33]
  356.         add     eax, ebp
  357.         sub     eax, 34
  358.         cmp     esi, eax
  359.         je      .cd_get_parameters_of_file_2
  360. ; ïðîâåðêà êîíöà ïàïêè
  361.         movzx   eax, byte [ebp-1]
  362.         add     eax, ebp
  363.         cmp     esi, eax
  364.         jb      .unicode
  365. .cd_get_parameters_of_file_2:
  366.         mov     [edi], word 0
  367.         call    cd_get_parameters_of_file
  368.         add     [cd_mem_location], 560
  369.         jmp     .get_names_from_buffer_1
  370.  
  371. .unicode_parent_directory:
  372.         cmp     [cd_counter_block], 2
  373.         je      @f
  374.         mov     [edi], word 2E00h; '.'
  375.         add     edi, 2
  376.         jmp     .cd_get_parameters_of_file_2
  377. @@:
  378.         mov     [edi], dword 2E002E00h; '..'
  379.         add     edi, 4
  380.         jmp     .cd_get_parameters_of_file_2
  381.  
  382. .end_buffer:
  383.         pop     edx edi esi eax
  384.         ret
  385.  
  386. cd_get_parameters_of_file:
  387.         mov     edi, [cd_mem_location]
  388. cd_get_parameters_of_file_1:
  389. ; ïîëó÷àåì àòðèáóòû ôàéëà
  390.         xor     eax, eax
  391. ; ôàéë íå àðõèâèðîâàëñÿ
  392.         inc     eax
  393.         shl     eax, 1
  394. ; ýòî êàòàëîã?
  395.         test    [ebp-8], byte 2
  396.         jz      .file
  397.         inc     eax
  398. .file:
  399. ; ìåòêà òîìà íå êàê â FAT, â ýòîì âèäå îòñóòñâóåò
  400. ; ôàéë íå ÿâëÿåòñÿ ñèñòåìíûì
  401.         shl     eax, 3
  402. ; ôàéë ÿâëÿåòñÿ ñêðûòûì? (àòðèáóò ñóùåñòâîâàíèå)
  403.         test    [ebp-8], byte 1
  404.         jz      .hidden
  405.         inc     eax
  406. .hidden:
  407.         shl     eax, 1
  408. ; ôàéë âñåãäà òîëüêî äëÿ ÷òåíèÿ, òàê êàê ýòî CD
  409.         inc     eax
  410.         mov     [edi], eax
  411. ; ïîëó÷àåì âðåìÿ äëÿ ôàéëà
  412. ;÷àñ
  413.         movzx   eax, byte [ebp-12]
  414.         shl     eax, 8
  415. ;ìèíóòà
  416.         mov     al, [ebp-11]
  417.         shl     eax, 8
  418. ;ñåêóíäà
  419.         mov     al, [ebp-10]
  420. ;âðåìÿ ñîçäàíèÿ ôàéëà
  421.         mov     [edi+8], eax
  422. ;âðåìÿ ïîñëåäíåãî äîñòóïà
  423.         mov     [edi+16], eax
  424. ;âðåìÿ ïîñëåäíåé çàïèñè
  425.         mov     [edi+24], eax
  426. ; ïîëó÷àåì äàòó äëÿ ôàéëà
  427. ;ãîä
  428.         movzx   eax, byte [ebp-15]
  429.         add     eax, 1900
  430.         shl     eax, 8
  431. ;ìåñÿö
  432.         mov     al, [ebp-14]
  433.         shl     eax, 8
  434. ;äåíü
  435.         mov     al, [ebp-13]
  436. ;äàòà ñîçäàíèÿ ôàéëà
  437.         mov     [edi+12], eax
  438. ;âðåìÿ ïîñëåäíåãî äîñòóïà
  439.         mov     [edi+20], eax
  440. ;âðåìÿ ïîñëåäíåé çàïèñè
  441.         mov     [edi+28], eax
  442. ; ïîëó÷àåì òèï äàííûõ èìåíè
  443.         xor     eax, eax
  444.         test    dword [ebx+4], 1; 0=ANSI, 1=UNICODE
  445.         jnz     .unicode_1
  446.         mov     [edi+4], eax
  447.         jmp     @f
  448. .unicode_1:
  449.         inc     eax
  450.         mov     [edi+4], eax
  451. @@:
  452. ; ïîëó÷àåì ðàçìåð ôàéëà â áàéòàõ
  453.         xor     eax, eax
  454.         mov     [edi+32+4], eax
  455.         mov     eax, [ebp-23]
  456.         mov     [edi+32], eax
  457.         ret
  458.  
  459. ;----------------------------------------------------------------
  460. ;
  461. ;  fs_CdGetFileInfo - LFN variant for CD
  462. ;                     get file/directory attributes structure
  463. ;
  464. ;----------------------------------------------------------------
  465. fs_CdGetFileInfo:
  466.         cmp     byte [esi], 0
  467.         jnz     @f
  468.         mov     eax, 2
  469.         ret
  470. @@:
  471.         push    edi
  472.         call    cd_find_lfn
  473.         pushfd
  474.         cmp     [DevErrorCode], 0
  475.         jz      @f
  476.         popfd
  477.         pop     edi
  478.         mov     eax, 11
  479.         ret
  480. @@:
  481.         popfd
  482.         jnc     @f
  483.         pop     edi
  484.         mov     eax, ERROR_FILE_NOT_FOUND
  485.         ret
  486. @@:
  487.  
  488.         mov     edi, edx
  489.         push    ebp
  490.         mov     ebp, [cd_current_pointer_of_input]
  491.         add     ebp, 33
  492.         call    cd_get_parameters_of_file_1
  493.         pop     ebp
  494.         and     dword [edi+4], 0
  495.         pop     edi
  496.         xor     eax, eax
  497.         ret
  498.  
  499. ;----------------------------------------------------------------
  500. cd_find_lfn:
  501.         mov     [cd_appl_data], 0
  502. ; in: esi+ebp -> name
  503. ; out: CF=1 - file not found
  504. ; else CF=0 and [cd_current_pointer_of_input] direntry
  505.         push    eax esi
  506. ; 16 ñåêòîð íà÷àëî íàáîðà äåñêðèïòîðîâ òîìîâ
  507.  
  508.         call    WaitUnitReady
  509.         cmp     [DevErrorCode], 0
  510.         jne     .access_denied
  511.  
  512.         call    prevent_medium_removal
  513. ; òåñòîâîå ÷òåíèå
  514.         mov     [CDSectorAddress], dword 16
  515.         mov     [CDDataBuf_pointer], CDDataBuf
  516.         call    ReadCDWRetr;_1
  517.         cmp     [DevErrorCode], 0
  518.         jne     .access_denied
  519.  
  520. ; âû÷èñëåíèå ïîñëåäíåé ñåññèè
  521.         call    WaitUnitReady
  522.         cmp     [DevErrorCode], 0
  523.         jne     .access_denied
  524.         call    Read_TOC
  525.         mov     ah, [CDDataBuf+4+4]
  526.         mov     al, [CDDataBuf+4+5]
  527.         shl     eax, 16
  528.         mov     ah, [CDDataBuf+4+6]
  529.         mov     al, [CDDataBuf+4+7]
  530.         add     eax, 15
  531.         mov     [CDSectorAddress], eax
  532. ;  mov  [CDSectorAddress],dword 15
  533.         mov     [CDDataBuf_pointer], CDDataBuf
  534.  
  535. .start:
  536.         inc     dword [CDSectorAddress]
  537.         call    ReadCDWRetr;_1
  538.         cmp     [DevErrorCode], 0
  539.         jne     .access_denied
  540.  
  541. .start_check:
  542. ; ïðîâåðêà íà âøèâîñòü
  543.         cmp     [CDDataBuf+1], dword 'CD00'
  544.         jne     .access_denied
  545.         cmp     [CDDataBuf+5], byte '1'
  546.         jne     .access_denied
  547. ; ñåêòîð ÿâëÿåòñÿ òåðìèíàòîðîì íàáîð äåñêðèïòîðîâ òîìîâ?
  548.         cmp     [CDDataBuf], byte 0xff
  549.         je      .access_denied
  550. ; ñåêòîð ÿâëÿåòñÿ äîïîëíèòåëüíûì è óëó÷øåííûì äåñêðèïòîðîì òîìà?
  551.         cmp     [CDDataBuf], byte 0x2
  552.         jne     .start
  553. ; ñåêòîð ÿâëÿåòñÿ äîïîëíèòåëüíûì äåñêðèïòîðîì òîìà?
  554.         cmp     [CDDataBuf+6], byte 0x1
  555.         jne     .start
  556.  
  557. ; ïàðàìåòðû root äèðåêòðîðèè
  558.         mov     eax, [CDDataBuf+0x9c+2]; íà÷àëî root äèðåêòðîðèè
  559.         mov     [CDSectorAddress], eax
  560.         mov     eax, [CDDataBuf+0x9c+10]; ðàçìåð root äèðåêòðîðèè
  561.         cmp     byte [esi], 0
  562.         jnz     @f
  563.         mov     [cd_current_pointer_of_input], CDDataBuf+0x9c
  564.         jmp     .done
  565. @@:
  566. ; íà÷èíàåì ïîèñê
  567. .mainloop:
  568.         dec     dword [CDSectorAddress]
  569. .read_to_buffer:
  570.         inc     dword [CDSectorAddress]
  571.         mov     [CDDataBuf_pointer], CDDataBuf
  572.         call    ReadCDWRetr      ; ÷èòàåì ñåêòîð äèðåêòîðèè
  573.         cmp     [DevErrorCode], 0
  574.         jne     .access_denied
  575.         push    ebp
  576.         call    cd_find_name_in_buffer
  577.         pop     ebp
  578.         jnc     .found
  579.         sub     eax, 2048
  580. ; äèðåêòîðèÿ çàêîí÷èëàñü?
  581.         cmp     eax, 0
  582.         ja      .read_to_buffer
  583. ; íåò èñêîìîãî ýëåìåíòà öåïî÷êè
  584. .access_denied:
  585.         pop     esi eax
  586.         mov     [cd_appl_data], 1
  587.         stc
  588.         ret
  589. ; èñêîìûé ýëåìåíò öåïî÷êè íàéäåí
  590.   .found:
  591. ; êîíåö ïóòè ôàéëà
  592.         cmp     byte [esi-1], 0
  593.         jz      .done
  594.   .nested:
  595.         mov     eax, [cd_current_pointer_of_input]
  596.         push    dword [eax+2]
  597.         pop     dword [CDSectorAddress]       ; íà÷àëî äèðåêòîðèè
  598.         mov     eax, [eax+2+8]; ðàçìåð äèðåêòîðèè
  599.         jmp     .mainloop
  600. ; óêàçàòåëü ôàéëà íàéäåí
  601.    .done:
  602.         test    ebp, ebp
  603.         jz      @f
  604.         mov     esi, ebp
  605.         xor     ebp, ebp
  606.         jmp     .nested
  607. @@:
  608.         pop     esi eax
  609.         mov     [cd_appl_data], 1
  610.         clc
  611.         ret
  612.  
  613. cd_find_name_in_buffer:
  614.         mov     [cd_current_pointer_of_input_2], CDDataBuf
  615. .start:
  616.         call    cd_get_name
  617.         jc      .not_found
  618.         call    cd_compare_name
  619.         jc      .start
  620. .found:
  621.         clc
  622.         ret
  623. .not_found:
  624.         stc
  625.         ret
  626.  
  627. cd_get_name:
  628.         push    eax
  629.         mov     ebp, [cd_current_pointer_of_input_2]
  630.         mov     [cd_current_pointer_of_input], ebp
  631.         mov     eax, [ebp]
  632.         test    eax, eax ; âõîäû çàêîí÷èëèñü?
  633.         jz      .next_sector
  634.         cmp     ebp, CDDataBuf+2048  ; áóôåð çàêîí÷èëñÿ?
  635.         jae     .next_sector
  636.         movzx   eax, byte [ebp]
  637.         add     [cd_current_pointer_of_input_2], eax; ñëåäóþùèé âõîä êàòàëîãà
  638.         add     ebp, 33; óêàçàòåëü óñòàíîâëåí íà íà÷àëî èìåíè
  639.         pop     eax
  640.         clc
  641.         ret
  642. .next_sector:
  643.         pop     eax
  644.         stc
  645.         ret
  646.  
  647. cd_compare_name:
  648. ; compares ASCIIZ-names, case-insensitive (cp866 encoding)
  649. ; in: esi->name, ebp->name
  650. ; out: if names match: ZF=1 and esi->next component of name
  651. ;      else: ZF=0, esi is not changed
  652. ; destroys eax
  653.         push    esi eax edi
  654.         mov     edi, ebp
  655. .loop:
  656.         cld
  657.         lodsb
  658.         push    eax
  659.         call    char_todown
  660.         call    ansi2uni_char
  661.         xchg    ah, al
  662.         scasw
  663.         pop     eax
  664.         je      .coincides
  665.         call    char_toupper
  666.         call    ansi2uni_char
  667.         xchg    ah, al
  668.         sub     edi, 2
  669.         scasw
  670.         jne     .name_not_coincide
  671. .coincides:
  672.         cmp     [esi], byte '/'; ðàçäåëèòåëü ïóòè, êîíåö èìåíè òåêóùåãî ýëåìåíòà
  673.         je      .done
  674.         cmp     [esi], byte 0; ðàçäåëèòåëü ïóòè, êîíåö èìåíè òåêóùåãî ýëåìåíòà
  675.         je      .done
  676.         jmp     .loop
  677. .name_not_coincide:
  678.         pop     edi eax esi
  679.         stc
  680.         ret
  681. .done:
  682. ; ïðîâåðêà êîíöà ôàéëà
  683.         cmp     [edi], word 3B00h; ñåïàðàòîð êîíöà ôàéëà ';'
  684.         je      .done_1
  685. ; ïðîâåðêà äëÿ ôàéëîâ íå çàêàí÷èâàþùèõñÿ ñåïàðàòîðîì
  686.         movzx   eax, byte [ebp-33]
  687.         add     eax, ebp
  688.         sub     eax, 34
  689.         cmp     edi, eax
  690.         je      .done_1
  691. ; ïðîâåðêà êîíöà ïàïêè
  692.         movzx   eax, byte [ebp-1]
  693.         add     eax, ebp
  694.         cmp     edi, eax
  695.         jne     .name_not_coincide
  696. .done_1:
  697.         pop     edi eax
  698.         add     esp, 4
  699.         inc     esi
  700.         clc
  701.         ret
  702.  
  703. char_todown:
  704. ; convert character to uppercase, using cp866 encoding
  705. ; in: al=symbol
  706. ; out: al=converted symbol
  707.         cmp     al, 'A'
  708.         jb      .ret
  709.         cmp     al, 'Z'
  710.         jbe     .az
  711.         cmp     al, '€'
  712.         jb      .ret
  713.         cmp     al, ''
  714.         jb      .rus1
  715.         cmp     al, 'Ÿ'
  716.         ja      .ret
  717. ; 0x90-0x9F -> 0xE0-0xEF
  718.         add     al, 'à'-''
  719. .ret:
  720.         ret
  721. .rus1:
  722. ; 0x80-0x8F -> 0xA0-0xAF
  723. .az:
  724.         add     al, 0x20
  725.         ret
  726.  
  727. uni2ansi_char:
  728. ; convert UNICODE character in al to ANSI character in ax, using cp866 encoding
  729. ; in: ax=UNICODE character
  730. ; out: al=converted ANSI character
  731.         cmp     ax, 0x80
  732.         jb      .ascii
  733.         cmp     ax, 0x401
  734.         jz      .yo1
  735.         cmp     ax, 0x451
  736.         jz      .yo2
  737.         cmp     ax, 0x410
  738.         jb      .unk
  739.         cmp     ax, 0x440
  740.         jb      .rus1
  741.         cmp     ax, 0x450
  742.         jb      .rus2
  743. .unk:
  744.         mov     al, '_'
  745.         jmp     .doit
  746. .yo1:
  747.         mov     al, 'ð'
  748.         jmp     .doit
  749. .yo2:
  750.         mov     al, 'ñ'
  751.         jmp     .doit
  752. .rus1:
  753. ; 0x410-0x43F -> 0x80-0xAF
  754.         add     al, 0x70
  755.         jmp     .doit
  756. .rus2:
  757. ; 0x440-0x44F -> 0xE0-0xEF
  758.         add     al, 0xA0
  759. .ascii:
  760. .doit:
  761.         ret
  762.