⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rxdosbio.asm

📁 dos source
💻 ASM
📖 第 1 页 / 共 5 页
字号:
        storarg _relCluster, ax                         ; required rel cluster offset
        or ax, ax                                       ; starts at first file cluster ?
        jz _LoadProgram_18                              ; yes -->

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  at start, we must position at rel cluster
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

_LoadProgram_14:
        mov ax, word ptr [ BootDrive ]
        mov dx, word ptr [ _currentCluster ][ bp ]
        call getNextCluster                             ; get next cluster
        jz _LoadProgram_Return                          ; exit if error -->

        mov word ptr [ _currentCluster ][ bp ], dx      ; save cluster number
        dec word ptr [ _relCluster ][ bp ]              ; scan more clusters ?
        jnz _LoadProgram_14                             ; scan more -->

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  optimize cluster read
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

_LoadProgram_18:
        mov ax, word ptr [ BootDrive ]
        mov dx, word ptr [ _currentCluster ][ bp ]
        call scanClusterMap
        mov word ptr [ _sectorsToRead ][ bp ], cx       ; # sectors to sequentially read
        mov word ptr [ _scanEndCluster ][ bp ], dx      ; last cluster scanned

    ;   mov dl, byte ptr [ BootDrive_BPB. _bpbSectorsPerCluster ]
    ;   sub dl, al                                      ; sectors remaining
    ;   sub word ptr [ _sectorsToRead ][ bp ], dx       ; adjust sectors to read
    ;   jnz _LoadProgram_26                             ; keep reading if more required -->
    ;   mov word ptr [ _sectorsToRead ][ bp ], 0001     ; else default to one sector

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  get sector offset to read
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

_LoadProgram_26:
        xor dx, dx
        mov ax, word ptr [ _buffer. _pointer ][ bp ]
        div word ptr [ BootDrive_BPB. _bpbBytesPerSector ]
        div byte ptr [ BootDrive_BPB. _bpbSectorsPerCluster ]

        xor bh, bh
        mov bl, ah                                      ; sector adjust for pointer

        mov ax, word ptr [ _currentCluster ][ bp ]
        dec ax
        dec ax

        xor cx, cx
        mov cl, byte ptr [ BootDrive_BPB. _bpbSectorsPerCluster ]
        mul cx                                          ; compute sector
        add ax, word ptr [ ReservedBeforeDataSector. _low  ]
        adc dx, word ptr [ ReservedBeforeDataSector. _high ]

        add ax, bx                                      ; add sector adjust
        adc dx, 0000

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  read buffer
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

        mov cx, dx
        mov dx, ax                                      ; sector address

        mov al, byte ptr [ BootDrive ]
        getdarg es, di, _buffer
        getarg bx, _sectorsToRead
        call ReadBuffer                                 ; do read
        jc _LoadProgram_Abrupt                          ; if error -->

        mov ax, word ptr [ _sectorsToRead ][ bp ]
        mul word ptr [ BootDrive_BPB. _bpbBytesPerSector ]
        add word ptr [ _buffer. _pointer ][ bp ], ax

        getarg dx, _scanEndCluster                      ; last cluster scanned
        storarg _currentCluster, dx                     ; cluster address of pgm /start
        cmp dx, -1                                      ; was last read to end of file ?
        jnz _LoadProgram_18                             ; no, keep reading -->

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  return
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

_LoadProgram_Return:
        mov cx, word ptr [ _buffer. _pointer ][ bp ]
        or cx, cx                                       ; if ok return

_LoadProgram_Abrupt:
        Return

        ;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
        ;  Read FAT Buffer                                              ;
        ;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
        ;                                                               ;
        ;  Input:                                                       ;
        ;   cx:dx  sector to read                                       ;
        ;...............................................................;

readFATBuffer:
        les di, dword ptr [ _FATbuffer ]

        cmp word ptr [ _FATbuffer_SectorNumber. _low  ], dx
        jnz readFATBuffer_08
        cmp word ptr [ _FATbuffer_SectorNumber. _high ], cx
        jz readFATBuffer_12

readFATBuffer_08:
        mov bx, 0001
        mov al, byte ptr [ BootDrive ]
        mov word ptr [ _FATbuffer_SectorNumber. _high ], cx
        mov word ptr [ _FATbuffer_SectorNumber. _low  ], dx
        call readBuffer

readFATBuffer_12:
        ret

        ;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
        ;  Read Buffer                                                  ;
        ;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
        ;                                                               ;
        ;  Input:                                                       ;
        ;   ax     drive                                                ;
        ;   bx     buffers to read                                      ;
        ;   cx:dx  logical sector to read                               ;
        ;   es:di  buffer address                                       ;
        ;...............................................................;

readBuffer:
        Entry
        ddef _bufferPtr, es, di
        ddef _sector, cx, dx
     ;  def _readSector
     ;  def _readHead
     ;  def _readTrack
        def _drive, ax
        def _buffers, bx
        def _retries   

        SaveRegisters bp, dx, ax, cx

readBuffer_08:
        mov word ptr [ _retries ][ bp ], 3

readBuffer_10:
        getdarg dx, ax, _sector
        add ax, word ptr [ BootDrive_BPB. _bpbHiddenSectors. _low ]
        adc dx, word ptr [ BootDrive_BPB. _bpbHiddenSectors. _high ]

        div word ptr [ BootDrive_BPB. _bpbSectorsPerTrack ]
        inc dl
        mov cl, dl                                      ; _readSector

        xor dx, dx
        div word ptr [ BootDrive_BPB. _bpbHeads ]
      ; mov word ptr [ _readTrack ][ bp ], ax           ; dont need to save track
      ; mov byte ptr [ _readHead  ][ bp ], dl           ; don't need to save heads
        mov dh, dl                                      ; head

        shl ah, 1                                       ; high order two bits of track
        shl ah, 1                                       ; ... moved to top end of reg
        shl ah, 1
        shl ah, 1
        shl ah, 1
        shl ah, 1
        or cl, ah                                       ; or with sector
        mov ch, al                                      ; remainder of track to ch

        mov al, byte ptr [ _buffers ][ bp ]             ; plus buffers to read 
        mov ah, al                                      ; buffers
        add ah, cl                                      ; starting sector
        sub ah, byte ptr [ BootDrive_BPB. _bpbSectorsPerTrack ]
        jle readBuffer_12                               ; no, ok to read -->
        sub al, ah                                      ; safe number of buffers to read
        inc ax

readBuffer_12:
        push ax                                         ; # buffers requested
        mov ah, 02h                                     ; read command type
        mov dl, byte ptr [ _drive ][ bp ]
        getdarg es, bx, _bufferPtr
      ;  NormalizeBuffer es, bx

        int 13h
        pop ax                                          ; # buffers requested
        jc readBuffer_26                                ; if error -->

        xor ah, ah
        xor cx, cx
        mov bx, ax
        mul word ptr [ BootDrive_BPB. _bpbBytesPerSector ]
        add word ptr [ _bufferPtr. _pointer ][ bp ], ax

        add word ptr [ _sector. _low  ][ bp ], bx
        adc word ptr [ _sector. _high ][ bp ], cx

        sub byte ptr [ _buffers ][ bp ], bl             ; buffers remaining after this read 
        jg  readBuffer_08                               ; if more to read
        jmp short readBuffer_28                         ; exit -->

readBuffer_26:
        xor ax, ax
        mov dl, byte ptr [ _drive ][ bp ]
        int 13h                                         ; if error, attempt reset

        dec word ptr [ _retries ][ bp ]
        jnz readBuffer_10

        stc                                             ; make sure exit with error flag

readBuffer_28:
        RestoreRegisters cx, ax, dx, bp
        Return

        ;''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''';
        ;  Get Next Cluster                                             ;
        ;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -;
        ;                                                               ;
        ;  Input:                                                       ;
        ;   ax     drive                                                ;
        ;   dx     current cluster                                      ;
        ;                                                               ;
        ;  Output:                                                      ;
        ;   dx     next cluster                                         ;
        ;   zr     if end of cluster chain.                             ;
        ;...............................................................;

getNextCluster:
        Entry
        def _drive, ax
        def _cluster, dx
        def _MaxClusters

        saveRegisters es, di, si, cx, bx, ax

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  determine whether its 12 or 16 bit FAT entries
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

        xor cx, cx
        mov cl, byte ptr [ BootDrive_BPB. _bpbSectorsPerCluster  ]
        mov dx, word ptr [ BootDrive_BPB. _bpbHugeSectors. _high ]
        mov ax, word ptr [ BootDrive_BPB. _bpbHugeSectors. _low  ]
        div cx
        storarg _MaxClusters, ax

        mov dx, word ptr [ BootDrive_BPB. _bpbHugeSectors. _high ]
        mov ax, word ptr [ BootDrive_BPB. _bpbHugeSectors. _low  ]

        mov dx, -1                                      ; presume end if error
        mov ax, word ptr [ _cluster ][ bp ]             ; get cluster #
        or ax, ax                                       ; invalid number 
        jz getNextCluster_Return                        ; exit -->
        cmp ax, word ptr [ _MaxClusters ][ bp ]
        jnc getNextCluster_Return                       ; if valid cluster # -->

getNextCluster_08:
        xor dx, dx
        test word ptr [ _MaxClusters ][ bp ], 0F000h
        jnz getNextCluster_16Bits                       ; if 16 -->

;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
;  12 bit FAT entries
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

getNextCluster_12Bits:
        mov ax, word ptr [ _drive   ][ bp ]             ; get drive
        mov dx, word ptr [ _cluster ][ bp ]             ;  and cluster
        call _get_12Bit_ClusterValue

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -