home *** CD-ROM | disk | FTP | other *** search
/ PC World 2002 February / PCWorld_2002-02_cd.bin / Software / Vyzkuste / ranish / SOURCES.ZIP / FAT_BOOT.ASM < prev    next >
Assembly Source File  |  1998-07-05  |  5KB  |  279 lines

  1. .MODEL LARGE
  2. .DATA
  3. .CODE
  4. LOCALS
  5. PUBLIC    _FAT_BOOT
  6. _FAT_BOOT    PROC    NEAR
  7.     ;
  8.     ;  MBR loads BOOT at 0000:7C00h
  9.     ;
  10.     jmp    short @@xcode
  11.     nop
  12.     ;
  13. RESERVD    DB    59 Dup(?)
  14.     ;
  15. @@xcode:
  16.     xor    ax, ax
  17.     mov    ds, ax
  18.     mov    es, ax
  19.     mov    ss, ax        ;  CPU clears interrupt flag for next command
  20.     mov    sp, 7C00h
  21.     ;
  22.     mov    bp, sp
  23.     mov    [bp+24h], dl    ; Save disk number
  24.  
  25.     mov    al, 20h            ; 32 bytes in each directory entry
  26.     mul    word ptr [bp+11h]    ; number of entries in root directory
  27.     div    word ptr [bp+0Bh]    ; sector size
  28.     mov    cx, ax            ; number of sectors in root directory
  29.  
  30.     mov    al, [bp+10h]        ; Number of FATs
  31.     cbw
  32.     mul    word ptr [bp+16h]    ; Size of the FAT
  33.     add    ax, [bp+0Eh]        ; Reserved Sectors
  34.     adc    dx, 0
  35.     add    ax, [bp+1Ch]        ; Hidden sectors
  36.     adc    dx, [bp+1Eh]
  37.  
  38.     push    cx
  39.     mov    bx, 0500h        ; Lets read root dir to that address
  40.     mov    cx, 1
  41.     call    READ_N_SECT        ; Reading 1 sector to make DOS happy
  42.     pop    cx
  43.  
  44.     mov    bx, 8000h        ; Here we have enought space for large
  45.                     ; root directory (more than 944 entr.)
  46.  
  47.     call    READ_N_SECT        ; Reading CX sectors to address BX
  48.     jb    @@print_error        ; starting with sector DX:AX
  49.  
  50.     add    ax, cx
  51.     adc    dx, 0
  52.  
  53.     push    dx    ; Now DX:AX is the first sector of the first cluster
  54.     push    ax
  55.  
  56.     ; Looking for WINBOOT.SYS, IO.SYS, ...
  57.  
  58.     lea    di, [bp+(IO_SYS-_FAT_BOOT)]
  59. @@next_name:
  60.     mov    si, bx
  61.     cmp    Byte Ptr [di], 0
  62.     je    @@print_error
  63.     mov    cx, [bp+11h]    ; number of entries in root directory
  64. @@next_entr:
  65.     push    si
  66.     push    di
  67.     push    cx
  68.     mov    cx, 0Bh
  69.     repz
  70.      cmpsb
  71.     pop    cx
  72.     pop    di
  73.     pop    si
  74.     jz    @@found
  75.     add    si, 20h
  76.     loop    @@next_entr
  77.     add    di, 0Bh
  78.     jmp    @@next_name
  79. @@found:
  80.     push    ax
  81.     push    dx
  82.  
  83.     mov    di, [si+1Ah]    ; first cluster in file
  84.     lea    ax, [di-2]
  85.     jc    @@print_error
  86.     mov    dl, [bp+0Dh]    ; cluster size
  87.     mov    dh, 0
  88.     mul    dx
  89.  
  90.     pop    cx
  91.     pop    bx
  92.     add    ax, bx
  93.     adc    dx, cx
  94.  
  95.     mov    bx, 0700h
  96.     mov    cx, 4
  97.  
  98.     call    READ_N_SECT
  99.  
  100.     jb    @@print_error
  101.  
  102.     cmp    word ptr [bx], 5A4Dh    ; "MZ"
  103.     je    @@win95
  104.     
  105.     pop    bx    ;ax
  106.     pop    ax    ;dx
  107.  
  108.     mov    ch, [bp+15h]    ; Media descriptor byte
  109.     mov    dl, [bp+24h]    ; Hard drive number
  110. @@dos:
  111. ;    jmp    0070:0000
  112.         DB    0EAh
  113.         DW    0000, 0070h
  114.  
  115. @@win95:
  116.     mov    bx, 0078h    ; IO.SYS expects to see all this garbage.
  117.     lds    si, [bx]    ; Plus it's cluster number in DI and
  118.     push    ds        ; it's relative sector in [bp-02]:[bp-04].
  119.     push    si
  120.     push    ss
  121.     push    bx
  122.     lea    si, [bp+(NULL00-_FAT_BOOT)]
  123. ;    jmp    0070:0200
  124.         DB    0EAh
  125.         DW    200h, 0070h
  126.     ;
  127.     ; Print error, wait for key, reboot.
  128.     ;
  129. @@print_error:
  130.     lea    si, [bp+(ERRMSG-_FAT_BOOT)]
  131.     mov    ah, 0Eh
  132.     mov    bx, 0007h
  133. @@pr1:
  134.     lodsb
  135.     or    al, al
  136.     jz    @@pr2
  137.     int    10h
  138.     jmp    @@pr1
  139. @@pr2:
  140.     xor    ax, ax
  141.     int    16h
  142.     int    19h
  143. _FAT_BOOT    ENDP
  144.     ;
  145.     ;
  146.     ;
  147. READ_N_SECT    PROC    NEAR
  148.         ;
  149.         ;
  150.         ;    ES:BX - Destination address
  151.         ;    DX:AX - Relative sector on disk
  152.         ;    CX    - Number of sectors to read
  153.         ;
  154.         ;    Returns: Flag CF set if error
  155.         ;
  156.         push    ax
  157.         push    bx
  158.         push    cx
  159.         push    dx
  160.  
  161. @@next_sect:
  162.         call    READ_SECT
  163.         jb    @@end
  164.  
  165.         add    ax, 1
  166.         adc    dx, 0
  167.  
  168.         add    bx, [bp+0Bh]    ; Sector size
  169.  
  170.         loop    @@next_sect
  171. @@end:
  172.         pop    dx
  173.         pop    cx
  174.         pop    bx
  175.         pop    ax
  176.         ret
  177. READ_N_SECT    ENDP
  178.         ;
  179.         ;
  180.         ;
  181. READ_SECT    PROC    NEAR
  182.         ;
  183.         ;
  184.         ;    ES:BX - Destination address
  185.         ;    DX:AX - Relative sector on disk
  186.         ;
  187.         ;    Returns: Flag CF set if error
  188.         ;
  189.         push    si
  190.         push    di
  191.         push    bx
  192.         push    cx
  193.         push    dx
  194.         push    ax
  195.  
  196.         mov    cx, 3
  197.         push    cx
  198. @@next_try:
  199.         mov    ah, 08        ; Get disk parameters
  200.         mov    dl, [bp+24h]    ; Hard disk number
  201.         int    13h
  202.         jb    @@reset
  203.  
  204.         mov    ah, 0
  205.         mov    al, dh
  206.         inc    ax        ; Number of heads / cylinder
  207.         and    cx, 3Fh
  208.         mov    di, cx        ; Number of sectors / head
  209.         mul    cx
  210.         mov    si, ax        ; Number of sectors / cylinder
  211.  
  212.         pop    cx
  213.         pop    ax        ; Rel sect low
  214.         pop    dx        ; Rel sect high
  215.         push    dx
  216.         push    ax
  217.         push    cx
  218.  
  219.         div    si    ; Now ax=cylinder, dx=sector on cylinder
  220.         mov    cx, ax
  221.         shr    cx, 1
  222.         shr    cx, 1
  223.         and    cl, 0C0h
  224.         mov    ch, al
  225.         mov    ax, dx
  226.         xor    dx, dx
  227.         div    di    ; Now ax=head, dx=sector on head
  228.         mov    dh, al
  229.         inc    dl
  230.         and    dl, 3Fh
  231.         or    cl, dl
  232.         mov    dl, [bp+24h]    ; Hard disk number
  233.         mov    ax, 0201h    ; Read (AH=02) 1 Sector (AL=01)
  234.         int    13h
  235.         jnb    @@end
  236. @@reset:
  237.         pop    cx
  238.         dec    cx
  239.         push    cx
  240.         jb    @@end
  241.         
  242.         mov    ax, 0
  243.         int    13h
  244.         jmp    @@next_try
  245. @@end:
  246.         pop    cx
  247.         pop    ax
  248.         pop    dx
  249.         pop    cx
  250.         pop    bx
  251.         pop    di
  252.         pop    si
  253.         ret
  254. READ_SECT    ENDP
  255.     ;
  256.     ;
  257.     ;
  258. ERRMSG:    DB 0Dh,0Ah,"Non-system disk or error."
  259.     DB 0Dh,0Ah,"Hit a key to reboot ... "
  260. NULL00:    DB 0,0
  261.     ;
  262.     ;  "1234567 123"
  263. IO_SYS:    
  264.     DB "WINBOOT SYS"
  265.     DB "IO      SYS"
  266.     DB 0
  267.     ;
  268.  
  269. GAP    PROC
  270. GAPLEN    EQU    (1FEh-(GAP-_FAT_BOOT))
  271. IF GAPLEN
  272.     DB    GAPLEN DUP(0)    
  273. ENDIF
  274. GAP    ENDP
  275.  
  276. ;    DB    40h DUP(0)
  277.     DB    055h, 0AAh
  278. END
  279.