Subversion Repositories Kolibri OS

Rev

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