;*
;*  File viewer
;*
;*  CopyRight 1995. Nicholas Poljakov all rights reserved.
;*
.MODEL LARGE
include c:\include\dos.inc
include c:\include\bios.inc
.STACK
.DATA
;
    PUBLIC Cnt_H, Cnt_L, b_ptr, h_cnt, t_cnt, h_buf, t_buf
    PUBLIC v_addr, str, str_lt, v_page
    PUBLIC _pv, set_scr0, line_up, line_dn, extable
    PUBLIC page_up, page_dn, map_str, make_w
    PUBLIC get_s_r, get_s_l, rt_buf, lf_buf, scroll, MapErr
    PUBLIC deact_w, cal_cnt, nonek, SetVMem, GetFN, FilTitle
ESCAPE  EQU 27
UP      equ 48h
DN      equ 50h
PUP     equ 73
PDN     EQU 81
BUF_SIZ EQU 32000
;
U_Y     equ 8
U_X     equ 10
X_SIZ   equ 70
Y_SIZ   EQU 16
TOP     equ 1
BOTTOM  equ Y_SIZ - 4
;
path    db  80 dup (?)
        db  0
fd      dw  0
;
; vars for buffers manipulation
Cnt_H   dw  0  ; file pointer
Cnt_L   dw  0  ; for LSEEK
h_cnt   dw  0
t_cnt   dw  0
h_buf   dw  0
t_buf   dw  0
b_ptr   dw  0
BuffSeg dw  0  ; buffer segment
cur_cnt dw  0
cur_ln  db  0
array   dw  23 dup (?) ; Lengths of the strings
buf_lt  dw  0
str_lt  dw  0
str     db 100 dup (?)
;
; vars for window
;
v_page  db  0      ; video page
w_off   dw  (U_Y - 1) *  160 + (U_X - 1) * 2
siz_y   db  Y_SIZ - 2
siz_x   db  X_SIZ - 2
attrib  db  70h    ; attibute for window
attrib1 db  70h    ; attibute for query
attrib2 db  0fh    ; attibute for title
attrib3 db  0fh    ; attibute for error message
sksave  db  0
;
v_addr  dw  0
w_save  db  X_SIZ * Y_SIZ * 2 dup (?)
svline  dw  80 dup (?)
;
dcl0    db  'File : '
dcl0lt  equ $ - dcl0
dcl1    db  'Enter the file name please : '
dcl1lt  equ  $ - dcl1
dcl2    db  'Sorry... file not found !'
dcl2lt  equ  $ - dcl2
err2    DB      13,10,"Insufficient memory... Sorry!",13,10,"$"
;
; Call table

exkeys    DB      72,73,80,81,60  ; Extended key codes
lexkeys   EQU     $-exkeys        ; Table of keys
extable   DD      line_up
          DD      page_up
          DD      line_dn
          DD      page_dn
          DD      ResetFL
          DD      nonek
;
;buff    db BUF_SIZ dup (?)
.CODE
_pv    proc  far
;
;       mov   ax, _DATA
;       mov   ds, ax
;
        push  bp
        mov   bp, sp
        push  si
        push  di
;
;  In [bp+6] -> Arg1     (offset Path_name)
;  in [bp+8] -> Arg2     (segment Path_name)
;

        call far ptr  SetVMem    ; Set addres of video memory

; Allocate dynamic memory for file buffer

        @GetBlok 0FFFh                ; Try to allocate 64K
        jnc     SaveBSeg
        @DispStr err2                 ; else error and quit
        jmp     short Main_exit
SaveBSeg:
        mov     BuffSeg,ax            ; Save buffer segment

RdFilN:
        call far ptr  set_scr0   ; Set initial window
        cmp   ax, 0
        je    Reread
        call far ptr  MapErr
        jmp short RdFilN
Reread:
        mov   ah, 0      ; Keyboard
        int   16h        ;     input
        cmp   al, 0
        je    Test_mv    ; Test if it's cursor move key
        cmp   al, ESCAPE
        jne   Reread
        call far ptr  deact_w
Main_exit:
;       @Exit            ; Exit if 'escape' pressed or error
        mov     ax, 0    ; Return
        mov     dx, 0    ;       code
        pop     di
        pop     si
        pop     bp
        ret
;
Test_mv:
        mov   al, ah     ; Test scan code
;
        push    es
        push    ds                    ; Load DS into ES
        pop     es
        mov     di,OFFSET exkeys      ; Load address and length of key list
        mov     cx,lexkeys+1
        cld
        repne   scasb                 ; Find position
        pop     es
        sub     di,(OFFSET exkeys)+1  ; Point to key
        shl     di,1                  ; Adjust pointer for word addresses
        shl     di,1                  ; Adjust pointer for dword addresses
        call    extable[di]           ; Call procedure
        jmp     Reread
_pv    endp
;
line_up proc  far
        push  es
        mov   ax, b_ptr  ; current position in buffer
        push  ax         ; save it
        sub   ax, cur_cnt
        mov   b_ptr, ax
        call far ptr  get_s_l
        cmp   ax, 0
        je    Lu_contin
        pop   ax         ; old position
        mov   b_ptr, ax
        jmp  short Lu_exit
Lu_contin:
        pop   ax         ; to restory SP
        mov   al, -1
        call far ptr  scroll
;
;  Shift array on the right
;
        push  ds
        pop   es
        xor   bx, bx
        mov   bl, cur_ln
        mov   cx, bx
        shl   bl, 1
        mov   di, offset array
        add   di, bx        ; point to end of the array
;
        mov   ax, word ptr [di]
        add   t_buf, ax     ; set t_buf value
;
        mov   si, di
        sub   si, 2         ; point to end  of array - 1
        shl   cx, 1
        std
        rep  movsb
;
        mov   bx, offset array
        mov   ax, str_lt
        mov   word ptr [bx], ax ; set first element
;
        sub   h_buf, ax     ; set h_buf value
;
;
; Calculate the total length of mapped strings
;
;
        call far ptr  cal_cnt
;
        mov   ax, b_ptr   ; set new position
        add   ax, cur_cnt
        mov   b_ptr, ax
;
        mov   ax, TOP
        call far ptr  map_str
Lu_exit:
        mov   ax, 0
        pop   es
        ret
line_up endp
;
line_dn proc  far
        push  es
        call far ptr  get_s_r
        cmp   ax, 0
        jne   Ld_exit
        mov   al, 1
        call far ptr  scroll
        mov   al, cur_ln
        cmp   al, BOTTOM - 1
        inc   al
        mov   bx, ax
        jb    M_str
        mov   bx, offset array
        mov   ax, word ptr [bx]
        add   h_buf, ax
; Shift array left to one element
        push  ds
        pop   es
        mov   di, offset array
        mov   si, di
        add   si, 2
        mov   cx, BOTTOM - 1
        shl   cx, 1
        cld
        rep  movsb
;
        mov   bx, BOTTOM - 1
        jmp   short Skip_sl
M_str:
        mov   cur_ln, al
Skip_sl:
        shl   bx, 1
        mov   ax, str_lt
        mov   array[bx], ax  ; save length of cur. string
;
        sub   t_buf, ax
;
; Calculate the total length of mapped strings
;
;
        call far ptr  cal_cnt
;
        xor   ax, ax
        mov   al, cur_ln
        inc   al
        call far ptr  map_str
Ld_exit:
        mov   ax, 0
        pop   es
        ret
line_dn endp
;
page_up proc  far
        push  es
        mov   cx, BOTTOM
Pg_fill0:
        push  cx
        call far ptr  line_up
        pop   cx
        loop  Pg_fill0
;
        mov   ax, 0
        pop   es
        ret
page_up endp
;
page_dn proc  far
        push  es
;        mov   al, BOTTOM
;        call far ptr  scroll
        mov   cx, BOTTOM
Pg_fill:
        push  cx
        call far ptr  line_dn
        pop   cx
        loop  Pg_fill
;
        mov   ax, 0
        pop   es
        ret
page_dn endp
;
make_w  proc  far
        push  es
        mov   ax, 10h
        mov   bl, v_page
        xor   bh, bh
        mul   bx
        add   v_addr, ax
        cmp   sksave, 0
        jne   ClearW
;
; Save window
;
        mov   di, offset w_save
        mov   si, w_off
        push  ds
        push  ds
        pop   es
        mov   ax, v_addr
        mov   ds, ax
        mov   cx, Y_SIZ
S_cycl:
        push  cx
        push  si
        mov   cx, X_SIZ * 2
        cld
        rep movsb
        pop   si
        add   si, 160
        pop   cx
        loop  S_cycl
;
        pop   ds
;
;  Clear the window
;
ClearW:
        mov   ax, v_addr
        mov   es, ax
        mov   di, w_off
        mov   ah, attrib
        mov   al, 20h
        mov   cx, Y_SIZ
C_cycl:
        push  cx
        push  di
        mov  cx, X_SIZ
        rep  stosw
        pop   di
        add   di, 160
        pop   cx
        loop  C_cycl
;
;   Draw the border
;
        mov   di, w_off
        inc   di
        inc   di
        mov   al, 205
        mov   ah, attrib
        mov  cx, X_SIZ - 2
        rep  stosw
        mov   al, 186
        mov   cx, Y_SIZ - 2
        mov   di, w_off
        add   di, 160
D_cycl:
        push  di
        stosw
        add   di, (X_SIZ - 2) * 2
        stosb
        pop   di
        add   di, 160
        loop  D_cycl
;
        mov   di, w_off
        add   di, (Y_SIZ - 1) * 160
        inc   di
        inc   di
        mov   al, 205
        mov  cx, X_SIZ - 2
        rep  stosw
;
        mov   di, w_off
        mov   al, 201
        stosw
        add   di, (X_SIZ - 2) * 2
        mov   al, 187
        stosw
        mov   di, w_off
        add   di, (Y_SIZ - 1) * 160
        mov   al, 200
        stosw
        add   di, (X_SIZ - 2) * 2
        mov   al, 188
        stosw
;
        mov   ax, 0
        pop   es
        ret
;
make_w  endp
;
set_scr0 proc  far
        push  es
;        call far ptr  GetFN
;        @OpenFil path, 0
;        jnc   M_win
;        mov   ax, -1
;
; Try to open command line file
;
cmdchk:
;       mov     bl,es:[80h]           ; Get length
;       sub     bh,bh
;       mov     WORD PTR es:[bx+81h],0; Convert to ASCIIZ
        les     bx, dword ptr [bp + 6]
        push    ds
;       @OpenFil 82h,0,es             ; Open argument
        @OpenFil bx,0,es             ; Open argument
        pop     ds
        jnc     M_win
        mov     ax, -1
        pop     es
        ret                           ; error return
M_win:
        mov     fd, ax                ; save descriptor of file
        mov     t_cnt, 1
;
        call far ptr    rt_buf
        mov     h_cnt, 0
;
        call far ptr    make_w
        call far ptr    FilTitle
;
        mov   cx, Y_SIZ - 4
        xor   ax, ax
Set_cycl:
        push  ax
        call far ptr  get_s_r
        cmp   ax, 0
        je    Set_cy_cont
        pop   ax
        jmp short SetExit
Set_cy_cont:
        pop   ax
;
        push  ax
        mov   bx, t_buf      ; correct t_buf value
        mov   ax, str_lt
        sub   bx, ax
        mov   t_buf, bx
        pop   ax
;
        mov   cur_ln, al    ; save number of current line
        mov   bx, ax
        shl   bx, 1
        mov   dx, str_lt
        mov   array[bx], dx ; save length of cur. line
        inc   ax
        push  ax
        call far ptr  map_str
        pop   ax
        loop  Set_cycl
;
        call far ptr  cal_cnt
;
SetExit:
        mov   ax, 0
        pop   es
        ret
;
set_scr0 endp
;
;
get_s_r proc  far
        push  es
        push  cx
        cmp   t_buf, 0
        jg    Get_contin
        call far ptr  rt_buf
        cmp   ax, -1
        jne   Get_contin
        pop   cx
        pop     es
        ret
Get_contin:
        mov   cx, t_buf
;       push  ds
;       pop   es
;       mov   di, b_ptr  ; pointer in buffer
        les   di, dword ptr b_ptr   ; //12.2.92 external buffer//
        mov   al, 0ah
        cld
        repne scasb
        jz    Next_prc
Next_prc:
;
        mov   cx, di
        mov   si, b_ptr
        sub   cx, si
        mov   str_lt, cx  ; Save length of string
;
        cmp   cx, 100     ; Test upper length
        jb    MvStr1
        mov   cx, 99
MvStr1:
        push  ds
        mov   ax, ds
        mov   di, BuffSeg
        mov   ds, di
        mov   es, ax
        mov   di, offset str
        cld
        rep movsb
        pop   ds
;
        mov   ax, str_lt
        add   b_ptr, ax
;
        mov   ax, 0
        pop   cx
        pop   es
        ret
get_s_r endp
;
get_s_l proc  far
        push  es
        push  cx
        cmp   h_buf, 0
        jg    Get_l_contin
        call far ptr  lf_buf
        cmp   ax, -1
        jne   Get_l_contin
        pop   cx
        pop   es
        ret
Get_l_contin:
        mov   cx, h_buf
;       push  ds
;       pop   es
;       mov   di, b_ptr  ; pointer in buffer
        les   di, dword ptr b_ptr ;//12.2.92 external buffer//
        sub   di, 2      ; skip 0ah char.
        sub   cx, 2      ; dec. corresponded length
        mov   al, 0ah
        std
        repne scasb
;
        jnz   Skip_sub_2 ; 0ah was't found...
        add   di, 2      ; 0ah was found !
Skip_sub_2:
        mov   cx, b_ptr
        sub   cx, di
        jns   Sv_lt
        neg   cx
Sv_lt:
        or    cx, cx
        jnz   SvLen
        mov   cx, 2       ; it's first null line
        mov   di, 0       ; offset buff
SvLen:
        mov   str_lt, cx  ; Save length of string
;
        mov   b_ptr, di
;
        cmp   cx, 100     ; Test upper length
        jb    MvStr2
        mov   cx, 99
MvStr2:
        push  ds
        mov   ax, ds
        mov   si, BuffSeg
        mov   ds, si
        mov   es, ax
        mov   si, di
        mov   di, offset str
        cld
        rep movsb
        pop   ds
;
        mov   ax, 0
        pop   cx
        pop   es
        ret
get_s_l endp
;
rt_buf  proc  far
        push  es
        push  bx
        push  cx
        push  dx
        push  si
        push  di
;
        cmp   t_cnt, 0
        jne   Rt_read
        mov   ax, -1
        jmp   Rt_exit
;
Rt_read:
        mov   cx, Cnt_H
        mov   dx, Cnt_L
        @MovePtrAbs fd     ; set file pointer
        push  ds
        mov   ax, BuffSeg
        @Read 0, BUF_SIZ, fd, ax
        pop   ds
        jnc   Chk_count
        mov   ax, -1
        jmp   short Rt_exit
Chk_count:
        cmp   ax, BUF_SIZ ; full block ?
        je    Rt_set_next
        mov   t_cnt, 0    ; last block
        cmp   ax, 0
        jne   Cr_Cnt
        mov   ax, -1
        jmp   short Rt_exit
Rt_set_next:
        mov   t_cnt, 1     ; not last block
        mov   cx, ax
        mov   di, ax       ; offset buff
        mov   ax, BuffSeg
        mov   es, ax
        mov   al, 0ah
        std
   repne scasb
        cld
        mov   ax, cx
;
; Set new value of file pointer
;
Cr_Cnt:
        cwd
        add   Cnt_L, ax
        adc   Cnt_H, dx
;
        mov   h_cnt, 1     ; it's not first block
;
; Set buffer variables
;
        mov   dx, 0        ; offset buff
        mov   b_ptr, dx
        mov   buf_lt, ax
        mov   t_buf, ax
        mov   h_buf, 0
        mov   cur_cnt, 0
        push  ds
        pop   es
        mov   di, offset array
        mov   ax, 0
        mov   cx, 23
        rep stosw          ; Clear array
;
        xor   ax, ax
;
Rt_exit:
        pop   di
        pop   si
        pop   dx
        pop   cx
        pop   bx
        pop   es
        ret
rt_buf  endp
;
lf_buf  proc  far
        push  es
        push  bx
        push  cx
        push  dx
        push  si
        push  di
;
        cmp   h_cnt, 0
        jne   Lf_set_fp
        mov   ax, -1
        jmp   Lf_exit
Lf_set0:
        mov   Cnt_L, 0
        mov   Cnt_H, 0
        mov   h_cnt, 0
        jmp short Lf_mv_fp
Lf_set_fp:
;
;  Set file pointer for LSEEK
;
        mov   ax, buf_lt    ; move back to skip this buffer
        cwd
        sub   Cnt_L, ax
        sbb   Cnt_H, dx
;
        sub   Cnt_L, BUF_SIZ
        sbb   Cnt_H, 0
        js    Lf_set0
;
Lf_mv_fp:
        mov   cx, Cnt_H
        mov   dx, Cnt_L
        @MovePtrAbs fd
;
; Read prev. block
;
        push  ds
        mov   ax, BuffSeg
        @Read 0, BUF_SIZ, fd, ax
        pop   ds
        jnc   Lf_Chk_cnt
        mov   ax, -1
        jmp   short Lf_exit
SkLstStr:
        push  ax
        mov   di, ax         ; offset buff
        mov   ax, BuffSeg
        mov   es, ax
        mov   al, 0ah
        std
    repne scasb
        pop   ax
        mov   b_ptr, di
        jmp   short SetBufVars
Lf_Chk_cnt:
        mov   cx, ax
        cmp   h_cnt, 0    ; it's first buffer ?
        je    SkLstStr
        push  ax
        cwd
        add   Cnt_L, ax    ; new
        adc   Cnt_H, dx    ; file pointer
;
        mov   di, 0        ; offset buff
        mov   al, 0ah
        push  ds
        pop   es
        cld
    repne scasb
        pop   ax
;
        mov   dx, ax         ; offset buff
        mov   b_ptr, dx   ; b_ptr points to tail of buffer
;
; Set buffer variables
;
SetBufVars:
        mov   t_cnt, 0
        cmp   ax, BUF_SIZ
        jne   Lf_contin
        mov   t_cnt, 1    ; it's not last buffer
Lf_contin:
        mov   buf_lt, cx
        mov   h_buf, cx
        mov   t_buf, 0
        mov   cur_cnt, 0
        push  ds
        pop   es
        mov   di, offset array
        mov   ax, 0
        mov   cx, 23
        cld
        rep stosw          ; Clear array
;
        xor   ax, ax
;
Lf_exit:
        pop   di
        pop   si
        pop   dx
        pop   cx
        pop   bx
        pop   es
        ret
lf_buf  endp
;
scroll  proc  far
        push  es
        push  bx
        push  cx
        push  dx
;
        cmp   al, 1
        jne   Scr_dn
        @Scroll -1, attrib, U_X, U_Y+2, U_X+X_SIZ-3, U_Y+Y_SIZ-3
        jmp short Scr_exit
Scr_dn:
        cmp   al, -1
        jne   Cl_w
        @Scroll 1, attrib, U_X, U_Y+2, U_X+X_SIZ-3, U_Y+Y_SIZ-3
        jmp short Scr_exit
Cl_w:
        @Scroll -BOTTOM, attrib, U_X, U_Y+2, U_X+X_SIZ-3, U_Y+Y_SIZ-3
;
Scr_exit:
        pop   dx
        pop   cx
        pop   bx
        pop   es
;
        mov   ax, 0
        ret

scroll  endp
;
map_str proc  far
        push  es
        push  cx
        mov   dx, v_addr
        mov   es, dx
        mov   di, w_off
        add   di, (160 + 1) * 2
        mov   bx, 160
        mul   bx
        add   di, ax
        mov   si, offset str
        mov   cx, str_lt
        cmp   cx, 0
        je    Map_exit
        cmp   cx, X_SIZ - 2
        jb    Map_contin
        mov   cx, X_SIZ - 2
Map_contin:
        mov   ah, attrib
        cld
Map_cycl:
        lodsb
        cmp   al, 31
        ja    StoreAL
        mov   al, 32
StoreAL:
        stosw
        loop  Map_cycl
;
Map_exit:
        mov   ax, 0
        pop   cx
        pop   es
        ret
map_str endp
;
deact_w proc  far
        push  es
;
; Restory the window
;
        mov   si, offset w_save
        mov   ax, v_addr
        mov   es, ax
        mov   di, w_off
        mov   cx, Y_SIZ
R_cycl:
        push  cx
        push  di
        mov   cx, X_SIZ * 2
        cld
        rep movsb
        pop   di
        add   di, 160
        pop   cx
        loop  R_cycl
;
        mov   ax, 0
        pop   es
        ret
deact_w endp
cal_cnt proc  far
        push  es
        push  cx
        push  bx
;
; Calculate the total length of mapped strings
;
        xor   cx, cx
        mov   cl, cur_ln
        inc   cl          ; cur_ln + 1
        mov   bx, offset array
        xor   ax, ax
Calc_cnt:
        add   ax, word ptr [bx]
        add   bx, 2
        loop  Calc_cnt
;
        mov   cur_cnt, ax
;
        pop   bx
        pop   cx
;
        mov   ax, 0
        pop   es
        ret
cal_cnt endp
nonek   proc  far
        mov   ax, 0
        ret
nonek   endp
SetVMem proc  far
        push  es
        @GetMode
        mov   v_page, bh
        cmp   al, 2
        jne   M3
        mov   v_addr, 0b800h
        jmp  short S_win
M3:
        cmp   al, 3
        jne   M7
        mov   v_addr, 0b800h
        jmp  short S_win
M7:
        cmp   al, 7
        jne   Err_exit
        mov   v_addr, 0b000h
        jmp  short S_win
Err_exit:
        mov   ax, -1
        pop   es
        ret
;
S_win:
        xor   ax, ax
        pop   es
        ret
SetVMem endp
GetFN   proc  far
        push  es
;
        push  ds
        mov   ax, ds
        mov   es, ax       ; ES -> data segment
        mov   ax, v_addr
        mov   ds, ax       ; DS -> video memory
        mov   di, offset svline
        mov   si, 24 * 160 ; offset to last line
        mov   cx, 80       ; save full line
        cld
        rep   movsw
;
        pop   ds
        mov   es, ax
        mov   ah, attrib1
        mov   al, 32
        mov   di, 24 * 160 ; offset to last line
        mov   cx, 80       ; save full line
        cld
        rep   stosw        ; clear the last line
;
        mov   bx, offset dcl1
        mov   cx, dcl1lt
        mov   di, 24 * 160 ; offset to last line
SetDcl1:
        mov   al, byte ptr ds:[bx]
        stosw
        inc   bx
        loop  SetDcl1
;
        mov   si, di       ; save di
        mov   bx, offset path
        mov   dh, ah       ; save attrib1
GetString:
        mov   ah, 0
        int   16h          ; read char. from keyb.
        cmp   al, 0dh      ; Enter
        je    SetFN_exit
        cmp   ah, 1        ; ESC
        jne   TestBS
        mov   di, si       ; restory DI
        mov   cx, X_SIZ - 2 - dcl1lt
        mov   ah, dh
        mov   al, 32
        cld
        rep   stosw        ; clear the "tail" of string
        mov   di, si       ; restory DI
        mov   bx, offset path
        mov   byte ptr ds:[bx], 0
        jmp short GetString
TestBS:
        cmp   ah, 0eh      ; backspace ?
        jne   RestAttr
        cmp   si, di
        je    GetString
        sub   di, 2
        mov   ah, dh
        mov   al, 32
        stosw
        sub   di, 2        ; clear last shar.
        dec   bx
        mov   byte ptr [bx], 0
        jmp short GetString
RestAttr:
        mov   ah, dh       ; restory attrib1
        stosw
        mov   byte ptr ds:[bx], al
        inc   bx
        jmp  short GetString
SetFN_exit:
        mov  byte ptr ds:[bx], 0
;
        mov   si, offset svline
        mov   di, 24 * 160 ; offset to last line
        mov   cx, 80       ; rest. full line
        cld
        rep   movsw        ; rest. the last line
;
        pop   es
        xor   ax, ax
        ret
GetFN   endp
;
ResetFL proc  far
        cmp   fd, 0
        je    SetFirstB
        @ClosFil fd
        mov   sksave, 255
SetFirstB:
        call far ptr  deact_w
ResetScr:
        call far ptr  set_scr0
        cmp   ax, 0
        je    ResetExit
        call far ptr  MapErr
        jmp short ResetScr
;
ResetExit:
        xor   ax, ax
        ret
ResetFL endp
FilTitle proc  far
        push  es
;
        mov   ax, v_addr
        mov   es, ax
; Clear tile line
        mov   ah, attrib2
        mov   al, 32
        mov   di, w_off
        add   di, 162
        mov   cx, X_SIZ - 2
        cld
        rep   stosw
;
        mov   si, offset dcl0
        mov   di, w_off
        add   di, 162
        mov   cx, dcl0lt
FillT:
        lodsb
        stosw               ; Map 'File : '
        loop  FillT
;
        push  ds
        lds   si, dword ptr [bp + 6]
FilPath:
        lodsb
        cmp   al, 0         ; end_of_string ?
        je    FillExit
        stosw
        jmp short FilPath
;
FillExit:
        pop   ds
        pop   es
        xor   ax, ax
        ret
FilTitle endp
MapErr  proc  far
        push  es
;
        push  ds
        mov   ax, ds
        mov   es, ax       ; ES -> data segment
        mov   ax, v_addr
        mov   ds, ax       ; DS -> video memory
        mov   di, offset svline
        mov   si, 24 * 160 ; offset to last line
        mov   cx, 80       ; save full line
        cld
        rep   movsw
;
        pop   ds
        mov   es, ax
        mov   ah, attrib3
        mov   al, 32
        mov   di, 24 * 160 ; offset to last line
        mov   cx, 80       ; save full line
        cld
        rep   stosw        ; clear the last line
;
        mov   bx, offset dcl2
        mov   cx, dcl2lt
        mov   di, 24 * 160 ; offset to last line
SetDcl2:
        mov   al, byte ptr ds:[bx]
        stosw
        inc   bx
        loop  SetDcl2
;
        mov ah, 0
        int 1ah
        add dx, 36   ; 2 sec
        mov bx, dx
 Repeat:
        int 1ah
        cmp dx, bx
        jne Repeat
;
        mov   si, offset svline
        mov   di, 24 * 160 ; offset to last line
        mov   cx, 80       ; rest. full line
        cld
        rep   movsw        ; rest. the last line
;
        pop   es
        xor   ax, ax
        ret
MapErr  endp
        end
