.include "dram-refresh.asm"
.include "timer.asm"
.include "utils.asm"
-; .include "heap.asm"
+ .include "heap.asm"
.include "mmc.asm"
; .include "mmc-old.asm"
; along with avrcpm. If not, see <http://www.gnu.org/licenses/>.
;
; $Id$
-;\r
-\r
-#ifndef CPMDSK_SUPPORT\r
- #define CPMDSK_SUPPORT 1 \r
-#endif\r
-\r
-#if CPMDSK_SUPPORT\r
-\r
+;
+
+#ifndef CPMDSK_SUPPORT
+ #define CPMDSK_SUPPORT 1
+#endif
+
+#if CPMDSK_SUPPORT
+
;------------------------------------------ Defines for CPM Structures
#define PART_TYPE 4
#define PART_START 8
-#define PART_SIZE 12\r
-\r
+#define PART_SIZE 12
+
#define PARTID_CPM 0x52 /* Partition table id */
- /* http://www.win.tue.nl/~aeb/partitions/partition_types-1.html */\r
+ /* http://www.win.tue.nl/~aeb/partitions/partition_types-1.html */
;----------------------------------------------- Start of Data Segment
- .dseg\r
-\r
+ .dseg
+
;----------------------------------------------- Start of Code Segment
- .cseg\r
+ .cseg
-; ====================================================================\r
+; ====================================================================
; Function: Does a Disk write operation
-; ====================================================================\r
-; Parameters\r
-; --------------------------------------------------------------------\r
-; Registers : none\r
-; Variables : [r] seekdsk Number of Disk to Read\r
-; [r] seeksec Sector to read\r
-; [r] seektrk Track to read\r
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers : none
+; Variables : [r] seekdsk Number of Disk to Read
+; [r] seeksec Sector to read
+; [r] seektrk Track to read
; hostdsk = host disk #, (partition #)
; hostlba = host block #, relative to partition start
-; Read/Write "hostsize" bytes to/from hostbuf\r
-; --------------------------------------------------------------------\r
-; Description:\r
+; Read/Write "hostsize" bytes to/from hostbuf
+; --------------------------------------------------------------------
+; Description:
; ====================================================================
cpm_hostparam:
lds xl,hostdsk
-\r
+
.if HOSTRW_DEBUG
mov temp,xl
subi temp,-('A')
rcall uartputc
printstring ": "
.endif
-\r
+
rcall dsk_getpartentry ; get partition entry
-\r
+
lds temp,hostlba ; get sector to access
lds temp2,hostlba+1
lds temp3,hostlba+2
add xl,temp ; add offset to startsector
adc xh,temp2
adc yl,temp3
- adc yh,_0\r
+ adc yh,_0
.if HOSTRW_DEBUG
printstring ", abs:"
pop temp3
pop temp4
printstring " "
-.endif\r
+.endif
ori temp,255
cpm_hpex:
ret
-; ====================================================================\r
+; ====================================================================
; Function: Does a Disk write operation
-; ====================================================================\r
-; Parameters\r
-; --------------------------------------------------------------------\r
-; Registers : none\r
-; Variables : [r] seekdsk Number of Disk to Read\r
-; [r] seeksec Sector to read\r
-; [r] seektrk Track to read\r
-; --------------------------------------------------------------------\r
-; Description:\r
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers : none
+; Variables : [r] seekdsk Number of Disk to Read
+; [r] seeksec Sector to read
+; [r] seektrk Track to read
+; --------------------------------------------------------------------
+; Description:
; ====================================================================
cpm_writehost:
breq cpm_rdwr_err
rcall mmcWriteSect
- tst temp
- breq cpm_rdwr_ok
-
- rjmp cpm_rdwr_err ; skip disk change detection code
-
-; After a second thought, the following code doesn't make sense, because
-; disk change (change of one or more disk images) can not reliably detected.
-; At least with the existing code.
-
- rcall mgr_init_partitions ;reinit card
- cbr temp,0x80 ;this should have been a test of bit 7.
- breq cpm_rdwr_err
-
- rcall cpm_hostparam ;if same card, try again.
- breq cpm_rdwr_err
- rcall mmcWriteSect
- tst temp
+ tst temp
brne cpm_rdwr_err
+
rjmp cpm_rdwr_ok
+
-; ====================================================================\r
+; ====================================================================
; Function: Does a Disk read operation
-; ====================================================================\r
-; Parameters\r
-; --------------------------------------------------------------------\r
-; Registers : none\r
-; Variables : [r] seekdsk Number of Disk to Read\r
-; [r] seeksec Sector to read\r
-; [r] seektrk Track to read\r
-; --------------------------------------------------------------------\r
-; Description:\r
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers : none
+; Variables : [r] seekdsk Number of Disk to Read
+; [r] seeksec Sector to read
+; [r] seektrk Track to read
+; --------------------------------------------------------------------
+; Description:
; ====================================================================
cpm_readhost:
.if HOSTRW_DEBUG
printnewline
printstring "host read "
-.endif\r
+.endif
rcall cpm_hostparam
breq cpm_rdwr_err
rcall mmcReadSect
- tst temp
- breq cpm_rdwr_ok
-
- rjmp cpm_rdwr_err ; skip disk change detection code
-
- rcall mgr_init_partitions ;reinit card
- cbr temp,0x80
- breq cpm_rdwr_err
-
- rcall cpm_hostparam ;if same card, try again.
- breq cpm_rdwr_err
- rcall mmcReadSect
- tst temp
+ tst temp
brne cpm_rdwr_err
cpm_rdwr_ok:
- sts erflag,_0
+ sts erflag,_0
ret
cpm_rdwr_err:
- sts erflag,_255
- ret\r
-\r
-\r
-; ====================================================================\r
+ sts erflag,_255
+ ret
+
+
+; ====================================================================
; Function: Add's a CP/M Partition to the Partition table
-; ====================================================================\r
-; Parameters\r
-; --------------------------------------------------------------------\r
-; Registers : none\r
-; Variables : [r] seekdsk Number of Disk to Read\r
-; [r] seeksec Sector to read\r
-; [r] seektrk Track to read\r
-; --------------------------------------------------------------------\r
-; Description:\r
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers : none
+; Variables : [r] seekdsk Number of Disk to Read
+; [r] seeksec Sector to read
+; [r] seektrk Track to read
+; --------------------------------------------------------------------
+; Description:
; ====================================================================
cpm_add_partition:
- \r
- ldi temp,dskType_CPM\r
- st y+,temp\r
+
+ ldi temp,dskType_CPM
+ st y+,temp
ldd temp,z+PART_START
st y+,temp
st y+,temp
ldd temp,z+PART_SIZE+3
st y+,temp
- ret\r
- \r
-#endif\r
+ ret
+
+#endif
; $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_RAM = 3
;*****************************************************
;* CP/M to host disk constants *
.dseg
-ndisks: .byte 1 ;Number of CP/M disks
+; The following 3 variables are copied from DRAM.
+; Don't change order.
+
+biosdrvtbl: .byte 2 ;
+biosdirbuf: .byte 2 ;
+biosenddat: .byte 2 ;
+
+ndisks: .byte 1 ;Number of CP/M disks
+
+; The following 5 variables are accessed from 8080/z80 via the
+; virtual port interface. Don't change order.
-seekdsk: .byte 1 ;seek disk number
-seektrk: .byte 2 ;seek track number
-seeksec: .byte 1 ;seek sector number
+biospar_base:
+bcbadr: .byte 2 ;adr of BiosControlBlock
+seekdsk: .byte 1 ;seek disk number
+seektrk: .byte 2 ;seek track number
+seeksec: .byte 2 ;seek sector number
+dmaadr: .byte 2 ;last dma address
-unacnt: .byte 1 ;unalloc rec cnt
-unadsk: .byte 1 ;last unalloc disk
-unatrk: .byte 2 ;last unalloc track
-unasec: .byte 1 ;last unalloc sector
+unacnt: .byte 1 ;unalloc rec cnt
+unadsk: .byte 1 ;last unalloc disk
+unatrk: .byte 2 ;last unalloc track
+unasec: .byte 1 ;last unalloc sector
-erflag: .byte 1 ;error reporting
-wrtype: .byte 1 ;write operation type
-dmaadr: .byte 2 ;last dma address
+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)
-hostlba: .byte 3 ;host sector number (relative to partition start)
+hostdsk: .byte 1 ;host disk number
+hosttype: .byte 1 ;host disk type (same entry as 1 parition entry)
+hostlba: .byte 3 ;host sector number (relative to partition start)
; ------------------------------- 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
; ====================================================================
; --------------------------------------------------------------------
; Registers : [w] z Pointer to the Partitionentry
; [r] xl Number of Diskentry to Read
+; [w] _tmp0 scratch
+; [w] _tmp1 "
; --------------------------------------------------------------------
; Description:
; ====================================================================
ret
; ====================================================================
-; Function:
+; Function: Virtual Port Interface
; ====================================================================
; Parameters
; --------------------------------------------------------------------
-; Registers : none
-; Variables : [r] seeksec Sector to read
-; [r] seektrk Track to read
+; Registers :
+; Variables :
+;
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+
+dsk_param_getadr:
+ ldiw z,biospar_base
+ add zl,temp3
+ adc zh,_0
+ ret
+
+dsk_param_wr:
+ rcall dsk_param_getadr
+ st z,temp
+ cpi temp3,bcbadr+1-seektrk
+ brne dsk_param_wr1
+ std z+1,_0
+dsk_param_wr1:
+ cpi temp3,bcbadr+1-biospar_base
+ breq SetBCB
+ ret
+
+dsk_param_rd:
+ cpi temp3,seekdsk-biospar_base
+ breq dskDiskCheck
+ rcall dsk_param_getadr
+ 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 dsk_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 temp,ndisks
+ lds temp2,seekdsk
+.if DSKSEL_DEBUG
+ printnewline
+ printstring "DiskCheck: "
+ rcall printhexw
+.endif
+ cpi temp2,RAMDISKNR
brsh dsk_dchrd ;maybe ramdisk
; Check if selected disk # is less then # of disks.
- lds temp,ndisks
- tst temp
+ lds temp,ndisks
+ tst temp ;0 disks?
brne dsk_dchpart1
; No disks yet, need to init
- rcall mgr_init_partitions
- cbr temp,0x80
- lds temp2,seekdsk
+ rcall mgr_init_partitions ;disk chanched?
+; sbrs temp,7
+; rjmp dsk_dchpart0
+ push temp
+ rcall dsk_drvtblinit
+; rcall dbg_prdrvtbl
+ pop temp
+dsk_dchpart0:
+ cbr temp,0x80
+ lds temp2,seekdsk
dsk_dchpart1:
- cp temp2,temp
- brsh dsk_dcher
+ cp temp2,temp
+ brsh dsk_dch_err
+
+.if DSKSEL_DEBUG
+ printnewline
+ printstring "Select: "
+ mov temp,temp2
+ rcall printhex
+.endif
+ ldsw x,biosdrvtbl
+ lsl temp2 ;drive #
+ add xl,temp2
+ adc xh,_0
+ rcall dram_readw_pp ;get drive table entry
+
+ or temp,temp2 ;if !0, drive is allready initialized
+ brne dsk_dchend
+ lds temp,seekdsk
+ rcall dsk_diskinit
dsk_dchend:
- ldi temp,0
+.if DSKSEL_DEBUG
+ push temp
+ ldsw x,biosdrvtbl
+ lds temp,seekdsk
+ lsl temp ;drive #
+ add xl,temp
+ adc xh,_0
+ rcall dram_readw_pp
+ 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
+ cpi temp,RAMDISKNR+RAMDISKCNT
+ brsh dsk_dchrd_err
+
+ ldi temp,0xff ;return ok
+ ret
#endif
-dsk_dcher:
- ldi temp,0xff ;error return
+dsk_dchrd_err:
+ ldi temp,0 ;error return
ret
-
+
+
+; ====================================================================
+; Function: Return status of last disk i/o function
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
dskErrorRet:
- lds temp,erflag
+ lds temp,erflag
ret
-dskDiskSel:
- sts seekdsk,temp
- ret
+
+; -------------------------------------------------------------------
-dskTrackSel_l:
- sts seektrk,temp
- sts seektrk+1,_0
- ret
-dskTrackSel_h:
- sts seektrk+1,temp
+ .dseg
+tmpdpb: .byte 15
+
+ .cseg
+
+; 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
+#if 0
+;rd1016
+ .db 0x20,0x00 ;spt
+ .db 0x04,0x0F ;block shift, bock mask
+ .db 0x00,0xFB ;extent mask, low(disk size -1),
+ .db 0x01,0xBF ;high(disk size -1), low(dir max)
+ .db 0x00,0xE0 ;high(dir max), alloc0
+ .db 0x00,0x30 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
+;rd9192s
+ .db 0x20,0x00 ;spt
+ .db 0x05,0x1F ;block shift, bock mask
+ .db 0x01,0xFD ;extent mask, low(disk size -1),
+ .db 0x07,0xFF ;high(disk size -1), low(dir max)
+ .db 0x01,0xF0 ;high(dir max), alloc0
+ .db 0x00,0x80 ;alloc1, low(chk size)
+ .db 0x00,0x02 ;high(chk size), low(offset)
+ .db 0x00,0x00 ;high(offset), fill
+#endif
+
+; Test
+cpy_dpb:
+ push zh
+ push zl
+ push yh
+ push yl
+ ldiw z,dpblist*2
+ ldi temp2,16
+ mul temp,temp2
+ add zl,_tmp0
+ adc zh,_tmp1
+ ldiw y,tmpdpb
+cpydpb_l:
+ lpm temp,z+
+ st y+,temp
+ cpi yl,low(tmpdpb + 15)
+ brne cpydpb_l
+ pop yl
+ pop yh
+ pop zl
+ pop zh
ret
+
+; clear drive table
+; for now, only entries 1 - 3 are cleared.
-dskSecSel:
- sts seeksec,temp
+; ====================================================================
+; Function: Clear drive table
+; ====================================================================
+; Parameters
+; --------------------------------------------------------------------
+; Registers :
+; Variables :
+;
+; --------------------------------------------------------------------
+; Description:
+; ====================================================================
+
+; For now, only entries 1 - 3 are cleared.
+
+dsk_drvtblinit:
+ ldsw x,biosdrvtbl
+ adiw x,2
+ ldi temp3,3
+dsk_drvi_l:
+ ldi temp,0
+ ldi temp2,0
+ rcall dram_writew_pp
+ dec temp3
+ brne dsk_drvi_l
+
+ lds temp,biosenddat
+ lds temp2,biosenddat+1
+ rcall heap_init
+ clr temp
ret
-dskDmal:
- sts dmaadr,temp
+
+; ----------------------------------------------------------------------
+; Init CP/M data structures
+; temp = drive #
+;
+; return !0 if ok
+; 0 on error
+
+
+dsk_diskinit:
+ mov temp3,temp ;save disk #
+
+
+; Test
+ rcall cpy_dpb
+
+
+
+
+; get mem for DPH
+; -----------------------------------------------------------------
+; DPH: | XLT | | | |DIRBUF | DPB | CSV | ALV |
+; -----------------------------------------------------------------
+;(offset) 0 2 4 6 8 10 12 14
+
+ ldi temp, low (16)
+ ldi temp2,high(16)
+ rcall heap_get
+ brne dsk_di_1
+ rjmp dsk_di_err ;
+dsk_di_1:
+ movw x,temp
+ movw y,temp
+ ldi temp,0
+ ldi temp2,0
+ rcall dram_writew_pp ;XLT
+ adiw x,6
+ lds temp,biosdirbuf
+ lds temp2,biosdirbuf+1
+ 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
+
+ ldi temp, low (15)
+ ldi temp2,high(15)
+ rcall heap_get
+ breq dsk_di_err_p1
+ movw x,temp
+
+ ldiw z,tmpdpb
+dsk_dicpl:
+ ld temp,z+
+ rcall dram_write_pp
+ cpi zl,low(tmpdpb + 15)
+ brne dsk_dicpl
+ sbiw x,15
+ movw temp,x
+ movw x,y
+ adiw x,10
+ rcall dram_writew_pp ;DPB
+
+; get mem for dir check vector
+
+ lds temp,tmpdpb+11 ;cks
+ lds temp2,tmpdpb+11+1
+ cp temp,_0
+ cpc temp2,_0
+ breq dsk_dicks0
+ rcall heap_get
+ breq dsk_di_err_p1
+dsk_dicks0:
+ rcall dram_writew_pp ;CSV
+
+; get mem for alloc vector
+
+ lds temp,tmpdpb+5 ;dsm
+ lds temp2,tmpdpb+5+1
+ subi temp, low (-8)
+ sbci temp2,high(-8)
+ lsr temp2
+ ror temp
+ lsr temp2
+ ror temp
+ lsr temp2
+ ror temp ;(dsm+1+7)/8
+ rcall heap_get
+ breq dsk_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
+ movw temp,y
+ rcall dram_writew_pp
+ ori temp,0xff ;return ok
ret
-dskDmah:
- sts dmaadr+1,temp
+; error, free mem
+
+dsk_di_err_p1:
+ movw temp,y
+ rcall heap_release
+dsk_di_err:
+ eor temp,temp ;return 0 (+ Z-flag)
ret
+
; ====================================================================
; Function: Does a Disk interaction
dsk_read:
sts erflag,_0
sbi flags,readop ; Set read operation flag
+
;RAM disk?
lds xl,seekdsk
#if RAMDISKCNT
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
\r
.dseg\r
\r
-\r
-; Partition table offsets:\r
-tmp_tbl:\r
- .byte PARTENTRY_SIZE*MAXDISKS\r
-\r
; ------------------------------- Start of Code Segment\r
.cseg\r
\r
; ==================================================================== \r
mgr_init_partitions:\r
\r
- sts ndisks,_0 ; Set Number of Disks to 0\r
+ sts ndisks,_0 ; Set Number of Disks to 0\r
\r
-; Initialize temp partition table\r
- ldiw y,tmp_tbl\r
- ldi temp2,PARTENTRY_SIZE*MAXDISKS\r
+; Initialize partition table\r
+ ldiw y,hostparttbl\r
+ ldi temp2,PARTENTRY_SIZE*MAXDISKS\r
mgr_picl:\r
- st y+,_0\r
- dec temp2\r
+ st y+,_0\r
+ dec temp2\r
brne mgr_picl\r
\r
; Start mmc Card interaction\r
ldiw y,0 ; Sector 0\r
movw x,y\r
lcall mmcReadSect\r
- tst temp\r
+ tst temp\r
breq mgr_check_bootsektor\r
\r
mgr_pierr:\r
ret\r
\r
mgr_check_bootsektor:\r
-;Pointer to first temp table entry\r
- ldiw y,tmp_tbl\r
-;Test, if it has a valid MBR\r
+;Pointer to first table entry\r
+ ldiw y,hostparttbl\r
+ ldi temp3,0 ;temp3 holds number of found disks (paritions)\r
\r
- ldiw z,hostbuf+510-1 ;Point to last byte of partition table\r
+;Test, if it has a valid MBR\r
\r
- ldi temp3,0 ;temp3 holds number of found disks (paritions)\r
- ldd temp,z+1 ;MBR signature (0xAA55) at and of sector?\r
- ldd temp2,z+2\r
- ldi temp4,0xAA\r
- cpi temp,0x55 \r
- cpc temp2,temp4\r
+ lds temp,hostbuf+510 ;MBR signature (0xAA55) at and of sector?\r
+ lds temp2,hostbuf+510+1\r
+ ldi temp4,0xAA\r
+ cpi temp,0x55 \r
+ cpc temp2,temp4\r
breq mgr_search\r
\r
;No MBR, no partition table ...\r
- inc temp3 ;pretend we have one.\r
- ldi temp,high((1<<16) * 128/512)\r
+\r
+ inc temp3 ;pretend we have one.\r
+ sts ndisks,temp3\r
+ ldi temp,high((1<<16) * 128/512)\r
ldi temp2,dskType_CPM\r
- std y+0,temp2\r
- std y+1,_0 ;start at beginning of card\r
- std y+2,_0\r
- std y+3,_0\r
- std y+4,_0\r
- std y+5,_0 ;max CP/M 2.2 disk size\r
- std y+6,temp ;\r
- std y+7,_0\r
- std y+8,_0\r
+ std y+0,temp2\r
+ std y+1,_0 ;start at beginning of card\r
+ std y+2,_0\r
+ std y+3,_0\r
+ std y+4,_0\r
+ std y+5,_0 ;max CP/M 2.2 disk size\r
+ std y+6,temp ;\r
+ std y+7,_0\r
+ std y+8,_0\r
rjmp mgr_pend\r
\r
; Search for valid Partitions and ImageFiles \r
mgr_search:\r
- sbiw z,63 ;Now at first byte of partition table\r
- ldi temp4,high(hostbuf+510)\r
+ ldiw z,hostbuf+510-64 ;Point to first byte of partition table\r
+ ldi temp4,4 ;Partition table has 4 entries.\r
\r
mgr_ploop:\r
\r
; Get Partitiontype\r
- ldd temp,z+PART_TYPE\r
+ ldd temp,z+PART_TYPE\r
\r
; Test for CP/M Partition\r
- cpi temp,PARTID_CPM\r
+ cpi temp,PARTID_CPM\r
brne mgr_nextp\r
\r
rcall cpm_add_partition\r
\r
- inc temp3\r
- cpi temp3,MAXDISKS\r
+ inc temp3\r
+ sts ndisks,temp3\r
+ cpi temp3,MAXDISKS\r
breq mgr_pend\r
\r
mgr_nextp:\r
adiw zl,16\r
- cpi zl,low(hostbuf+510)\r
- cpc zh,temp4\r
- brlo mgr_ploop\r
+ dec temp4\r
+ brne mgr_ploop\r
\r
#if FAT16_SUPPORT\r
\r
; Test for FAT16 Partition\r
- ldiw z,hostbuf+510-1-63 ;Point to first byte of partition table\r
- ldi temp4,high(hostbuf+510)\r
+ ldiw z,hostbuf+510-64 ;Point to first byte of partition table\r
+ ldi temp4,4\r
\r
mgr_ploop2:\r
-\r
; Get Partitiontype\r
- ldd temp,z+PART_TYPE\r
+ ldd temp,z+PART_TYPE\r
\r
; Test for FAT Partition\r
- cpi temp,PARTID_FAT16\r
+ cpi temp,PARTID_FAT16\r
brne mgr_nextp2\r
\r
- rcall fat_add_partition\r
+ rcall fat_add_partition\r
\r
- rjmp mgr_pend\r
+ rcall fat_scan_partition\r
+ rcall fat_reset_cache\r
+\r
+ rjmp mgr_pend ;Stop after first FAT16 parrtition found.\r
\r
mgr_nextp2:\r
adiw zl,16\r
- cpi zl,low(hostbuf+510)\r
- cpc zh,temp4\r
- brlo mgr_ploop2\r
+ dec temp4\r
+ brne mgr_ploop2\r
#endif\r
\r
mgr_pend:\r
-\r
-#if 0 /* ToDo: ramdisks are not in sd-card partitions */\r
-; Initialize RAM-Disks\r
- rcall rdsk_add_partition\r
-#endif\r
-\r
-/*\r
- Don't use change info. It doesn't word reliably with partitions, \r
- and it doesn't work at all with fat images:\r
-*/\r
-#define CHANGEINFO 0\r
-\r
-;Store new partitions and check if the SD card has been changed.\r
-\r
- ldiw y,tmp_tbl\r
- ldiw z,hostparttbl\r
- ldi temp4,PARTENTRY_SIZE*MAXDISKS\r
- clt\r
-\r
-mgr_pcpl:\r
- ld temp,y+\r
- ld temp2,z\r
- st z+,temp\r
- cpse temp,temp2\r
- set\r
- dec temp4\r
- brne mgr_pcpl\r
-\r
- mov temp,temp3\r
- sts ndisks,temp\r
-#if CHANGEINFO\r
- brtc mgr_pcpe\r
-\r
-; SD card changed.\r
-#endif\r
- tst temp\r
- breq mgr_pcpe\r
-\r
-\r
-#if FAT16_SUPPORT\r
- rcall fat_scan_partition\r
- rcall fat_reset_cache
-#endif\r
- lds temp,ndisks\r
-#if CHANGEINFO\r
- sbr temp,0x80\r
-#endif\r
-\r
-mgr_pcpe:\r
-\r
+ lds temp,ndisks ;return # of "disks"\r
tst temp\r
ret\r
\r
\r
mgr_prnt_parttbl:\r
ldiw z,hostparttbl\r
- lds yl,ndisks\r
- ldi xh,'A'\r
+ lds yl,ndisks\r
+ ldi xh,'A'\r
\r
-pprl:
- ldd temp ,z+1 ;Get partition start
- ldd temp2,z+2
- ldd temp3,z+3
- ldd temp4,z+4
+pprl:\r
+ ldd temp ,z+1 ;Get partition start\r
+ ldd temp2,z+2\r
+ ldd temp3,z+3\r
+ ldd temp4,z+4\r
\r
printnewline\r
\r
- cp temp,_0 ;If zero ...
- cpc temp2,_0
- cpc temp3,_0
- cpc temp4,_0
- breq mgr_prnop ;... no partition table at 0
+ cp temp,_0 ;If zero ...\r
+ cpc temp2,_0\r
+ cpc temp3,_0\r
+ cpc temp4,_0\r
+ breq mgr_prnop ;... no partition table at 0\r
\r
; Partitiontype examining\r
ldd xl,z+0\r
; CP/M ?\r
- cpi xl,dskType_CPM\r
+ cpi xl,dskType_CPM\r
brne mgr_prtb_nocpm\r
rcall mgr_prnt_diskname\r
rcall mgr_prnt_table_cpm\r
rjmp mgr_prnt_size\r
\r
-; FAT16 ?\r
mgr_prtb_nocpm:\r
- cpi xl,dskType_FAT\r
+#if FAT16_SUPPORT\r
+; FAT16 ?\r
+ cpi xl,dskType_FAT\r
brne mgr_prtb_nofat\r
rcall mgr_prnt_diskname\r
rcall mgr_prnt_table_fat\r
rjmp mgr_prnt_size\r
-; RAMDISK ?\r
mgr_prtb_nofat:\r
- cpi xl,dskType_RAM\r
+#endif\r
+#if 0 /* RAMDISK is not on SD card */\r
+; RAMDISK ?\r
+ cpi xl,dskType_RAM\r
brne mgr_prnt_err\r
rcall mgr_prnt_diskname\r
rcall mgr_prnt_table_ram\r
rjmp mgr_prnt_size\r
-; Entry Error\r
+#endif\r
mgr_prnt_err: \r
+; Entry Error\r
rcall mgr_prnt_table_err\r
rjmp mgr_prnt_size\r
\r
rcall mgr_prnt_image\r
\r
mgr_prnt_size:\r
- call print_ultoa
+ lcall print_ultoa\r
printstring ", size: "\r
\r
- ldd temp ,z+5 ;Get partition size\r
- ldd temp2,z+6 ;Get partition size\r
- ldd temp3,z+7 ;Get partition size\r
- ldd temp4,z+8 ;Get partition size\r
+ ldd temp ,z+5 ;Get partition size\r
+ ldd temp2,z+6\r
+ ldd temp3,z+7\r
+ ldd temp4,z+8\r
\r
- lsr temp4\r
- ror temp3\r
- ror temp2\r
- ror temp\r
- call print_ultoa
+ lsr temp4\r
+ ror temp3\r
+ ror temp2\r
+ ror temp\r
+ lcall print_ultoa\r
printstring "KB."\r
\r
mgr_goto_next_part: \r
adiw z,PARTENTRY_SIZE\r
- inc xh
- dec yl\r
- tst yl\r
- brne pprl
+ inc xh\r
+ dec yl\r
+ brne pprl\r
\r
mgr_pppre:\r
ret\r
lcall print_ultoa\r
printstring ", size: "\r
\r
- ldd temp ,z+5 ;Get partition size\r
- ldd temp2,z+6 ;Get partition size\r
- ldd temp3,z+7 ;Get partition size\r
- ldd temp4,z+8 ;Get partition size\r
+ ldd temp ,z+5 ;Get partition size\r
+ ldd temp2,z+6\r
+ ldd temp3,z+7\r
+ ldd temp4,z+8\r
\r
lcall print_ultoa\r
printstring "BYTE."\r
\r
- rjmp mgr_goto_next_part\r
+ rjmp mgr_goto_next_part\r
\r
mgr_prnt_diskname:\r
push temp\r
- mov temp,xh
- call uartputc\r
- ldi temp,':'
- call uartputc\r
- pop temp\r
+ mov temp,xh\r
+ lcall uartputc\r
+ ldi temp,':'\r
+ lcall uartputc\r
+ pop temp\r
ret\r
\r
mgr_prnt_table_cpm:\r
; Virtual Ports for the BIOS Interaction
;
-; Copyright (C) 2010 Frank Zoll
+; Copyright (C) 2010 Leo C.
;
; This file is part of avrcpm.
;
; along with avrcpm. If not, see <http://www.gnu.org/licenses/>.
;
; $Id$
-;\r
-\r
-\r
-; ---------------- Defines for the Virtual peripherial interface -------
-
-;The hw is modelled to make writing a CPM BIOS easier.
-;Ports:
-;0 - Con status. Returns 0xFF if the UART has a byte, 0 otherwise.
-;1 - Console input, aka UDR.
-;2 - Console output
-;3 - "UART" status: bit 0=rx, bit 1 = tx
-;4 - "UART" data register, no wait
-;15 - Disk select
-;16,17 - Track select
-;18 - Sector select
-;20 - Write addr l
-;21 - Write addr h
-;22 - Trigger - write to read, to write a sector using the above info;
-; , write to allocated/dirctory/unallocated
-
-;----------------------------------------------- Start of Data Segment
-
- .dseg\r
-\r
-\r
+;
+
+
+;
+; Port Direction Function
+;hex dez
+;-------------------------------------------------------------------------
+;00 0 in - Con status.
+; Returns 0xFF if the UART has a byte, 0 otherwise.
+;01 1 in/out - Console input, aka UDR. / Console Output
+;02 2 out - Console Output (deprecated)
+;03 3 in - "UART" status: bit 0 = rx, bit 1 = tx
+;04 4 in - "UART" data register, no wait
+;
+;0D,0E 13,14 in/out - Set address of Bios Controll Block
+;0F 15 in/out - Disk select
+;10,11 16,17 in/out - Track select
+;12,13 18,19 in/out - Sector select
+;14,15 20,21 in/out - Write addr
+;
+;16 22 out - Trigger disk i/o operations
+; Bit 7 = 1: Read sector
+; Bit 6 = 1: Write sector
+; Bit 5 = 1: BIOS WBOOT
+; Bit 4 = 1: BIOS Home
+; Only one of bits 4..7 may be set.
+; If Write function (bit 6=1):
+; Bits 0..2: 0 - write to allocated
+; 1 - write to directory
+; 2 - write unallocated
+; 3 - write to directory
+;
+;16 22 in - Result of last read/write operation.
+; 0x00 = ok, 0xff = error (--> Bad Sector)
+;
+;40 64-71 in/out - Timer/Clock controll.
+;46
+
+
; ---------------------------------------------- Start of Code Segment
- .cseg\r
-\r
+ .cseg
+vport_tbl:
+ .db 00,1 ;Port 0, length 1
+ .dw conStatus ; in
+ .dw dbgOut ; out
+ .db 01,1
+ .dw uartgetc
+ .dw uartputc
+ .db 02,1 ;Port 2 (old console output)
+ .dw uartgetc ; filler
+ .dw uartputc ; deprecated
+ .db 03,1
+ .dw uartstat
+ .dw vport_out_dummy
+ .db 04,1
+ .dw uartin
+ .dw uartout
+
+ .db 13,9 ; Port 13-21, (lenth 9)
+ .dw dsk_param_rd
+ .dw dsk_param_wr
+ .db 22,1
+ .dw dskErrorRet
+ .dw dskDoIt
+
+ .db TIMERPORT,7
+ .dw clockget
+ .dw clockput
+ .db 0,0 ; Stop mark
+
+;---------------------------------------------------------------------
+
+;Called with port in temp2 and value in temp.
+portWrite:
+ set
+ rjmp vprw_start
+
+;Called with port in temp2. Should return value in temp.
+portRead:
+ clt
+
+vprw_start:
+.if PORT_DEBUG > 1
+ tst temp2
+ brne dvp_1 ;don't debug console status
+ brts dvp_1
+ rjmp conStatus
+dvp_1:
+ printnewline
+ brts dvp_11
+ printstring "Port In: "
+ rjmp dvp_12
+dvp_11:
+ printstring "Port Out: "
+dvp_12:
+ push temp
+ mov temp,temp2
+ rcall printhex
+ pop temp
+.endif
+ ldiw z,vport_tbl*2
+
+vprw_loop:
+ lpm _tmp0,z+
+ lpm temp4,z+ ;length
+ cpi temp4,0
+ breq vprw_exit ;no more ports
+
+ mov temp3,temp2
+ sub temp3,_tmp0 ;base port
+ brcs vprw_next ;port # too high
+ cp temp3,temp4 ;may be in range
+ brcs vprw_found ;
+vprw_next: ;port # not in range, test next block.
+ adiw z,4
+ rjmp vprw_loop
+vprw_found:
+ brtc PC+2
+ adiw z,2
+ lpm _tmp0,z+
+ lpm _tmp1,z+
+ movw z,_tmp0
+
+.if PORT_DEBUG > 1
+ push temp2
+ push temp
+ printstring ", exec: "
+ movw temp,z
+ rcall printhexw
+ printstring ", rel port: "
+ mov temp,temp3
+ rcall printhex
+ pop temp
+ pop temp2
+ printstring ", val: "
+ brts dvp_2
+ icall
+ rcall printhex
+ printstring " "
+ ret
+dvp_2:
+ rcall printhex
+ printstring " "
+ ijmp ; relative port # in temp3
+.else
+ ijmp
+.endif
+
+vprw_exit:
+ ; trap for nonexistent port?
+.if PORT_DEBUG > 1
+ printstring ", not found!"
+.endif
+vport_in_dummy:
+ ldi temp,0xff
+vport_out_dummy:
+ ret
+
+
uartstat:
clr temp
lds temp2,rxcount
uartst_1:
ret
+uartin:
+ clr temp
+ lds temp2,rxcount
+ cpse temp2,_0
+ rjmp uartgetc
+ ret
+
uartout:
lds temp2,txcount
cpi temp2,TXBUFSIZE
uartout_1:
ret
-uartin:
- clr temp
- lds temp2,rxcount
- cpse temp2,_0
- rjmp uartgetc
- ret\r
-\r
+
conStatus:
lds temp,rxcount
cpse temp,_0
ldi temp,0xff
ret
-conInp:
- rjmp uartgetc
dbgOut:
printnewline
rcall printhex
ret
-conOut:
- rjmp uartputc\r
-\r
-;Called with port in temp2. Should return value in temp.
-portRead:
- cpi temp2,0
- breq conStatus
- cpi temp2,1
- breq conInp
- cpi temp2,3
- breq uartstat
- cpi temp2,4
- breq uartin
-
- cpi temp2,15
- breq dskDiskCheck
- cpi temp2,22
- breq dskErrorRet
-
- cpi temp2,TIMER_MSECS
- brlo pr_noclock
- cpi temp2,TIMER_MSECS+6
- brsh pr_noclock
- rjmp clockget
-
-pr_noclock:
- ldi temp,0xFF
- ret
-
-;Called with port in temp2 and value in temp.
-portWrite:
- cpi temp2,0
- breq dbgOut
- cpi temp2,2
- breq conOut
- cpi temp2,4
- breq uartout
-
- cpi temp2,15
- breq dskDiskSel
- cpi temp2,16
- breq dskTrackSel_l
- cpi temp2,17
- breq dskTrackSel_h
- cpi temp2,18
- breq dskSecSel
- cpi temp2,20
- breq dskDmaL
- cpi temp2,21
- breq dskDmaH
-
- cpi temp2,22
- breq dskDoIt
-
- cpi temp2,TIMERPORT
- brlo pw_noclock
- cpi temp2,TIMER_MSECS+6
- brsh pw_noclock
- rjmp clockput
-
-pw_noclock:
- ret\r
-\r
-
-\r
;---------------------------------------------------------------------
+; vim:set ts=8 noet nowrap
+