; $Id$
;
+.equ DSKSEL_DEBUG = 0
; ---------------- Defines for the Filesystem Interface -------
;*****************************************************
;* Disk-Manager constants *
;*****************************************************
- .equ dskType_None = 0
- .equ dskType_CPM = 1
- .equ dskType_FAT = 2
- .equ dskType_RAM = 3
+ .equ dskType_None = 0*16
+ .equ dskType_CPM = 1*16
+ .equ dskType_FAT = 2*16
+; .equ dskType_RAM = 3*16
+ .equ dskType_MASK = 0xf*16
;*****************************************************
;* CP/M to host disk constants *
;*****************************************************
- .equ MAXDISKS = 6 ;Max number of Disks (partitions)
+ .equ MAXDISKS = 8 ;Max number of Disks (partitions)
.equ PARTENTRY_SIZE = 9 ;Size of a Partitiontableentry
.equ blksize = 1024 ;CP/M allocation size
.equ hostsize = 512 ;host disk sector size
erflag: .byte 1 ;error reporting
wrtype: .byte 1 ;write operation type
-hostbuf: .byte hostsize ;host buffer (from/to SD-card)
-hostparttbl: .byte PARTENTRY_SIZE*MAXDISKS ;host partition table (type, start sector, sector count)
+hostbuf: .byte hostsize ;host buffer (from/to SD-card)
+hostparttbl: .byte PARTENTRY_SIZE*MAXDISKS ;host partition table (type, start sector, sector count)
hostparttbltop:
hostdsk: .byte 1 ;host disk number
hosttype: .byte 1 ;host disk type (same entry as 1 parition entry)
; ------------------------------- Start of Code Segment
.cseg
+;---------------------------------------------------------------------
+
+.if DSKSEL_DEBUG
+
+dbg_prdrvtbl:
+ push xh
+ push xl
+ push temp3
+ push temp2
+ push temp
+ printnewline
+ printstring "drvtbl ("
+ lds xl,biosdrvtbl
+ lds xh,biosdrvtbl+1
+ movw temp,x
+ rcall printhexw
+ printstring "): "
+ ldi temp3,16
+dbg_pcpel:
+ rcall dram_readw_pp
+ rcall printhexw
+ printstring " "
+ dec temp3
+ brne dbg_pcpel
+ pop temp
+ pop temp2
+ pop temp3
+ pop xl
+ pop xh
+ ret
+
+dbg_print_biosd:
+ printnewline
+ lds temp,bcbadr
+ lds temp2,bcbadr+1
+ rcall printhexw
+ printstring " "
+ lds temp,biosdrvtbl
+ lds temp2,biosdrvtbl+1
+ rcall printhexw
+ printstring " "
+ lds temp,biosdirbuf
+ lds temp2,biosdirbuf+1
+ rcall printhexw
+ printstring " "
+ lds temp,biosenddat
+ lds temp2,biosenddat+1
+ rcall printhexw
+ printstring " "
+ ret
+.endif
+
+; ====================================================================
+; Function: Get a Pointer to a Partitiontable entry
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers : [w] z Pointer to the Partitionentry
+; [r] xl Number of Diskentry to Read
+; [w] _tmp0 scratch
+; [w] _tmp1 "
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+dsk_getpartentry:
+
+ ldi zl,PARTENTRY_SIZE
+ mul xl,zl
+ ldiw z,hostparttbl
+ add zl,_tmp0
+ add zh,_tmp1
+ ret
+
; ====================================================================
; Function: Virtual Port Interface
; ====================================================================
; --------------------------------------------------------------------
; Description:
; ====================================================================
-
+
dsk_param_getadr:
ldiw z,biospar_base
add zl,temp3
ld temp,z
ret
+SetBCB:
+ lds xl,bcbadr
+ mov xh,temp
+ ldiw z,biosdrvtbl
+ ldi temp3,6
+sbcb_l:
+ rcall dram_read_pp
+ st z+,temp
+ dec temp3
+ brne sbcb_l
+
+; rcall dbg_print_biosd
+ rcall dpb_drvtblinit
+; rcall dbg_prdrvtbl
+
+ ret
+
+; ====================================================================
+; Function: Check if disk exists
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+; return 0, if selected disk not exist.
+; return !0, if disk exist
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
dskDiskCheck:
- lds temp2,seekdsk
- cpi temp2,RAMDISKNR
+ lds temp2,ndisks
+ lds temp,seekdsk
+.if DSKSEL_DEBUG
+ printnewline
+ printstring "DiskCheck: "
+ rcall printhexw
+.endif
+ cpi temp,RAMDISKNR
brsh dsk_dchrd ;maybe ramdisk
; Check if selected disk # is less then # of disks.
- lds temp,ndisks
- tst temp ;0 disks?
+ lds temp2,ndisks
+ tst temp2 ;0 disks?
brne dsk_dchpart1
; No disks yet, need to init
rcall mgr_init_partitions ;disk chanched?
- sbrs temp,7
- rjmp dsk_dchpart0
+; sbrs temp,7
+; rjmp dsk_dchpart0
push temp
- rcall dsk_drvtblinit
- rcall dbg_prdrvtbl
- pop temp
+ rcall dpb_drvtblinit
+; rcall dbg_prdrvtbl
+ pop temp2
dsk_dchpart0:
- cbr temp,0x80
- lds temp2,seekdsk
+ cbr temp2,0x80
+ lds temp,seekdsk
dsk_dchpart1:
- cp temp2,temp
- brsh dsk_dcher
+ cp temp,temp2
+ brsh dsk_dch_err
+.if DSKSEL_DEBUG
printnewline
printstring "Select: "
- mov temp,temp2
rcall printhex
-
- lds xl,biosdrvtbl
- lds xh,biosdrvtbl+1
- lsl temp2 ;drive #
- add xl,temp2
- adc xh,_0
- rcall dram_readw_pp
-
- printstring ", "
- rcall printhexw
-
- or temp,temp2
+.endif
+ rcall dpb_drvtbl_entry_get
+ or temp,temp2 ;if !0, drive is allready initialized
brne dsk_dchend
lds temp,seekdsk
- rcall dsk_diskinit
- brne dsk_dcher
+ rcall dpb_diskinit
dsk_dchend:
- ldi temp,0
+.if DSKSEL_DEBUG
+ push temp
+ lds temp,seekdsk
+ rcall dpb_drvtbl_entry_get
+
+ printstring ", "
+ rcall printhexw
+ pop temp
+.endif
+
ret
+dsk_dch_err:
+ ldi temp,0 ;error return
+ ret
+
+; Check RAMDISK
+
dsk_dchrd:
#if RAMDISKCNT
- cpi temp,RAMDISKNR+RAMDISKCNT
- brlo dsk_dchend
-#endif
-dsk_dcher:
- ldi temp,0xff ;error return
+ cpi temp,RAMDISKNR+RAMDISKCNT
+ brsh dsk_dchrd_err
+
+ ldi temp,0xff ;return ok
ret
-
-dskErrorRet:
- lds temp,erflag
+#endif
+dsk_dchrd_err:
+ ldi temp,0 ;error return
ret
-SetBCB:
- lds xl,bcbadr
- mov xh,temp
- ldiw z,biosdrvtbl
- ldi temp3,6
-sbcb_l:
- rcall dram_read_pp
- st z+,temp
- dec temp3
- brne sbcb_l
-
- rcall dbg_print_biosd
- rcall dsk_drvtblinit
+; ====================================================================
+; Function: Return status of last disk i/o function
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+dskErrorRet:
+ lds temp,erflag
ret
-;---------------------------------------------------------------------
-
-dbg_prdrvtbl:
- push xh
- push xl
- push temp3
- push temp2
- push temp
- printnewline
- printstring "drvtbl ("
- lds xl,biosdrvtbl
- lds xh,biosdrvtbl+1
- movw temp,x
- rcall printhexw
- printstring "): "
- ldi temp3,16
-dbg_pcpel:
- rcall dram_readw_pp
- rcall printhexw
- printstring " "
- dec temp3
- brne dbg_pcpel
- pop temp
- pop temp2
- pop temp3
- pop xl
- pop xh
- ret
-
-; -------------------------------------------------------------------
-dbg_print_biosd:
- printnewline
- lds temp,bcbadr
- lds temp2,bcbadr+1
- rcall printhexw
- printstring " "
- lds temp,biosdrvtbl
- lds temp2,biosdrvtbl+1
- rcall printhexw
- printstring " "
- lds temp,biosdirbuf
- lds temp2,biosdirbuf+1
- rcall printhexw
- printstring " "
- lds temp,biosenddat
- lds temp2,biosenddat+1
- rcall printhexw
- printstring " "
-
- ret
-
; -------------------------------------------------------------------
.cseg
-; init bios disk tables.
-; leave drive 'A' out for now
-
-
- rcall dbg_prdrvtbl
-
- rcall dsk_drvtblinit
- rcall dbg_prdrvtbl
-
- lds temp,biosenddat
- lds temp2,biosenddat+1
- rcall heap_init
-
- ldi temp,1
-dsk_pdil:
- cp temp,temp2
- brsh dsk_pdie
- push temp2
- push temp
- rcall dsk_diskinit
- pop temp
- pop temp2
- inc temp
- rjmp dsk_pdil
-
-
-
-dsk_pdie:
- mov temp,temp2
; Test DPBs (avrcpm format)
dpblist:
+;dpb243
+ .db 0x1A,0x00 ;spt
+ .db 0x03,0x07 ;block shift, bock mask
+ .db 0x00,0xF2 ;extent mask, low(disk size -1),
+ .db 0x00,0x3F ;high(disk size -1), low(dir max)
+ .db 0x00,0xC0 ;high(dir max), alloc0
+ .db 0x00,0x10 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
+;dpb243
+ .db 0x1A,0x00 ;spt
+ .db 0x03,0x07 ;block shift, bock mask
+ .db 0x00,0xF2 ;extent mask, low(disk size -1),
+ .db 0x00,0x3F ;high(disk size -1), low(dir max)
+ .db 0x00,0xC0 ;high(dir max), alloc0
+ .db 0x00,0x10 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
+;dpb243
+ .db 0x1A,0x00 ;spt
+ .db 0x03,0x07 ;block shift, bock mask
+ .db 0x00,0xF2 ;extent mask, low(disk size -1),
+ .db 0x00,0x3F ;high(disk size -1), low(dir max)
+ .db 0x00,0xC0 ;high(dir max), alloc0
+ .db 0x00,0x10 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
+;dpb243
+ .db 0x1A,0x00 ;spt
+ .db 0x03,0x07 ;block shift, bock mask
+ .db 0x00,0xF2 ;extent mask, low(disk size -1),
+ .db 0x00,0x3F ;high(disk size -1), low(dir max)
+ .db 0x00,0xC0 ;high(dir max), alloc0
+ .db 0x00,0x10 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
;dpb243
.db 0x1A,0x00 ;spt
.db 0x03,0x07 ;block shift, bock mask
#endif
; Test
-cpy_dpb:
+dpb_copy:
push zh
push zl
push yh
pop zh
ret
-; clear drive table
-; for now, only entries 1 - 3 are cleared.
+; ====================================================================
+; Function: get drive table entry pointer for drive # in temp
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+;
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+
+dpb_drvtbl_entry_p:
+
+ ldsw x,biosdrvtbl
+ lsl temp ;drive #
+ add xl,temp
+ adc xh,_0
+ ret
+
+
+; ====================================================================
+; Function: get drive table entry for drive # in temp
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+;
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+
+dpb_drvtbl_entry_get:
+
+ rcall dpb_drvtbl_entry_p
+ ljmp dram_readw_pp
+
; ====================================================================
; Function: Clear drive table
; Description:
; ====================================================================
-; For now, only entries 1 - 3 are cleared.
+; For now, only entries 1 - 7 are cleared.
-dsk_drvtblinit:
+dpb_drvtblinit:
ldsw x,biosdrvtbl
adiw x,2
- ldi temp3,3
-dsk_drvi_l:
+ ldi temp3,7
+dpb_drvi_l:
ldi temp,0
ldi temp2,0
rcall dram_writew_pp
dec temp3
- brne dsk_drvi_l
+ brne dpb_drvi_l
lds temp,biosenddat
lds temp2,biosenddat+1
; Init CP/M data structures
; temp = drive #
;
+; return !0 if ok
+; 0 on error
-dsk_diskinit:
+dpb_diskinit:
mov temp3,temp ;save disk #
; Test
- rcall cpy_dpb
+ rcall dpb_copy
ldi temp, low (16)
ldi temp2,high(16)
rcall heap_get
- brne dsk_di_1
- rjmp dsk_di_err ;
-dsk_di_1:
+ brne dpb_di_1
+ rjmp dpb_di_err ;
+dpb_di_1:
movw x,temp
- movw y,temp
+ movw y,temp ;save dph pointer
ldi temp,0
ldi temp2,0
rcall dram_writew_pp ;XLT
rcall dram_writew_pp ;DIRBUF
; get mem for DPB
-; -------------------------------------------------------------
-; DPB: | SPT |BSH|BLM|EXM| DSM | DRM |AL0|AL1| CKS | OFF |
-; -------------------------------------------------------------
-; 0 5 7 11 13
+; -------------------------------------------------------------
+; DPB: | SPT |BSH|BLM|EXM| DSM | DRM |AL0|AL1| CKS | OFF |
+; -------------------------------------------------------------
+; 0 5 7 11 13
ldi temp, low (15)
ldi temp2,high(15)
rcall heap_get
- breq dsk_di_err_p1
+ breq dpb_di_err_p1
movw x,temp
ldiw z,tmpdpb
-dsk_dicpl:
+dpb_dicpl:
ld temp,z+
rcall dram_write_pp
cpi zl,low(tmpdpb + 15)
- brne dsk_dicpl
+ brne dpb_dicpl
sbiw x,15
movw temp,x
movw x,y
lds temp2,tmpdpb+11+1
cp temp,_0
cpc temp2,_0
- breq dsk_dicks0
+ breq dpb_dicks0
rcall heap_get
- breq dsk_di_err_p1
-dsk_dicks0:
+ breq dpb_di_err_p1
+dpb_dicks0:
rcall dram_writew_pp ;CSV
; get mem for alloc vector
lsr temp2
ror temp ;(dsm+1+7)/8
rcall heap_get
- breq dsk_di_err_p1
+ breq dpb_di_err_p1
rcall dram_writew_pp ;ALV
; success, insert DPH into drvtbl
- lds xl,biosdrvtbl
- lds xh,biosdrvtbl+1
- lsl temp3 ;drive #
- add xl,temp3
- adc xh,_0
+ mov temp,temp3
+ rcall dpb_drvtbl_entry_p
movw temp,y
rcall dram_writew_pp
- clr temp
+ ori temp,0xff ;return ok
ret
; error, free mem
-dsk_di_err_p1:
+dpb_di_err_p1:
movw temp,y
rcall heap_release
-dsk_di_err:
- ldi temp,1
- or temp,temp
+dpb_di_err:
+ eor temp,temp ;return 0 (+ Z-flag)
ret
-; ====================================================================
-; Function: Get a Pointer to a Partitiontable entry
-; ====================================================================
-; Parameters
-; --------------------------------------------------------------------
-; Registers : [w] z Pointer to the Partitionentry
-; [r] xl Number of Diskentry to Read
-; [w] _tmp0 scratch
-; [w] _tmp1 "
-; --------------------------------------------------------------------
-; Description:
-; ====================================================================
-dsk_getpartentry:
-
- ldi zl,PARTENTRY_SIZE
- mul xl,zl
- ldiw z,hostparttbl
- add zl,_tmp0
- add zh,_tmp1
- ret
-
; ====================================================================
; Function: Does a Disk interaction
; --------------------------------------------------------------------
; Registers : in: temp
; Variables : [r] seekdsk Number of Disk to Read
-; [r] seeksec Sector to read
+; [r] seeksec Sector to read
; [r] seektrk Track to read
; --------------------------------------------------------------------
; Description:
; ====================================================================
dsk_read:
- sts erflag,_0
- sbi flags,readop ; Set read operation flag
+ sts erflag,_0
+ sbi flags,readop ; Set read operation flag
;RAM disk?
- lds xl,seekdsk
+ lds xl,seekdsk
#if RAMDISKCNT
cpi xl,RAMDISKNR
brlt PC+2
#endif
rcall dsk_getpartentry ; Get Paritiontableentry
ld temp,z ; Get Partitiontype
+ andi temp,dskType_MASK
; Isn't it a Disk ?
- cpi temp,dskType_None
+ cpi temp,dskType_None
brne PC+2
rjmp dsk_read_err
-
; It must be a FAT16-Imagefile or CP/M Partition.
sts unacnt,_0
sbi flags,rsflag ;must read data
- ldi temp,WRUAL ;write type
- sts wrtype,temp ;treat as unalloc
- rjmp dsk_rwoper ;to perform the read
+ ldi temp,WRUAL ;write type
+ sts wrtype,temp ;treat as unalloc
+ rjmp dsk_rwoper ;to perform the read
dsk_read_err:
ret
; Parameters
; --------------------------------------------------------------------
; Registers : in: temp Write type
-; Variables : [r] seekdsk Number of Disk to Read
-; [r] seeksec Sector to read
-; [r] seektrk Track to read
+; Variables : [r] seekdsk Number of Disk to Read
+; [r] seeksec Sector to read
+; [r] seektrk Track to read
; --------------------------------------------------------------------
; Description:
; ====================================================================
;write the selected sector
sts erflag,_0
cbi flags,readop ; not a read operation
-
;RAM disk?
- lds xl,seekdsk
+ lds xl,seekdsk
#if RAMDISKCNT
cpi xl,RAMDISKNR
brlt PC+2
#endif
rcall dsk_getpartentry ; Get Paritiontableentry
ld temp2,z ; Get Partitiontype
+ andi temp,dskType_MASK
; Isn't it a Disk ?
cpi temp2,dskType_None
brne PC+2
rjmp dsk_write_err
+
; It must be a FAT16-Imagefile or CP/M Partition.
cbi flags,readop ;not a read operation
; Description:
; ====================================================================
dsk_writehost:
- lds xl,hostdsk
- rcall dsk_getpartentry
- ld temp,z
+ lds xl,hostdsk
+ rcall dsk_getpartentry
+ ld temp,z
+ andi temp,dskType_MASK
#if FAT16_SUPPORT
; Is it a FAT16 Diskimage ?
- cpi temp,dskType_FAT
+ cpi temp,dskType_FAT
brne PC+2
rjmp fat_writehost
#endif
; Is it a CP/M Partition ?
- cpi temp,dskType_CPM
+ cpi temp,dskType_CPM
brne PC+2
rjmp cpm_writehost
; Disktype not supported -> Return
lds xl,hostdsk
rcall dsk_getpartentry
ld temp,z
+ andi temp,dskType_MASK
#if FAT16_SUPPORT
; Is it a FAT16 Diskimage ?
- cpi temp,dskType_FAT
+ cpi temp,dskType_FAT
brne PC+2
rjmp fat_readhost
#endif
; Is it a CP/M Partition ?
- cpi temp,dskType_CPM
+ cpi temp,dskType_CPM
brne PC+2
rjmp cpm_readhost
; Disktype not supported -> Return