diff --git a/CPM_v2.2_r7_b89a7e16/bios.asm b/CPM_v2.2_r7_b89a7e16/bios.asm index bcc655d..6d65a5c 100644 --- a/CPM_v2.2_r7_b89a7e16/bios.asm +++ b/CPM_v2.2_r7_b89a7e16/bios.asm @@ -557,10 +557,10 @@ print_strz: JP print_strz msg_hello: - DB ASCII_ESC, "60" ; Режим 32x18 60 + DB ASCII_ESC, "6", 0x30 ; Режим 32x18 60 DB ASCII_ESC, "8", 2 ; Выбор палтитры 82 - DB ASCII_ESC, "42" ; Выбор цвета 42 - DB "48K CP/M (V2.2) REL.7/2D\r\n64K RAM DISK (A:)\r\n180K FD (B:)\r\n", 0 + DB ASCII_ESC, "4", 0x32 ; Выбор цвета 42 + DB "48K CP/M (V2.2) REL.7/2D\r\n64K RAM DISK (A:)\r\n720K FD (B:)\r\n", 0 ; -------------------------------------------------- ; Disk parameters headers in ROM @@ -632,18 +632,33 @@ DPB_64K: DW 0008h ; CKS checksum vector size (8 sectors=1k) DW 0000h ; OFF (tracks reserved for system) -; For FLOPPY 360k -DPB_360K: - DW 0024h ; SPT Sector (128b) per track 36 * 128 = 18KB - DB 04h ; BSH 2k - DB 0Fh ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k - DB 01h ; EXM extent mask - DW 00B3h ; DSM Disk size blocks - 1 (179d) - DW 003Fh ; DRM Directory entries - 1 (63d) - DB 10000000b ; AL0 Dir map byte 1 - DB 00000000b ; AL1 Dir map byte 2 - DW 0010h ; CKS checksum vector size (16 sectors = 2k) - DW 0000h ; OFF (No of tracks reserved for system) +; ; For FLOPPY 360k +; DPB_360K: +; DW 36 ; SPT Sector (128b) per track 36 * 128 = 18KB +; DB 4 ; BSH 2k +; DB 15 ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k +; DB 1 ; EXM extent mask +; DW 179 ; DSM Disk size blocks - 1 (179d) +; DW 63 ; DRM Directory entries - 1 (63d) +; DB 10000000b ; AL0 Dir map byte 1 +; DB 00000000b ; AL1 Dir map byte 2 +; DW 0010h ; CKS checksum vector size (16 sectors = 2k) +; DW 0000h ; OFF (No of tracks reserved for system) + +; For FLOPPY 720k +dpb_flop_720k: + DW 36 ; SPT Sector (128b) per track 36 * 128 = 18KB + DB 4 ; BSH 2k + DB 15 ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k + DB 0 ; EXM extent mask + DW 359 ; DSM Disk size blocks - 1 (359d) + DW 127 ; DRM Directory entries - 1 (127d) + DB 11000000b ; AL0 Dir map byte 1 (2 dir blk) + DB 00000000b ; AL1 Dir map byte 2 + DW 32 ; CKS checksum vector size (32 sectors = 2k) + DW 0x0000 ; OFF (No of tracks reserved for system) + + DPB_END: DB 4h ; reserved diff --git a/CPM_v2.2_r8_bc0695e4/README.md b/CPM_v2.2_r8_bc0695e4/README.md index ba194e1..b264655 100644 --- a/CPM_v2.2_r8_bc0695e4/README.md +++ b/CPM_v2.2_r8_bc0695e4/README.md @@ -21,7 +21,7 @@ To compile sources, use [sjasmplus Z80 assembler](https://github.com/z00m128/sja It is assumed that there is a USB-RS232 (USB-TTL) adapter on the /dev/ttyUSB0. 1) At Ocean's CP/M command line: - + A>READ 2) At Linux terminal, configure tty for 4800,8N2: @@ -32,7 +32,6 @@ It is assumed that there is a USB-RS232 (USB-TTL) adapter on the /dev/ttyUSB0. cat okeah.hex > /dev/ttyUSB0 - srec_cat - Utility from **srecord** package - collection of tools for manipulating EPROM load files. [Forum topic](https://zx-pk.ru/threads/35390-zagruzka-hex-fajlov-direktivoj-l-monitora.html) diff --git a/CPM_v2.2_r8_bc0695e4/bdos.asm b/CPM_v2.2_r8_bc0695e4/bdos.asm index 3cae2b1..93232a2 100644 --- a/CPM_v2.2_r8_bc0695e4/bdos.asm +++ b/CPM_v2.2_r8_bc0695e4/bdos.asm @@ -2604,6 +2604,7 @@ bdos_get_file_size: RET ; ------------------------------------------------------- +; (F_RANDREC) - Update random access pointer ; Set the random record count bytes of the FCB to the number ; of the last record read/written by the sequential I/O calls. ; ------------------------------------------------------- diff --git a/CPM_v2.2_r8_bc0695e4/bios.asm b/CPM_v2.2_r8_bc0695e4/bios.asm index dedb8dc..d18e2e9 100644 --- a/CPM_v2.2_r8_bc0695e4/bios.asm +++ b/CPM_v2.2_r8_bc0695e4/bios.asm @@ -10,6 +10,8 @@ INCLUDE "ram.inc" INCLUDE "mon_entries.inc" + DEFINE CHECK_INTEGRITY + IFNDEF BUILD_ROM OUTPUT bios.bin ENDIF @@ -118,11 +120,11 @@ tape_wait_f: JP warm_boot ; r8 -disk_a_size DW 0x00C0 ; 192k disk A size -disk_b_size DW 0x02d0 ; 720 disk B size -disk_c_size DW 0x02d0 ; 720 disk C size -bios_var04 DB 0x50 -bios_var05 DB 0x50 +disk_a_size DW 192 ; 192k disk A size +disk_b_size DW 720 ; 720 disk B size +disk_c_size DW 720 ; 720 disk C size +disk_b_tracks DB 80 +disk_c_tracks DB 80 ; ------------------------------------------------------- ; cold start @@ -189,8 +191,8 @@ bios_init_ilv: LD DE, bios_ini_vals LD C, 13 CALL mov_dlhe_c - LD A, (bios_var05) ; 0x50 - LD (bios_var2), A + LD A, (disk_c_tracks) ; 0x50 + LD (disk_c_tracks), A RET ; << @@ -267,43 +269,51 @@ bios_wboot: ; r8 LD HL, CCP_RAM.bdos_enter_jump LD (bdos_ent_addr), HL + ; Disk A LD HL, CPM_VARS.DPB_A_RAM LD C, 0xf LD DE, dpb_ram LD A, (disk_a_size+1) OR A - JP Z, set_curr_dpb + JP Z, .drv_a_192 LD DE, dpb_empty - -set_curr_dpb: +.drv_a_192: CALL mov_dlhe_c + + ; Disk B LD HL, CPM_VARS.DPB_B_RAM LD C, 0xf LD DE, dpb_flop_360k LD A, (disk_b_size+1) CP 0x1 - JP Z, .l1 + JP Z, .drv_b_360 LD DE, dpb_flop_720k -.l1 +.drv_b_360: CALL mov_dlhe_c + + ; Disk C LD HL, CPM_VARS.DPB_C_RAM LD C, 0xf LD A, (disk_c_size+1) - CP 0x2 - JP Z, .l2 + CP 0x2 ; 720? + JP Z, .drv_c_720 LD DE, dpb_flop_360k - LD A, (bios_var3) + ; bios_var3 != 0 -> move DPB 360k + LD A, (disk_sw_trk) OR A - JP NZ, .l3 + JP NZ, .drv_c_mov + ; bios_var3 == 0 -> move DPB 720k LD DE, dpb_flop_720k - JP .l3 -.l2 + JP .drv_c_mov +.drv_c_720: LD DE, dpb_flop_720k - LD A, (bios_var3) + ; bios_var3 != 0 -> move DPB 720k + LD A, (disk_sw_trk) OR A - JP NZ, .l3 + JP NZ, .drv_c_mov + ; bios_var3 == 1 -> move DPB 360k LD DE, dpb_flop_360k -.l3 +.drv_c_mov: CALL mov_dlhe_c XOR A LD (CPM_VARS.slicer_has_data),A @@ -576,7 +586,7 @@ calc_sec_addr_in_bfr: LD A, (CPM_VARS.curr_sec) AND 0x3 LD L, A - LD H, 0x0 + LD H, 0 ADD HL, HL ADD HL, HL ADD HL, HL @@ -637,7 +647,7 @@ slicer_get_floppy_args: DEC A JP Z, .non_interleave LD HL, interleave_0 -.non_interleave +.non_interleave: LD A, (CPM_VARS.slicer_real_sector) ADD A, L LD L, A @@ -665,16 +675,16 @@ print_strz: JP print_strz msg_hello: - DB ASCII_ESC, "60" ; Режим 32x18 60 - DB ASCII_ESC, "83" - DB ASCII_ESC, "5!%" - DB ASCII_ESC, "41" - DB ASCII_ESC, "1", 0x16, 0xe2, 0xe2, 0xfc, 0x01 - DB ASCII_ESC, "40" - DB ASCII_ESC, "1", 0x1e, 0xe6, 0xdb, 0xf8, 0x01 - DB ASCII_ESC, "43" + DB ASCII_ESC, "6", "0" ; 40x25 cursor on + DB ASCII_ESC, "8", "3" ; set palette + DB ASCII_ESC, "5", 33, 37 ; set cursor r,c + DB ASCII_ESC, "4", "1" ; set color + DB ASCII_ESC, "1", 22, 226, 226, 252, 1 ; draw fill rect x1,y1,x2,y2,m + DB ASCII_ESC, "4", "0" ; set color + DB ASCII_ESC, "1", 30, 230, 219, 248, 1 ; draw fill rect x1,y1,x2,y2,m + DB ASCII_ESC, "4", "3" ; set color DB "OKEAH-240 CP/M (V2.2) REL.8'\r\n\n" - DB ASCII_ESC, "42", 0 + DB ASCII_ESC, "4", "2", 0 ; set color ; -------------------------------------------------- @@ -704,47 +714,47 @@ msg_hello: ; ------------------------------------- ; CKS - number of dir sectors to check before write, 0 for HDD -; For RAM-Disk 128k +; For RAM-Disk 192k dpb_ram: - DW 0010h ; SPT Sector (128b) per track (16d) - DB 03h ; BSH 1k - DB 07h ; BLM 1k; Allocation block size = (BLM + 1) * 128 = 1k - DB 00h ; EXM extent mask + DW 16 ; SPT Sector (128b) per track (16d) + DB 3 ; BSH 1k + DB 7 ; BLM 1k; Allocation block size = (BLM + 1) * 128 = 1k + DB 0 ; EXM extent mask DW 191 ; DSM Disk size blocks - 1 DW 31 ; DRM Dir elements - 1 DB 10000000b ; AL0 Dir map byte 1 DB 00000000b ; AL1 Dir map byte 2 - DW 0008h ; CKS checksum vector size (8 sectors=1k) - DW 0000h ; OFF (tracks reserved for system) + DW 0x0008 ; CKS checksum vector size (8 sectors=1k) + DW 0x0000 ; OFF (tracks reserved for system) dpb_empty: DS 15, 0xff ; For FLOPPY 720k dpb_flop_720k: - DW 0024h ; SPT Sector (128b) per track 36 * 128 = 18KB - DB 04h ; BSH 2k - DB 0Fh ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k - DB 00h ; EXM extent mask + DW 36 ; SPT Sector (128b) per track 36 * 128 = 18KB + DB 4 ; BSH 2k + DB 15 ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k + DB 0 ; EXM extent mask DW 359 ; DSM Disk size blocks - 1 (359d) DW 127 ; DRM Directory entries - 1 (127d) DB 11000000b ; AL0 Dir map byte 1 (2 dir blk) DB 00000000b ; AL1 Dir map byte 2 DW 32 ; CKS checksum vector size (32 sectors = 2k) - DW 0000h ; OFF (No of tracks reserved for system) + DW 0x0000 ; OFF (No of tracks reserved for system) ; For FLOPPY 360k dpb_flop_360k: - DW 0024h ; SPT Sector (128b) per track 36 * 128 = 18KB - DB 04h ; BSH 2k - DB 0Fh ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k - DB 01h ; EXM extent mask + DW 36 ; SPT Sector (128b) per track 36 * 128 = 18KB + DB 4 ; BSH 2k + DB 15 ; BLM 2k; Allocation block size = (BLM + 1) * 128 = 2k + DB 1 ; EXM extent mask DW 179 ; DSM Disk size blocks - 1 (179d) DW 127 ; DRM Directory entries - 1 (127d) DB 11000000b ; AL0 Dir map byte 1 (2 dir blk) DB 00000000b ; AL1 Dir map byte 2 DW 32 ; CKS checksum vector size (32 sectors = 2k) - DW 0000h ; OFF (No of tracks reserved for system) + DW 0x0000 ; OFF (No of tracks reserved for system) bios_ini_vals: DB 0xaa, 0xaa, 0, 0xff, 1, 8, 6, 4, 2, 9, 7, 5, 3 @@ -754,9 +764,8 @@ bios_ini_vals: ; -------------------------------------------------- ; Disk A RAM dph_disk_a: - DW 00h ; Sector translate table pointer - DW 00h, 00h, 00h ; Scratchpad area - ; 0xda00 + DW 0 ; Sector translate table pointer + DW 0, 0, 0 ; Scratchpad area DW CPM_VARS.dir_buffer ; Directory buffer pointer DW CPM_VARS.DPB_A_RAM ; DPB Pointer DW CPM_VARS.CHK_VEC_A ; Check Vector pointer @@ -764,8 +773,8 @@ dph_disk_a: ; Disk B Floppy dph_disk_b: - DW 00h ; Sector translate table pointer - DW 00h, 00h, 00h ; Scratchpad area + DW 0 ; Sector translate table pointer + DW 0, 0, 0 ; Scratchpad area DW CPM_VARS.dir_buffer ; Directory buffer pointer DW CPM_VARS.DPB_B_RAM ; DPB Pointer DW CPM_VARS.CHK_VEC_B ; Check Vector pointer @@ -773,17 +782,16 @@ dph_disk_b: ; Disk C Floppy dph_disk_c: - DW 00h ; Sector translate table pointer - DW 00h, 00h, 00h ; Scratchpad area + DW 0 ; Sector translate table pointer + DW 0, 0, 0 ; Scratchpad area DW CPM_VARS.dir_buffer ; Directory buffer pointer DW CPM_VARS.DPB_C_RAM ; DPB Pointer DW CPM_VARS.CHK_VEC_C ; Check Vector pointer DW CPM_VARS.AL_MAP_C ; Allocation map pointer +res_data: ; offset 0xda28 + DB 1, 8, 6, 4, 2, 9, 7, 5, 3 - -res_data: ; 0xda28 - DB 1,8,6,4,2,9,7,5,3 DPB_END EQU $ DB 0x0e, 3 @@ -797,9 +805,9 @@ FILL_SIZE EQU 0x500-CODE_SIZE DISPLAY "| BIOS\t| ",/H,boot_f," | ",/H,CODE_SIZE," | ",/H,FILL_SIZE," |" + IFDEF CHECK_INTEGRITY ; Check integrity ASSERT bios_wboot = 0xd6a8 - ASSERT set_curr_dpb = 0xd722 ASSERT sel_disk = 0xd781 ASSERT home = 0xd7a7 ASSERT ram_disk_calc_addr = 0xd7eb @@ -812,6 +820,7 @@ FILL_SIZE EQU 0x500-CODE_SIZE ASSERT dpb_ram = 0xd9af ASSERT dph_disk_a = 0xd9f8 ASSERT res_data = 0xda28 + ENDIF FILLER: DS FILL_SIZE, 0xff diff --git a/CPM_v2.2_r8_bc0695e4/ccp_rom.asm b/CPM_v2.2_r8_bc0695e4/ccp_rom.asm index 75e64ad..da5f73b 100644 --- a/CPM_v2.2_r8_bc0695e4/ccp_rom.asm +++ b/CPM_v2.2_r8_bc0695e4/ccp_rom.asm @@ -267,7 +267,7 @@ ccp_dir: JP Z, .calc_remanis_ds LD HL, (BIOS.disk_c_size) - LD A, (bios_var3) + LD A, (disk_sw_trk) OR A JP NZ, .calc_remanis_ds diff --git a/CPM_v2.2_r8_bc0695e4/equates.inc b/CPM_v2.2_r8_bc0695e4/equates.inc index b1b5622..d59272c 100644 --- a/CPM_v2.2_r8_bc0695e4/equates.inc +++ b/CPM_v2.2_r8_bc0695e4/equates.inc @@ -111,6 +111,10 @@ KBD_IRQ EQU 0x02 KBD_ACK EQU 0x10 +IRQ_KEYBOARD EQU 0x02 +IRQ_PRINTER EQU 0x08 +IRQ_TIMER EQU 0x10 + KEY_ALF EQU 0x0D KEY_FIX EQU 0x15 ; ------------------------------------------------------ diff --git a/CPM_v2.2_r8_bc0695e4/ram.inc b/CPM_v2.2_r8_bc0695e4/ram.inc index 38997e0..f8f29fe 100644 --- a/CPM_v2.2_r8_bc0695e4/ram.inc +++ b/CPM_v2.2_r8_bc0695e4/ram.inc @@ -28,10 +28,11 @@ ;reserve1 EQU 0x003b @bios_var0 EQU 0x0040 ; 0xaa - bios init r8 @bios_var1 EQU 0x0041 ; 0xaa - bios init r8 -@bios_var2 EQU 0x0042 ; 0x00 - bios init r8 +@disk_sw_trk EQU 0x0042 ; 0x00 - bios init r8 @bios_var3 EQU 0x0043 ; 0xff - bios init r8 -@interleave_0 EQU 0x0044 -;reserve2 EQU 0x0050 +@interleave_0 EQU 0x0044 ; 1, 8, 6, 4, 2, 9, 7, 5, 3 [44..4C] + +;reserve2 EQU 0x0050 @fcb1 EQU 0x005c ; Default FCB, 16 bytes @fcb2 EQU 0x006c ;NMI_ISR EQU 0x0066 diff --git a/JumpingJack/.vscode/tasks.json b/JumpingJack/.vscode/tasks.json new file mode 100644 index 0000000..0e70f56 --- /dev/null +++ b/JumpingJack/.vscode/tasks.json @@ -0,0 +1,22 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "label": "make (sjasmplus)", + "type": "shell", + "command": "sjasmplus", + "args": [ + "--i8080", + "--sld=jack.sld", + "--raw=jack.obj", + "--fullpath", + "jack.asm" + ], + "problemMatcher": "$problem-matcher-sjasmplus", + "group": { + "kind": "build", + "isDefault": true + } + } + ] +} \ No newline at end of file diff --git a/JumpingJack/README.md b/JumpingJack/README.md new file mode 100644 index 0000000..e002702 --- /dev/null +++ b/JumpingJack/README.md @@ -0,0 +1,10 @@ +# Океан 240.2 +## Игра Jumping Jack + +Дизасемблирована мной и исправлена для работы под монитором версии 8. + +Исходный код для ассемблера [sjasmplus](https://github.com/z00m128/sjasmplus) в нотации Z80 (ограничен инструкциями i8080). + +Игра использует прямые обращения к переменным монитора для установки цвета и позиции курсора. +Так же использовала точку входа в монитор, которой нет в мониторе r8. Точка заменена на выход в CP/M. + diff --git a/JumpingJack/jack.asm b/JumpingJack/jack.asm new file mode 100644 index 0000000..1eebb56 --- /dev/null +++ b/JumpingJack/jack.asm @@ -0,0 +1,3650 @@ +; =================================================== +; Ocean-240.2 computer +; Jumping Jack Game +; +; Disassembled by Romych 2025-03-25 +; Patched for Monitor R8 +; =================================================== + DEVICE NOSLOT64K + SLDOPT COMMENT WPMEM, ASSERTION, LOGPOINT + + INCLUDE "ok240/equates.inc" + + OUTPUT jack.com + +; Monitor entry points +; -------------------------------------------------- +mon_con_status EQU 0xE006 +mon_con_in EQU 0xE009 + +; Monitor variables +; -------------------------------------------------- +; R8 +cursor_pos EQU 0xbfe1 +curr_color EQU 0xbfe3 + +; R5 +;cursor_pos EQU 0xbfed +;curr_color EQU 0xbfef + + +; BDOS Entries +; -------------------------------------------------- +WARM_BOOT EQU 0x0000 ; Jump warm_boot (Restart) +BDOS_ENTER EQU 0x0005 ; Jump bdos (CALL 5 to make CP/M requests) + +; BDOS Functions +C_WRITESTR EQU 9 ; Output string + +; IO Ports +; -------------------------------------------------- +SYS_DD17PB EQU 0xC1 ; Port B - [ROM14,13][REST][ENROM-][A18,17,16][32k] +VID_DD67PB EQU 0xE1 ; Port B - [VSU,C/M,FL3..1,COL3..1] +DD67PC EQU 0xE2 ; Port C - [USER3..1,STB-LP,BELL,TAPE3..1] + + +; Jumping jack constants +; -------------------------------------------------- +arr_len EQU 0x20 +stack EQU 0xbfc0 + + + ORG 0x100 +; -------------------------------------------------- +; JAMPING JACK Entry point +; -------------------------------------------------- + NOP + NOP + NOP + JP j_start + +init_levels: + LD HL, arr_len + LD DE, j_arr_src1 + LD BC, j_arr_src2 + SCF + CCF + PUSH AF +rol_32_l1: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l1 + POP AF + LD HL, arr_len + LD DE, j_arr_src10 + LD BC, j_arr_src11 + SCF + CCF + PUSH AF +rol_32_l2: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l2 + POP AF + LD HL, arr_len + LD DE, j_arr_src2 + LD BC, j_arr_src3 + SCF + CCF + PUSH AF +rol_32_l3: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l3 + POP AF + LD HL, arr_len + LD DE, j_arr_src11 + LD BC, j_arr_src12 + SCF + CCF + PUSH AF +rol_32_l4: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l4 + POP AF + LD HL, arr_len + LD DE, j_arr_src3 + LD BC, j_arr_src4 + SCF + CCF + PUSH AF +rol_32_l5: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l5 + POP AF + LD HL, arr_len + LD DE, j_arr_src12 + LD BC, j_arr_src13 + SCF + CCF + PUSH AF +rol_32_l6: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l6 + POP AF + LD HL, arr_len + LD DE, j_arr_src4 + LD BC, j_arr_src5 + SCF + CCF + PUSH AF +rol_32_l7: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l7 + POP AF + LD HL, arr_len + LD DE, j_arr_src13 + LD BC, j_arr_src14 + SCF + CCF + PUSH AF +rol_32_l8: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l8 + POP AF + LD HL, arr_len + LD DE, j_arr_src5 + LD BC, j_arr_src6 + SCF + CCF + PUSH AF +rol_32_l9: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l9 + POP AF + LD HL, arr_len + LD DE, j_arr_src14 + LD BC, j_arr_src15 + SCF + CCF + PUSH AF +rol_32_l10: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l10 + POP AF + LD HL, arr_len + LD DE, j_arr_src6 + LD BC, j_arr_src7 + SCF + CCF + PUSH AF +rol_32_l11: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l11 + POP AF + LD HL, arr_len + LD DE, j_arr_src15 + LD BC, j_arr_src16 + SCF + CCF + PUSH AF +rol_32_l12: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l12 + POP AF + LD HL, arr_len + LD DE, j_arr_src7 + LD BC, j_arr_src8 + SCF + CCF + PUSH AF +rol_32_l13: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l13 + POP AF + LD HL, arr_len + LD DE, j_arr_src16 + LD BC, j_arr_src17 + SCF + CCF + PUSH AF +rol_32_l14: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l14 + POP AF + LD HL, arr_len + LD DE, j_arr_src8 + LD BC, j_arr_src9 + SCF + CCF + PUSH AF +rol_32_l15: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l15 + POP AF + LD HL, arr_len + LD DE, j_arr_src17 + LD BC, j_arr_src18 + SCF + CCF + PUSH AF +rol_32_l16: + POP AF + LD A, (DE) + RLA + LD (BC), A + PUSH AF + INC DE + INC BC + DEC HL + LD A, L + OR H + JP NZ, rol_32_l16 + POP AF + +on_vram_acc: + LD A, 0x10 + OUT (SYS_DD17PB), A ; Turn off ROM VideoRAM @ 0xC000 + +wait_game_start: + LD HL, (random_w) ;= 0x13C6 + LD C, 16 +.i_rnd0: + LD A, H + ADD HL, HL + AND 0x60 + JP PE, .i_rnd1 + INC HL +.i_rnd1: + DEC C + JP NZ, .i_rnd0 + LD (random_w), HL ; 0x13C6 + + LD HL, (monstr_pos) ; 0x27AC + LD C, 16 + +.i_rnd_m0: + LD A, H + ADD HL, HL + AND 0x60 + JP PE, i_rnd_m1 + INC HL +i_rnd_m1: + DEC C + JP NZ, .i_rnd_m + LD (monstr_pos), HL ; 0x27AC + + NOP + XOR A + OUT (SYS_DD17PB), A ; Turn on ROM, disable VRAM + CALL mon_con_in ; undefined mon_con_in() + CP CTRL_C + JP Z, exit_to_cpm + CP ASCII_SP + JP Z, game_start_ent + CP ASCII_CR + JP Z, game_start_ent + NOP + JP wait_game_start + NOP + NOP + NOP + NOP + +game_start_ent: + LD A, 0x10 + OUT (SYS_DD17PB), A ; VideoRAM @ 0xC000 no ROM + NOP + NOP + NOP + CALL clear_screen + LD D, 0x20 + LD A, (game_line) ;= 0x20 + LD HL, first_lvl0_addr + LD (j_addr_1), HL ;= 0x133D + LD HL, first_lvl1_addr + LD (j_addr_2), HL ;= 0x13FD +LAB_ram_030b: + PUSH AF + LD HL, (random_w) ;= 0x13C6 + LD C, 0x10 +LAB_ram_0311: + LD A, H + ADD HL, HL + AND 0x60 + JP PE, LAB_ram_0319 + INC HL +LAB_ram_0319: + DEC C + JP NZ, LAB_ram_0311 + LD (random_w), HL ;= 0x13C6 + LD B, H + POP AF + CP B + JP NC, LAB_ram_043d + CALL j_fill_6_zero_1 +LAB_ram_0329: + LD B, L + CP B + JP NC, LAB_ram_0460 + CALL j_fill_6_zero_2 +LAB_ram_0331: + DEC D + JP NZ, LAB_ram_030b + LD A, 0x10 + OUT (SYS_DD17PB), A ; VideoRAM @0xC000 no ROM + CALL clear_screen + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_addr_75) ;= 0xC0D8 + LD BC, j_arr_src_00 + LD DE, lvl_plane_0 + LD A, 0x1 +LAB_ram_034b: + PUSH AF + LD A, 0x20 +j_draw_btm_line: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, j_draw_btm_line + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_034b + POP HL + POP DE + POP BC + POP AF + LD HL, 0xc0dc ;= db + LD (j_player_addr), HL ;= 0xC0C8 + + ; Lifes at start + LD A, 10 +j_draw_nxt_life: + LD (j_lifes_param), A ;= 0x1 + CALL draw_scene + LD HL, (j_player_addr) ;= 0xC0C8 + INC H + INC H + LD (j_player_addr), HL ;= 0xC0C8 + LD A, (j_lifes_param) ;= 0x1 + DEC A + JP NZ, j_draw_nxt_life + DEC H + DEC H + LD (j_last_live_addr), HL ;= 0xD2DC + LD HL, 0xc0c8 ;= db + LD (j_player_addr), HL ;= 0xC0C8 + +; -------------------------------------------------- +; Draw treashure chest +; -------------------------------------------------- + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_chest_addr) ;= 0xC400 + LD BC, j_chest_c0 ; treashure chest color bit 0 + LD DE, j_chest_c1 ; treashure chest color bit 1 + LD A, 24 +j_treasure_chest: + PUSH AF + LD A, 3 +LAB_ram_03a6: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_03a6 + LD A, H + SUB 0x3 + SUB 0x3 + LD H, A + INC L + POP AF + DEC A + JP NZ, j_treasure_chest + POP HL + POP DE + POP BC + POP AF + +draw_game_scene: + CALL draw_levl_lines + CALL draw_levl_lines + CALL handle_monster + CALL player_monstr_hit + + ; Draw "fire" if active + LD A, (is_fire) + OR A + CALL NZ, handle_fire + + PUSH BC + ; Disable VRAM access + XOR A + OUT (SYS_DD17PB), A + ; Get Console status + CALL mon_con_status + OR A ; A = 0 - not keys, 0xFF - key pressed + JP NZ, .is_key + LD A, 0xff + JP .no_key +.is_key: + ; Read Key + CALL mon_con_in +.no_key: + LD B, A ; save key + + ; VideoRAM @0xC000 + LD A, 0x10 + OUT (SYS_DD17PB), A + + LD A, B + POP BC + CP KEY_LEFT + JP Z, handle_left_key + + CP KEY_RIGHT + JP Z, handle_right_key + + CP KEY_UP + JP Z, j_key_up + + CP ASCII_SP + JP Z, handle_fire_key + + CP 'C' + JP Z, handle_color_key + + CP CTRL_C + JP Z, exit_to_cpm + NOP + +after_switch_keys: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xbe + JP Z, draw_game_scene + CP 0xfe + JP Z, draw_game_scene + CALL draw_scene + + CALL player_on_floor + JP draw_game_scene + +; -------------------------------------------------- +; Change palette [COL3:1] +; -------------------------------------------------- +handle_color_key: + LD A, (save_vmode) ;= 0x62 at start + INC A + CP 0x67 ; COL3:1 == 111b ? + JP Z, .set_col000 +.set_color_mode: + LD (save_vmode), A + OUT (VID_DD67PB), A ; [VSU, C/M, FL3:1, COL3:1] + JP after_switch_keys + +.set_col000: + LD A, 0x60 + JP .set_color_mode + +LAB_ram_043d: + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD C, 0x3 + LD HL, (j_addr_1) ;= 0x133D +LAB_ram_0446: + LD (HL), 0xff + INC HL + DEC C + JP NZ, LAB_ram_0446 + LD C, 0x3 +LAB_ram_044f: + LD (HL), 0x00 + INC HL + DEC C + JP NZ, LAB_ram_044f + LD (j_addr_1), HL ;= 0x133D + POP AF + POP BC + POP DE + POP HL + JP LAB_ram_0329 +LAB_ram_0460: + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD C, 0x3 + LD HL, (j_addr_2) ;= 0x13FD +LAB_ram_0469: + LD (HL), 0xff + INC HL + DEC C + JP NZ, LAB_ram_0469 + LD C, 0x3 +LAB_ram_0472: + LD (HL), 0x00 + INC HL + DEC C + JP NZ, LAB_ram_0472 + LD (j_addr_2), HL ;= 0x13FD + POP AF + POP BC + POP DE + POP HL + JP LAB_ram_0331 + +; -------------------------------------------------- +; Fill 6 bytes by zero +; Inp: j_addr_1 -> buffer +; -------------------------------------------------- +j_fill_6_zero_1: + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD C, 6 + LD HL, (j_addr_1) ;= 0x133D +.fill_next: + LD (HL), 0x00 + INC HL + DEC C + JP NZ, .fill_next + LD (j_addr_1), HL ;= 0x133D + POP AF + POP BC + POP DE + POP HL + RET + +; -------------------------------------------------- +; Fill 6 bytes by zero +; Inp: j_addr_2 -> buffer +; -------------------------------------------------- +j_fill_6_zero_2: + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD C, 6 + LD HL, (j_addr_2) ;= 0x13FD +.fill_next: + LD (HL), 0x00 + INC HL + DEC C + JP NZ, .fill_next + LD (j_addr_2), HL ;= 0x13FD + POP AF + POP BC + POP DE + POP HL + RET + +; -------------------------------------------------- +; Draw horisontal moved level lines +; -------------------------------------------------- +draw_levl_lines: + LD D, full_lvl_size + LD HL, last_lvl0_addr ;= 0xBF +dll_prev_hl_d: + LD A, (HL) ;= 0xBF + CP 0 + JP Z, dll_lshift_skip_0 + LD B, A + RLCA ; cf<-[7:0]<-[7] + AND 0xfe ; simple left shift + LD (HL), A + LD A, B + RLCA + AND 0x1 + INC HL + LD B, (HL) ;= 0xBF + OR B + LD (HL), A ;= 0xBF + DEC HL + DEC HL + DEC D + JP NZ, dll_prev_hl_d +dll_lshift_complete: + LD A, (last_lvl0_addr) ;= 0xBF + LD (first_lvl0_addr), A + LD D, full_lvl_size + LD HL, first_lvl1_addr +dll_rshift: + LD A, (HL) + CP 0 + JP Z, dll_rshift_skip_0 + LD B, A + RRCA ; simple shift right + AND 0x7f ; [0] -> [7:0] -> C + LD (HL), A + LD A, B + RRCA + AND 0x80 + DEC HL + LD B, (HL) ;= 0xBF + OR B + LD (HL), A ;= 0xBF + INC HL + INC HL + DEC D + JP NZ, dll_rshift +dll_rshift_complete: + LD A, (first_lvl1_addr) + LD (last_lvl1_addr), A ;= 0x3 + LD A, full_lvl_size + LD (lvl_mrg_ctr), A + LD BC, first_lvl0_addr + LD DE, lvl_merged_0 + LD HL, first_lvl1_addr +dll_merg_next: + LD A, (BC) + OR (HL) + CPL + LD (DE), A + INC BC + INC DE + INC HL + LD A, (lvl_mrg_ctr) + DEC A + LD (lvl_mrg_ctr), A + OR A + JP NZ, dll_merg_next + LD HL, 0xc018 ; draw level line + LD (j_lvl_draw_addr), HL ;= 0xC0B8 + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_0 + LD DE, lvl_plane_0 + LD A, 1 +lvl_ln0_col_nxt: + PUSH AF + LD A, 32 +lvl_ln0_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln0_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln0_col_nxt + POP HL + POP DE + POP BC + POP AF + CALL calc_nxt_line_addr + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_1 + LD DE, lvl_plane_0 + LD A, 0x1 +lvl_ln1_col_nxt: + PUSH AF + LD A, 0x20 +lvl_ln1_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln1_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln1_col_nxt + POP HL + POP DE + POP BC + POP AF + CALL calc_nxt_line_addr + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_2 + LD DE, lvl_plane_0 + LD A, 0x1 +lvl_ln2_col_nxt: + PUSH AF + LD A, 0x20 +lvl_ln2_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln2_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln2_col_nxt + POP HL + POP DE + POP BC + POP AF + CALL calc_nxt_line_addr + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_3 + LD DE, lvl_plane_0 + LD A, 0x1 +lvl_ln3_col_nxt: + PUSH AF + LD A, 0x20 +lvl_ln3_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln3_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln3_col_nxt + POP HL + POP DE + POP BC + POP AF + CALL calc_nxt_line_addr + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_4 + LD DE, lvl_plane_0 + LD A, 0x1 +lvl_ln4_col_nxt: + PUSH AF + LD A, 0x20 +lvl_ln4_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln4_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln4_col_nxt + POP HL + POP DE + POP BC + POP AF + CALL calc_nxt_line_addr + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD BC, lvl_merged_5 + LD DE, lvl_plane_0 + LD A, 1 +lvl_ln5_col_nxt: + PUSH AF + LD A, 32 +lvl_ln5_row_nxt: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, lvl_ln5_row_nxt + LD A, H + SUB 0x20 + SUB 0x20 + LD H, A + INC L + POP AF + DEC A + JP NZ, lvl_ln5_col_nxt + POP HL + POP DE + POP BC + POP AF + RET +calc_nxt_line_addr: + LD HL, (j_lvl_draw_addr) ;= 0xC0B8 + LD A, L + ADD A, 0x20 + LD L, A + LD (j_lvl_draw_addr), HL ;= 0xC0B8 + RET +dll_lshift_skip_0: + DEC HL + DEC D + JP NZ, dll_prev_hl_d + JP dll_lshift_complete +dll_rshift_skip_0: + INC HL + DEC D + JP NZ, dll_rshift + JP dll_rshift_complete + +; -------------------------------------------------- +; Handle player movement to left +; -------------------------------------------------- +handle_left_key: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD DE, j_player_tlt_c0 + LD HL, j_player_tlt_c1 + LD A, (player_turn_frame) + OR A + JP Z, LAB_ram_0688 + LD BC, 0x20 +calc_lt_fr_addr: + ADD HL, BC + EX DE, HL + ADD HL, BC + EX DE, HL + DEC A + JP NZ, calc_lt_fr_addr +LAB_ram_0688: + LD (player_frame_addr0), HL ;= 0xCFD + PUSH HL + POP BC + EX DE, HL + LD (player_frame_addr1), HL ;= 0xE1D + EX DE, HL + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, 0x10 +kl_next_col: + PUSH AF + LD A, 0x2 +kl_next_row: + PUSH AF + LD A, H + CP 0xc0 + JP C, LAB_ram_06d1 + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + LD A, H + CP 0xff + JP Z, LAB_ram_06c3 +LAB_ram_06ac: + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, kl_next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A +LAB_ram_06ba: + INC L + POP AF + DEC A + JP NZ, kl_next_col + JP LAB_ram_06d5 +LAB_ram_06c3: + POP AF +LAB_ram_06c4: + INC BC + INC DE + DEC A + JP NZ, LAB_ram_06c4 + LD A, (j_player_addr+1) + LD H, A + JP LAB_ram_06ba +LAB_ram_06d1: + INC H + JP LAB_ram_06ac +LAB_ram_06d5: + POP HL + POP DE + POP BC + POP AF + LD A, (player_turn_frame) + OR A + JP Z, LAB_ram_06f8 + DEC A +LAB_ram_06e1: + LD (player_turn_frame), A + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xbe + JP Z, draw_game_scene + CP 0xfe + JP Z, draw_game_scene + CALL player_on_floor + JP draw_game_scene +LAB_ram_06f8: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xca + JP Z, l_key_ca +LAB_ram_0701: + CP 0xbe + JP Z, l_key_be + DEC H + DEC H + LD (j_player_addr), HL ;= 0xC0C8 +LAB_ram_070b: + LD A, 0x3 + JP LAB_ram_06e1 +l_key_be: + LD H, 0xfe + LD (j_player_addr), HL ;= 0xC0C8 + JP LAB_ram_070b + +; -------------------------------------------------- +; Handle player movement to right +; -------------------------------------------------- +handle_right_key: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD DE, j_player_trt_c0 + LD HL, j_player_trt_c1 + LD A, (player_turn_frame) + OR A + JP Z, LAB_ram_0734 + LD BC, 0x20 +calc_rt_fr_addr: + ADD HL, BC + EX DE, HL + ADD HL, BC + EX DE, HL + DEC A + JP NZ, calc_rt_fr_addr + +LAB_ram_0734: + LD (player_frame_addr0), HL ;= 0xCFD + PUSH HL + POP BC + EX DE, HL + LD (player_frame_addr1), HL ;= 0xE1D + EX DE, HL + LD HL, (j_player_addr) ;= 0xC0C8 + + LD A, 16 +kr_next_col: + PUSH AF + LD A, 2 +kr_next_row: + PUSH AF + LD A, H + CP 0xc0 + JP C, kr_coll_left + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + LD A, H + CP 0xff + JP Z, kr_coll_right + +kr_cont_left: + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, kr_next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A +kr_cont_right: + INC L + POP AF + DEC A + JP NZ, kr_next_col + JP LAB_ram_0781 + +kr_coll_right: + POP AF +LAB_ram_0770: + INC BC + INC DE + DEC A + JP NZ, LAB_ram_0770 + LD A, (j_player_addr+1) + LD H, A + JP kr_cont_right + +kr_coll_left: + INC H + JP kr_cont_left + +LAB_ram_0781: + POP HL + POP DE + POP BC + POP AF + CALL player_monstr_hit + LD A, (player_turn_frame) + CP 3 + JP Z, kr_last_frame + ; next frame + INC A +LAB_ram_0791: + LD (player_turn_frame), A + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xfe + JP Z, draw_game_scene + CP 0xbe + JP Z, draw_game_scene + CALL player_on_floor + JP draw_game_scene +kr_last_frame: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xc0 + JP Z, LAB_ram_0a4e +LAB_ram_07b1: + CP 0xfe + JP Z, LAB_ram_07c2 + INC H + INC H + LD (j_player_addr), HL ;= 0xC0C8 + CALL player_monstr_hit + +LAB_ram_07be: + XOR A + JP LAB_ram_0791 + +LAB_ram_07c2: + LD H, 0xbe + LD (j_player_addr), HL ;= 0xC0C8 + JP LAB_ram_07be + + +; -------------------------------------------------- +; Handle player movement jump up +; -------------------------------------------------- +j_key_up: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, L + CP 8 + JP Z, draw_game_scene + CALL erase_player + LD HL, (j_player_addr) ; Move player coord Up + LD A, L + SUB 15 ; y-=15 + LD L, A + LD (j_player_addr), HL + CALL draw_scene + +; -------------------------------------------------- +; Play Jump Sound +; -------------------------------------------------- + PUSH BC + LD BC, 50 +j_bell: + LD A, 0xf + OUT (DD67PC), A ;[USER3..1, STB-LP, BELL, TAPE3..1] + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 10 +j_buzz_delay1: + DEC DE + LD A, D + OR E + JP NZ, j_buzz_delay1 + POP AF + POP BC + POP DE + POP HL + LD A, 0 + OUT (DD67PC), A ;[USER3..1, STB-LP, BELL, TAPE3..1] + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 10 +j_buzz_delay2: + DEC DE + LD A, D + OR E + JP NZ, j_buzz_delay2 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, j_bell + POP BC + LD HL, (j_player_addr) ;= 0xC0C8 + DEC L + LD A, (player_turn_frame) + CP 2 + JP NC, jmp_next_frame + + ; Check collision +LAB_ram_0824: + LD A, (HL) ;= db + OR A + JP NZ, jump_collision + DEC L + INC H + LD A, (HL) ;= db + OR A + JP NZ, jump_collision + CALL erase_player + ; no collision, move player up 32px (17+15) + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, L + SUB 17 + LD L, A + LD (j_player_addr), HL ;= 0xC0C8 + CALL draw_scene + JP draw_game_scene + +jump_collision: + CALL erase_player + ; move player back down + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, L + ADD A, 15 + LD L, A + LD (j_player_addr), HL ;= 0xC0C8 + CALL draw_scene + CALL draw_death + CALL player_on_floor + JP draw_game_scene + +; -------------------------------------------------- +; Player on floor? +; -------------------------------------------------- +player_on_floor: + ; calc player floor addr + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, L + ADD A, 16 + LD L, A + ; hl - floor + LD A, (player_turn_frame) + CP 2 + JP NC, .floor_at_rt ; animation death +.chk_floor: + LD A, (HL) + OR A + JP Z, no_floor + RET + +.floor_at_rt: + INC H + INC H + JP .chk_floor + +; -------------------------------------------------- +; No floor under foots, fall down +; -------------------------------------------------- +no_floor: + ; move player down + CALL erase_player + LD HL, (j_player_addr) + LD A, L + ADD A, 16 + LD L, A + LD (j_player_addr), HL + ; redraw player + CALL draw_scene + ; and recheck floor again + LD HL, (j_player_addr) + LD A, L + ADD A, 16 + LD L, A + LD A, (HL) ;= db + OR A + JP Z, no_floor + +draw_death: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_player_addr) ;= 0xC0C8 + LD BC, j_play_death_c0 + LD DE, j_play_death_c1 + LD A, 16 +dd_next_col: + PUSH AF + LD A, 2 +dd_next_row: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, dd_next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, dd_next_col + POP HL + POP DE + POP BC + POP AF + PUSH BC + ; make death sound + LD BC, 0x32 +dp_nxt_beep: + LD A, 0xf + OUT (DD67PC), A ; Bell+Tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 10 +dp_dly_nxt1: + DEC DE + LD A, D + OR E + JP NZ, dp_dly_nxt1 + POP AF + POP BC + POP DE + POP HL + LD A, 0 + OUT (DD67PC), A ; Bell+Tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 10 +dp_dly_nxt2: + DEC DE + LD A, D + OR E + JP NZ, dp_dly_nxt2 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, dp_nxt_beep + POP BC + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, L + CP 0xc8 + JP Z, draw_grave_cross + +check_floor_down: + LD A, 16 +pl_next_frame: + LD (skip_frames), A + CALL draw_levl_lines + CALL draw_levl_lines + CALL handle_monster + CALL player_monstr_hit + + LD A, (is_fire) + OR A + CALL NZ, handle_fire + + LD HL, (j_player_addr) + LD A, L + ADD A, 16 + LD L, A + LD A, (HL) ;= db + OR A + JP Z, no_floor + LD A, (skip_frames) ;= 0x1 + DEC A + JP NZ, pl_next_frame + RET + +; -------------------------------------------------- +; Draw level and monster +; -------------------------------------------------- +draw_scene: + LD A, (player_turn_frame) + LD B, A + ADD A, B + LD (player_tf2), A + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD DE, j_arr_src10 + LD HL, j_arr_src1 + LD A, (player_tf2) + OR A + JP Z, jd_frame_0 + LD BC, 0x20 +LAB_ram_0948: + ADD HL, BC + EX DE, HL + ADD HL, BC + EX DE, HL + DEC A + JP NZ, LAB_ram_0948 +jd_frame_0: + LD (player_frame_addr0), HL ;= 0xCFD + PUSH HL + POP BC + EX DE, HL + LD (player_frame_addr1), HL ;= 0xE1D + EX DE, HL + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, 16 +j_draw_pl_nxt_col: + PUSH AF + LD A, 2 +j_draw_pl_nxt_row: + PUSH AF + LD A, H + CP 0xc0 + JP C, LAB_ram_0999 + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + LD A, H + CP 0xff + JP Z, LAB_ram_098b +LAB_ram_0974: + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, j_draw_pl_nxt_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A +LAB_ram_0982: + INC L + POP AF + DEC A + JP NZ, j_draw_pl_nxt_col + JP LAB_ram_099d +LAB_ram_098b: + POP AF +LAB_ram_098c: + INC BC + INC DE + DEC A + JP NZ, LAB_ram_098c + LD A, (j_player_addr+1) + LD H, A + JP LAB_ram_0982 +LAB_ram_0999: + INC H + JP LAB_ram_0974 +LAB_ram_099d: + POP HL + POP DE + POP BC + POP AF + CALL draw_levl_lines + CALL draw_levl_lines + CALL handle_monster + CALL player_monstr_hit + LD A, (is_fire) + OR A + CALL NZ, handle_fire + RET +jmp_next_frame: + INC H + INC H + JP LAB_ram_0824 + +; -------------------------------------------------- +; Erase player from scene +; -------------------------------------------------- +erase_player: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_player_addr) + LD BC, j_player_era_c0 + LD DE, j_player_era_c1 + LD A, 16 +.ep_next_col: + PUSH AF + LD A, 2 +.ep_next_row: + PUSH AF + LD A, (BC) + LD (HL), A ;= db + LD A, (DE) + INC H + LD (HL), A ;= db + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, .ep_next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, .ep_next_col + POP HL + POP DE + POP BC + POP AF + RET + +draw_grave_cross: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_last_live_addr) ;= 0xD2DC + LD BC, j_gravecross_c0 + LD DE, j_gravecross_c1 + LD A, 16 +dgc_next_col: + PUSH AF + LD A, 1 +dgc_next_row: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, dgc_next_row + LD A, H + SUB 0x1 + SUB 0x1 + LD H, A + INC L + POP AF + DEC A + JP NZ, dgc_next_col + POP HL + POP DE + POP BC + POP AF + LD HL, (j_last_live_addr) ;= 0xD2DC + LD A, H + CP 0xc0 + JP Z, is_lost_life + DEC H + DEC H + LD (j_last_live_addr), HL ;= 0xD2DC + JP check_floor_down + +is_lost_life: + CALL out_game_over + +f_init_game: + LD A, 1 + LD (j_monster_off), A + XOR A + LD (player_turn_frame), A + LD (is_fire), A + LD HL, 0xc0c8 ;= db + LD (j_player_addr), HL ;= 0xC0C8 + JP on_vram_acc + +l_key_ca: + LD A, L + CP 0x8 + JP Z, LAB_ram_0a58 + LD A, H + JP LAB_ram_0701 +LAB_ram_0a4e: + LD A, L + CP 0x8 + JP Z, LAB_ram_0a58 + LD A, H + JP LAB_ram_07b1 +LAB_ram_0a58: + PUSH BC + LD BC, 250 +j_bell1: + LD A, 0xf + OUT (DD67PC), A ; Bell+Tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0x14 +j_bell1_delay1: + DEC DE + LD A, D + OR E + JP NZ, j_bell1_delay1 + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A ; Bell+Tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0x14 +j_bell1_delay2: + DEC DE + LD A, D + OR E + JP NZ, j_bell1_delay2 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, j_bell1 + POP BC + + LD A, (game_line) ;= 0x20 + CP 80 + JP Z, final_sound + + CALL draw_happy_end + CALL clear_screen + + LD A, 0 + OUT (SYS_DD17PB), A ; vram off, rom on + + ; Out message, Wait for key + LD HL, (curr_color) + PUSH HL + LD A, 0 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x0870 + LD (cursor_pos), HL + LD DE, j_msg_pres_key ;= '\r' + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + ; Repeat again !!! + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x870 + LD (cursor_pos), HL + LD DE, j_msg_pres_key ;= '\r' + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + LD (curr_color), HL + LD A, 0x10 + OUT (SYS_DD17PB), A ; vram @ c000 + + ; Init to default values + XOR A + LD (player_turn_frame), A + LD A, (monstr_per) ;= 0x15 + ADD A, 5 + LD (monstr_per), A ;= 0x15 + + LD A, 1 + LD (j_monster_off), A + LD A, (game_line) ;= 0x20 + ADD A, 0x10 + LD (game_line), A ;= 0x20 + JP on_vram_acc + +; -------------------------------------------------- +; Play final sound for winner +; -------------------------------------------------- +final_sound: + PUSH BC + LD BC, 250 + +.fm_next_note: + LD A, 0xf + OUT (DD67PC), A ; "1" bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + + LD DE, 40 +.fm_delay1: + DEC DE + LD A, D + OR E + JP NZ, .fm_delay1 + + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A ; "0" bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + + LD DE, 40 +.fm_delay2: + DEC DE + LD A, D + OR E + JP NZ, .fm_delay2 + + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, .fm_next_note + POP BC + +; -------------------------------------------------- +; Display final message for winner +; -------------------------------------------------- +final_messages: + + CALL clear_screen + ; close VRAM access + LD A, 0x00 + OUT (SYS_DD17PB), A + + ; End Message 1 + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x80 + LD (cursor_pos), HL + LD DE, j_msg_fin1 + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + ; End Message 2 + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0xA0 + LD (cursor_pos), HL + LD DE, j_msg_fin2 + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + ; End Message 3 + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0xC0 + LD (cursor_pos), HL + LD DE, j_msg_fin3 ;= 0xda + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + ; End Message 4 + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 208 + LD (cursor_pos), HL + LD DE, j_msg_fin4 ;= 0xD0 + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + ; End Message, Wait key + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0xff + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x8e0 + LD (cursor_pos), HL + LD DE, j_msg_pres_key ;= '\r' + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + + LD (curr_color), HL + LD A, 16 + LD (game_line), A ;= 0x20 + LD A, 32 + LD (monstr_per), A ;= 0x15 + + JP f_init_game + +clear_screen: ; Make screen green + PUSH HL + PUSH BC + PUSH DE + PUSH AF + LD A, (save_vmode) ;= 0x62 + OUT (VID_DD67PB), A + LD HL, 0xc000 + LD D, 0x20 + LD A, (BYTE_ram_0cbc) + AND 0x3 + CP 0x00 + JP Z, LAB_ram_0c14 + CP 0x1 + JP Z, LAB_ram_0c1b + CP 0x2 + JP Z, LAB_ram_0c22 + LD B, 0xff + LD C, 0xff +LAB_ram_0c00: + LD E, 0xff +j_mv_nx_note: + LD (HL), B ;= db + INC H + LD (HL), C ;= db + DEC H + INC HL + DEC E + JP NZ, j_mv_nx_note + INC HL + INC H + DEC D + JP NZ, LAB_ram_0c00 + JP LAB_ram_0c29 +LAB_ram_0c14: + LD C, 0x00 + LD B, 0x00 + JP LAB_ram_0c00 +LAB_ram_0c1b: + LD B, 0x00 + LD C, 0xff + JP LAB_ram_0c00 +LAB_ram_0c22: + LD B, 0xff + LD C, 0x00 + JP LAB_ram_0c00 +LAB_ram_0c29: + POP AF + POP DE + POP BC + POP HL + RET + + include "jack_data.inc" + +; -------------------------------------------------- +; Variables +; -------------------------------------------------- + +j_addr_1: + dw first_lvl1_addr +j_addr_2: + dw lvl_merged_0 +player_frame_addr0: + dw j_arr_src1 +player_frame_addr1: + dw j_arr_src10 +j_last_live_addr: + dw 0xD2DC + +; -------------------------------------------------- +; +; Application entry point +; +; -------------------------------------------------- + +j_start: + LD A, 0x00 + OUT (SYS_DD17PB), A ; close VRAM + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x00 + LD (cursor_pos), HL + LD DE, j_set_vmode ; = 0x1B + LD C, C_WRITESTR ; 9 + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD (saved_color), HL + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x90 + LD (cursor_pos), HL + LD DE, j_msg_verion ; "ВЕРСИЯ 1.0" + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0xa0 + LD (cursor_pos), HL + LD DE, j_spaces_35 ; + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0xb0 + LD (cursor_pos), HL + LD DE, j_msg_instr1 ; Выстрел-клавиша "пробел", цвет "Ц" + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x2c0 + LD (cursor_pos), HL + LD DE, j_msg_anykey ; Нажмите любую клавишу + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD A, 0x10 + OUT (SYS_DD17PB), A + LD HL, 0xca18 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xce20 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xd220 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xd618 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xde18 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe218 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe618 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xea08 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xea18 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xee18 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xf418 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xf818 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xfc28 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xd648 + LD B, 0x5 + CALL j_draw_rv + LD HL, 0xda58 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe258 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe650 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xee50 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xee68 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xf248 + LD B, 0x6 + CALL j_draw_rv + LD HL, 0xf458 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xf658 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xf850 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xfa48 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xf868 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xfa70 + LD B, 0x1 + CALL j_draw_rv + LD HL, 0xc618 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xc630 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xd018 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd028 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd820 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xda28 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xdc20 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe418 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe428 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xf020 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xf228 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xfa18 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xfa30 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xce48 + LD B, 0x4 + CALL j_draw_rh + LD HL, 0xce68 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd070 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xde48 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xdc50 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe050 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xdc60 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xe848 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xe870 + LD B, 0x3 + CALL j_draw_rh + JP init_levels + +; -------------------------------------------------- +; Draw vertical rectangles 8x8 +; Inp: HL - pos +; B - count +; -------------------------------------------------- +j_draw_rv: + CALL j_draw_sqare + LD A, L + ADD A, 8 ; next, 8 lines down + LD L, A + DEC B + JP NZ, j_draw_rv + RET + +; -------------------------------------------------- +; Draw horisontal rectangles 8x8 +; Inp: HL - pos +; B - count +; -------------------------------------------------- +j_draw_rh: + CALL j_draw_sqare + INC H ; next, 8 column right + INC H + DEC B + JP NZ, j_draw_rh + RET + +; -------------------------------------------------- +; Draw single rectangle 8x8 +; Inp: HL - pos +; -------------------------------------------------- +j_draw_sqare: + LD (square_addr), HL + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (square_addr) + LD BC, img_square_c0 ;= 0xFF + LD DE, img_square_c1 + + LD A, 8 +.dsq_next_row: + PUSH AF + + LD A, 1 +.dsq_next_col: + PUSH AF + LD A, (BC) ;= 0xFF + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, .dsq_next_col + LD A, H + SUB 1 + SUB 1 + LD H, A + INC L + POP AF + DEC A + JP NZ, .dsq_next_row + POP HL + POP DE + POP BC + POP AF + RET + + db 0x60 + db 0x00 + +j_set_vmode: + db ASCII_ESC, '64$' ; Set mode 40x25 + +j_msg_verion: + db ASCII_ESC, '43', 9 ; Set color + db ASCII_ESC, '71' ; Set charset RUS + db "WERSIQ 1.0" + db " " + db ASCII_CR, ASCII_LF, ' ' + +j_spaces_35: + ds 35, ' ' + db '$' + +j_msg_instr1: + db ASCII_CR, ASCII_LF, ASCII_CR + db 'wystrel-klawi{a "probel",cwet - "c"$' + +j_msg_anykey: + db ASCII_CR, ASCII_LF, ASCII_LF, ASCII_LF, ASCII_LF + db 'nAVMITE L@BU@ KLAWI[U $' + db ' $' + +img_square_c0: + ds 8, 0xff + +img_square_c1: + ds 8, 0 + + ds 33, 0 + db 0x90 + db 0xc0 + +square_addr: + dw 0xEC70 + +; -------------------------------------------------- +; Move and draw monster +; -------------------------------------------------- +handle_monster: + ; draw at every 4th call + LD A, (monster_int) ; default = 4 + DEC A + LD (monster_int), A + OR A + RET NZ + ; + LD A, 4 + LD (monster_int), A ; interval=4 + ; + LD A, (j_monster_off) + OR A + JP Z, draw_monster + LD HL, (monstr_pos) ;= 0x27AC + LD C, 16 +LAB_ram_180f: + LD A, H + ADD HL, HL + AND 0x60 + JP PE, LAB_ram_1817 + INC HL +LAB_ram_1817: + DEC C + JP NZ, LAB_ram_180f + LD (monstr_pos), HL ;= 0x27AC + LD A, (monstr_per) ;= 0x15 + CP H + JP NC, monstr_reset + RET + +monstr_reset: + LD HL, 0xfe08 + LD (monstr_addr), HL ;= 0xE268 +.next: + LD HL, (monstr_addr) ;= 0xE268 + LD A, 0x20 + ADD A, L + LD L, A + LD (monstr_addr), HL ;= 0xE268 + LD A, (monstr_var1) ;= 0xCC + ADD A, 0x33 + LD (monstr_var1), A ;= 0xCC + LD B, A + LD HL, (monstr_pos) ;= 0x27AC + LD A, L + CP B + JP NC, .next + XOR A + LD (j_monster_off), A + +; -------------------------------------------------- +draw_monster: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD DE, monstr_img_c0 + LD HL, monstr_img_c1 + LD A, (monstr_rt) ;= 0x1 + OR A + JP Z, monstr_0 + LD BC, 0x60 +monstr_no_nxt: + ADD HL, BC + EX DE, HL + ADD HL, BC + EX DE, HL + DEC A + JP NZ, monstr_no_nxt +monstr_0: + LD (monstr_src0), HL ;= 0x18FB + PUSH HL + POP BC + EX DE, HL + LD (monstr_src1), HL ;= 0x19BB + EX DE, HL + LD HL, (monstr_addr) ;= 0xE268 + LD A, 16 +dm_next_col: + PUSH AF + LD A, 6 +dm_next_row: + PUSH AF + LD A, H + CP 0xc0 + JP C, dm_at_left + LD A, (BC) ;= 0xe0 + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + LD A, H + CP 0xff + JP Z, dm_at_right +dm_ret_left: + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, dm_next_row + LD A, H + SUB 6 + SUB 6 + LD H, A +dm_ret_right: + INC L + POP AF + DEC A + JP NZ, dm_next_col + JP LAB_ram_18b4 +dm_at_right: + POP AF +LAB_ram_18a3: + INC BC + INC DE + DEC A + JP NZ, LAB_ram_18a3 + LD A, (monstr_addr+1) + LD H, A + JP dm_ret_right +dm_at_left: + INC H + JP dm_ret_left +LAB_ram_18b4: + POP HL + POP DE + POP BC + POP AF + LD A, (monstr_rt) ;= 0x1 + OR A + JP Z, LAB_ram_18d2 + XOR A +LAB_ram_18c0: + LD (monstr_rt), A ;= 0x1 + LD HL, (monstr_addr) ;= 0xE268 + LD A, H + CP 0xb4 + JP Z, SUB_ram_18d7 + DEC H + DEC H + LD (monstr_addr), HL ;= 0xE268 + RET +LAB_ram_18d2: + LD A, 0x1 + JP LAB_ram_18c0 +SUB_ram_18d7: + XOR A + LD (monstr_var1), A ;= 0xCC + LD A, 0x1 + LD (j_monster_off), A + RET + +; -------------------------------------------------- +; Monster hit player? +; -------------------------------------------------- +player_monstr_hit: + LD HL, (j_player_addr) + INC H + INC H + LD B, H + LD D, L + LD HL, (monstr_addr) + LD A, H + CP B + JP Z, .chl_lo_addr + RET +.chl_lo_addr: + LD A, L + CP D + JP Z, is_lost_life + RET + +monstr_per: + db 21 + +monster_int: + db 4 + +monstr_var1: + db 204 + +monstr_rt: + db 1 + +monstr_img_c1: + ; col: 0 + db 0x00, 0xFC, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xfe + db 0xFF, 0x03, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x07 + ; col: 1 + db 0x00, 0x00, 0xf0, 0xFF, 0xFF, 0x0f, 0x00, 0x00 + db 0xf0, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xc8, 0xFF + ; col: 2 + db 0xFF, 0xFF, 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0xFF + db 0x01, 0x00, 0xEE, 0xFF, 0xFF, 0xFF, 0x03, 0x00 + ; col: 3 + db 0xf6, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x7B, 0xfe + db 0xFF, 0xFF, 0x0f, 0x00, 0x3D, 0x38, 0x00, 0xFF + ; col: 4 + db 0x0f, 0x00, 0x1E, 0x38, 0x00, 0xF8, 0x0f, 0x00 + db 0x00, 0x38, 0x00, 0xF8, 0x1D, 0x00, 0x00, 0x38 + ; col: 5 + db 0x00, 0xF8, 0x18, 0x00, 0x00, 0x38, 0x00, 0x3C + db 0xF8, 0x00, 0x00, 0x1E, 0x00, 0x3F, 0x00, 0x00 + + ; col: 6 + db 0xe0, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0xfe, 0xFF + db 0xFF, 0x30, 0x00, 0x00, 0x3F, 0xFF, 0xFF, 0x0F + ; col: 7 + db 0x00, 0x00, 0xc0, 0xFF, 0xFF, 0x3F, 0x00, 0x00 + db 0xe0, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xf0, 0xFF + ; col: 8 + db 0xFF, 0xFF, 0x01, 0x00, 0xFF, 0xFF, 0xFF, 0xFF + db 0x01, 0x00, 0x7E, 0xfe, 0xFF, 0xFF, 0x1F, 0x00 + ; col: 9 + db 0x00, 0xfe, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xfe + db 0x01, 0xFF, 0x37, 0x00, 0x00, 0xEF, 0x01, 0xFF + ; col: 10 + db 0x67, 0x00, 0x80, 0xC7, 0x01, 0xFC, 0x0f, 0x00 + db 0x80, 0xc3, 0x01, 0x38, 0x1F, 0x00, 0xc0, 0x81 + ; col: 11 + db 0x03, 0x38, 0x1C, 0x00, 0xe0, 0x81, 0x03, 0x1E + db 0x1C, 0x00, 0xf0, 0x80, 0x03, 0x0f, 0x1E, 0x00 + +monstr_img_c0: + ds 96, 0 + ds 96, 0 + +monstr_pos: + dw 0x27AC + +monstr_addr: + dw 0xE268 +monstr_src0: + dw 0x18FB +monstr_src1: + dw 0x19BB + +; -------------------------------------------------- +; Handle "Fire" key +; -------------------------------------------------- +handle_fire_key: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + CP 0xfe + JP NC, draw_game_scene + LD A, (is_fire) + OR A + JP NZ, draw_game_scene + LD A, 1 + LD (is_fire), A + PUSH AF + PUSH BC + PUSH DE + PUSH HL + + ; player fire animation + LD HL, (j_player_addr) ;= 0xC0C8 + LD BC, j_player_firer_c0 + LD DE, j_player_firer_c1 + + LD A, 16 ; 16 rows +.hf_next_col: + PUSH AF + LD A, 2 ; 2col=16px +.hl_next_row: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, .hl_next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, .hf_next_col + + POP HL + POP DE + POP BC + POP AF + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD A, 0x00 + OUT (SYS_DD17PB), A ; vram off, rom on + +; -------------------------------------------------- +; Sound for fire (10 pulses) +; -------------------------------------------------- + LD HL, 0xc100 ; 49408 + LD DE, 10 +.fire_snd_nxt: + LD A, 0xf + OUT (DD67PC), A ; "1" bell + tape + CALL delay_hl + XOR A + OUT (DD67PC), A ; "0" bell + tape + CALL delay_hl + DEC DE + LD A, E + OR D + JP NZ, .fire_snd_nxt + + LD A, 0x10 + OUT (SYS_DD17PB), A ; vram @ 0xc000 + POP AF + POP BC + POP DE + POP HL + JP fire_continue + +; -------------------------------------------------- +; Small delay +; Inp: HL->delay +; Out: HL = HL+1 +; -------------------------------------------------- +delay_hl: + LD A, (HL) +.next_hl: + DEC A + JP NZ, .next_hl + INC HL + RET + +; -------------------------------------------------- +fire_continue: + NOP + LD A, 6 + LD (j_fire_ctr), A + XOR A + LD (j_var8_7c), A + LD (j_fire_frame), A + JP draw_game_scene + +handle_fire: + ; firectr-- + LD A, (j_fire_ctr) ;= 0x6 + DEC A + LD (j_fire_ctr), A ;= 0x6 + OR A + JP Z, j_fire_complete + + LD A, (j_var8_7c) + OR A + JP Z, LAB_ram_1b71 + +draw_fire: + LD A, (j_fire_frame) + OR A + JP Z, draw_fire2 + ; draw fire + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_fire_pos) ;= 0x4F + LD BC, j_fire_c0 + LD DE, j_fire_c1 + LD A, 1 +.next_col: + PUSH AF + LD A, 2 +.next_row: + PUSH AF + LD A, (BC) ;= 0xFF + LD (HL), A ;= db + LD A, (DE) ;= 0xFF + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, .next_row + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, .next_col + POP HL + POP DE + POP BC + POP AF + XOR A + LD (j_fire_frame), A + CALL SUB_ram_1bbf + LD HL, (j_fire_pos) ;= 0x4F + LD A, 0x4 + CP 0xfc + JP Z, j_fire_complete + INC H + INC H + LD (j_fire_pos), HL ;= 0x4F + CALL player_on_floor +draw_fire_end: + CALL SUB_ram_1bbf + RET + +LAB_ram_1b71: + LD HL, (j_player_addr) ;= 0xC0C8 + LD A, H + ADD A, 0x4 + LD H, A + LD A, L + ADD A, 0x7 + LD L, A + LD (j_fire_pos), HL ;= 0x4F + LD A, 0x1 + LD (j_var8_7c), A + JP draw_fire +draw_fire2: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_fire_pos) ;= 0x4F + LD BC, j_fire2_c0 ;= 0xFF + LD DE, j_fire2_c1 ;= 0xFF + LD A, 1 +.next_col2: + PUSH AF + LD A, 2 +.next_row2: + PUSH AF + LD A, (BC) ;= 0xFF + LD (HL), A + LD A, (DE) ;= 0xFF + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, .next_row2 + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, .next_col2 + POP HL + POP DE + POP BC + POP AF + ; draw fire2 + LD A, 1 + LD (j_fire_frame), A + JP draw_fire_end +SUB_ram_1bbf: + LD HL, (j_fire_pos) ; = 0x4F + EX DE, HL + LD HL, (monstr_addr) ;= 0xE268 + LD A, H + CP D + JP Z, LAB_ram_1bcc + RET +LAB_ram_1bcc: + LD A, L + ADD A, 0x7 + CP E + JP Z, LAB_ram_1c11 + RET +j_fire_complete: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_fire_pos) ; = 0x4F + LD BC, j_player_era_c0 + LD DE, j_player_era_c1 + LD A, 0x1 +LAB_ram_1be3: + PUSH AF + LD A, 0x2 +LAB_ram_1be6: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_1be6 + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_1be3 + POP HL + POP DE + POP BC + POP AF + XOR A + LD (is_fire), A + LD (j_var8_7c), A + LD A, 0x6 + LD (j_fire_ctr), A ; = 0x6 + RET +LAB_ram_1c11: + PUSH BC + LD BC, 300 +LAB_ram_1c15: + LD A, 0xf + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0x5 +j_mini_dly_snd: + DEC DE + LD A, D + OR E + JP NZ, j_mini_dly_snd + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0x5 +LAB_ram_1c35: + DEC DE + LD A, D + OR E + JP NZ, LAB_ram_1c35 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, LAB_ram_1c15 + POP BC + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (monstr_addr) ; = 0xE268 + LD BC, BYTE_ARRAY_ram_1dc6 + LD DE, BYTE_ARRAY_ram_1e26 + LD A, 0x10 +LAB_ram_1c55: + PUSH AF + LD A, 0x6 +LAB_ram_1c58: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_1c58 + LD A, H + SUB 0x6 + SUB 0x6 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_1c55 + POP HL + POP DE + POP BC + POP AF + CALL j_fire_complete + CALL draw_levl_lines + CALL draw_levl_lines + CALL player_on_floor + PUSH BC + LD BC, 0x96 +LAB_ram_1c86: + LD A, 0xf + OUT (DD67PC), A + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0xa +LAB_ram_1c91: + DEC DE + LD A, D + OR E + JP NZ, LAB_ram_1c91 + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 0xa +LAB_ram_1ca6: + DEC DE + LD A, D + OR E + JP NZ, LAB_ram_1ca6 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, LAB_ram_1c86 + POP BC + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (monstr_addr) ; = 0xE268 + LD BC, BYTE_ARRAY_ram_1e86 + LD DE, BYTE_ARRAY_ram_1ed6 + LD A, 0x10 +LAB_ram_1cc6: + PUSH AF + LD A, 0x5 +LAB_ram_1cc9: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_1cc9 + LD A, H + SUB 0x5 + SUB 0x5 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_1cc6 + POP HL + POP DE + POP BC + POP AF + CALL draw_levl_lines + CALL draw_levl_lines + CALL player_on_floor + CALL SUB_ram_1d02 + CALL SUB_ram_1d02 + CALL SUB_ram_1d02 + CALL SUB_ram_1d02 + CALL SUB_ram_1d3d + JP SUB_ram_18d7 +SUB_ram_1d02: + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (monstr_addr) ; = 0xE268 + LD BC, j_player_era_c0 + LD DE, j_player_era_c1 + LD A, 0x10 +LAB_ram_1d11: + PUSH AF + LD A, 0x2 +LAB_ram_1d14: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_1d14 + LD A, H + SUB 0x2 + SUB 0x2 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_1d11 + POP HL + POP DE + POP BC + POP AF + LD HL, (monstr_addr) ; = 0xE268 + LD A, H + ADD A, 0x4 + LD H, A + LD (monstr_addr), HL ; = 0xE268 + RET +SUB_ram_1d3d: + LD HL, (j_last_live_addr) ; = 0xD2DC + LD A, H + CP 0xfe + RET Z + INC H + INC H + LD (j_last_live_addr), HL ; = 0xD2DC + PUSH AF + PUSH BC + PUSH DE + PUSH HL + LD HL, (j_last_live_addr) ; = 0xD2DC + LD BC, BYTE_ARRAY_ram_1f26 + LD DE, BYTE_ARRAY_ram_1f36 + LD A, 0x10 +LAB_ram_1d58: + PUSH AF + LD A, 0x1 +LAB_ram_1d5b: + PUSH AF + LD A, (BC) + LD (HL), A + LD A, (DE) + INC H + LD (HL), A ; = 0xFF + INC H + INC BC + INC DE + POP AF + DEC A + JP NZ, LAB_ram_1d5b + LD A, H + SUB 0x1 + SUB 0x1 + LD H, A + INC L + POP AF + DEC A + JP NZ, LAB_ram_1d58 + POP HL + POP DE + POP BC + POP AF + RET + +is_fire: + db 0 +j_fire_ctr: + db 0x6 +j_var8_7c: + db 0x00 +j_fire_frame: + db 0 + + ; Fire sign 1x16 pix +j_fire2_c0: + ; color plane 0 + db 0xFF, 0x00 +j_fire2_c1: + ; color plane 1 + db 0xFF, 0x00 + + ; Fire sign 1x16 pix +j_fire_c0: + ; color plane 0 + db 0x00, 0xFF +j_fire_c1: + ; color plane 1 + db 0x00, 0xFF + + ; Player fire r 16x16pix + ; color plane 0 +j_player_firer_c0: + ; Col: 0 + db 0xc0, 0x01, 0xe0, 0x03, 0xD0, 0x06, 0x90, 0x0C + db 0xa0, 0x03, 0xc0, 0x03, 0x80, 0x01, 0x80, 0x0f + ; Col: 1 + db 0x80, 0x07, 0x80, 0x03, 0x00, 0x01, 0x00, 0x01 + db 0x00, 0x01, 0x00, 0x01, 0x00, 0x01, 0x00, 0x03 + ; color plane 1 +j_player_firer_c1: + ; Col: 0 + db 0xc0, 0x01, 0xe0, 0x03, 0xD0, 0x06, 0x90, 0x0C + db 0xa0, 0x03, 0xc0, 0x03, 0x80, 0x01, 0x80, 0x0f + ; Col: 1 + db 0x80, 0x07, 0x80, 0x03, 0x00, 0x01, 0x00, 0x01 + db 0x00, 0x01, 0x00, 0x01, 0x00, 0x01, 0x00, 0x03 + +BYTE_ARRAY_ram_1dc6: + ds 32, 0 + ds 32, 0 + ds 32, 0 +BYTE_ARRAY_ram_1e26: + ; DS 32 + db 0x00, 0x6C, 0xEF, 0x00, 0x00, 0x00, 0x00, 0x6D + db 0x0C, 0x00, 0x00, 0x00, 0x60, 0x01, 0x6C, 0x1B + db 0x00, 0x00, 0x6C, 0xB0, 0x61, 0x1B, 0x00, 0x00 + db 0x00, 0x86, 0x0d, 0x00, 0x00, 0x00, 0xda, 0x26 + ; DS 32 + db 0x6C, 0x6B, 0x00, 0x00, 0x1A, 0xa0, 0x01, 0x6B + db 0x03, 0x00, 0xc0, 0x2C, 0x6C, 0x00, 0x03, 0x00 + db 0xD9, 0x80, 0x81, 0x5B, 0x03, 0x00, 0x00, 0x3A + db 0x0C, 0x58, 0x00, 0x00, 0x00, 0x02, 0x00, 0x40 + ; DS 32 + db 0x0b, 0x00, 0x00, 0x0C, 0x00, 0x3C, 0x08, 0x00 + db 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x0C + db 0x00, 0x0e, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00 + db 0x00, 0x00, 0x00, 0x0e, 0x00, 0xf0, 0x00, 0x00 + +BYTE_ARRAY_ram_1e86: + ; DS 32 + db 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06 + db 0x00, 0x00, 0x00, 0x43, 0xc0, 0x00, 0x00, 0x00 + db 0x10, 0xc1, 0x16, 0x00, 0x30, 0x10, 0x0d, 0x10 + db 0x00, 0x30, 0x43, 0x6C, 0x00, 0x00, 0x00, 0x10 + ; DS 32 + db 0x60, 0x06, 0x00, 0x00, 0x11, 0x08, 0x36, 0x00 + db 0x00, 0xc1, 0x0C, 0x20, 0x00, 0x00, 0x00, 0x00 + db 0x00, 0x00, 0x00, 0x20, 0x06, 0x04, 0x00, 0x00 + db 0x0C, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00 + + ds 16, 0 + +BYTE_ARRAY_ram_1ed6: + ds 16, 0 + ds 32, 0 + ds 32, 0 + +BYTE_ARRAY_ram_1f26: + ;db[16] + db 0x18, 0x3C, 0x42, 0x66, 0x5A, 0x3C, 0x18, 0x3C + db 0x5A, 0xA5, 0x24, 0x24, 0x42, 0x42, 0x42, 0xc3 +BYTE_ARRAY_ram_1f36: + ;db[16] + db 0x18, 0x3C, 0x42, 0x66, 0x5A, 0x3C, 0x18, 0x3C + db 0x5A, 0xA5, 0x24, 0x24, 0x42, 0x42, 0x42, 0xc3 + +j_fire_pos: + dw 0xE44F + +; -------------------------------------------------- +; Draw Big Jumping Jack and play sound +; -------------------------------------------------- +draw_happy_end: + CALL clear_screen + LD HL, 0xde70 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xdc78 + LD B, 0x4 + CALL j_draw_rh + LD HL, 0xda80 + LD B, 0x6 + CALL j_draw_rh + LD HL, 0xde88 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xda88 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xe488 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xdc98 + LD B, 0x4 + CALL j_draw_rh + LD HL, 0xdea0 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe0a0 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xdca8 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe2a8 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xdab0 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe4b0 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd8b8 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe6b8 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd6c0 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe8c0 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xdcc0 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xe2c0 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xdad8 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xe4d8 + LD B, 0x3 + CALL j_draw_rv + LD HL, 0xd8e8 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe6e8 + LD B, 0x1 + CALL j_draw_rh + PUSH BC + LD BC, 0x64 +j_nxt_snd_per: + LD A, 0xf + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 150 +j_mini_dly_snd2: + DEC DE + LD A, D + OR E + JP NZ, j_mini_dly_snd2 + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 150 +j_mini_dly_snd3: + DEC DE + LD A, D + OR E + JP NZ, j_mini_dly_snd3 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, j_nxt_snd_per + POP BC + CALL clear_screen + LD HL, 0xde38 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xdc40 + LD B, 0x4 + CALL j_draw_rh + LD HL, 0xda48 + LD B, 0x6 + CALL j_draw_rh + LD HL, 0xde50 + LD B, 0x2 + CALL j_draw_rh + LD HL, 0xda50 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xe450 + LD B, 0x2 + CALL j_draw_rv + LD HL, 0xdc60 + LD B, 0x4 + CALL j_draw_rh + LD HL, 0xd460 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xea60 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd668 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe868 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd870 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xe270 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xde68 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xe068 + LD B, 0x4 + CALL j_draw_rv + LD HL, 0xd888 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xe288 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xd690 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xe890 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd498 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xea98 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd098 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xee98 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xd2a0 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xeca0 + LD B, 0x1 + CALL j_draw_rh + PUSH BC + LD BC, 150 +j_nxt_snd_per1: + LD A, 0xf + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 100 +j_mini_dly_snd4: + DEC DE + LD A, D + OR E + JP NZ, j_mini_dly_snd4 + POP AF + POP BC + POP DE + POP HL + LD A, 0x00 + OUT (DD67PC), A ; bell + tape + PUSH HL + PUSH DE + PUSH BC + PUSH AF + LD DE, 100 +j_mini_dly_snd5: + DEC DE + LD A, D + OR E + JP NZ, j_mini_dly_snd5 + POP AF + POP BC + POP DE + POP HL + DEC BC + LD A, C + OR B + JP NZ, j_nxt_snd_per1 + POP BC + LD A, (j_snd_21ee) ;= 0x3 + DEC A + LD (j_snd_21ee), A ;= 0x3 + OR A + JP NZ, draw_happy_end + LD A, 3 + LD (j_snd_21ee), A ;= 0x3 + RET + +; -------------------------------------------------- +; Out big grave cross +; and messages +; -------------------------------------------------- +out_game_over: + CALL clear_screen + LD HL, 0xe038 + LD B, 0x9 + CALL j_draw_rv + LD HL, 0xdc48 + LD B, 0x5 + CALL j_draw_rh + LD HL, 0xe258 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xde60 + LD B, 0x1 + CALL j_draw_rh + LD HL, 0xde80 + LD B, 0x3 + CALL j_draw_rh + LD HL, 0xdc88 + LD B, 0x5 + CALL j_draw_rh + LD HL, 0xda90 + LD B, 0x7 + CALL j_draw_rh + LD A, 0x00 + OUT (SYS_DD17PB), A + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0xaa8 + LD (cursor_pos), HL + LD DE, j_msg_game_over1 + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x2b8 + LD (cursor_pos), HL + LD DE, j_msg_game_over2 ;= 0x0d + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + LD HL, (curr_color) + PUSH HL + LD A, 0x00 + LD L, A + CPL + LD H, A + LD (curr_color), HL + LD HL, 0x2c8 + LD (cursor_pos), HL + LD DE, j_msg_game_over3 ;= 0x20 + LD C, C_WRITESTR + CALL BDOS_ENTER + POP HL + LD (curr_color), HL + +j_wait_for_key: + CALL mon_con_status + OR A + JP Z, j_wait_for_key + LD A, 0x10 + OUT (SYS_DD17PB), A ; vram @ 0xc000 + RET + +j_snd_21ee: + db 3 + +j_msg_game_over1: + db 0x20, 0x0C, 0x09, 0xE4, 0xEF, 0xf0, 0xF2, 0xF9 + db 0xE7, 0xe1, 0xEC, 0xF3, 0xF1, '$' + +j_msg_game_over2: + db 0x0d, 0x0A, 0x20, 0xe5, 0xF3, 0xEC, 0xe9, 0xa0 + db 0xE8, 0xEF, 0xF4, 0xe9, 0xF4, 0xe5, 0xa0, 0xe5 + db 0xFD, 0xe5, 0x2C, 0xEE, 0xe1, 0xf6, 0xED, 0xe9 + db 0xF4, 0xe5, 0xa0, 0xEC, 0xe0, 0xE2, 0xF5, 0xe0 + db '$' + +j_msg_game_over3: + db 0x20, 0xeb, 0xEC, 0xe1, 0xF7, 0xe9, 0xFB, 0xF5 + db 0x0D, 0x0A, 0x22, 0xF3, 0xE2, 0xF2, 0xEF, 0xF3 + db 0x22, 0x2D, 0xC4, 0xCC, 0xd1, 0xa0, 0xd7, 0xD9 + db 0xc8, 0xcf, 0xC4, 0xc1, '$' + + db 0x00, 0x00, 0x00, 0x00, 0x00 + +; -------------------------------------------------- +; +; -------------------------------------------------- +exit_to_cpm: + LD A, 0 + OUT (SYS_DD17PB), A ; ROM on, Vram off + + LD HL,(saved_color) + LD (curr_color), HL + + LD DE, reset_vmode + LD C, C_WRITESTR + CALL BDOS_ENTER + + JP WARM_BOOT ; return CP/M + +saved_color: + dw 0 + +reset_vmode: + db ASCII_ESC, "70" ; Set LAT Charset + db ASCII_ESC, "60" ; Set mode 40x25 with cursor + db ASCII_US, ASCII_FF, "$" ; Clear screen, home cursor + +j_fill_11: + ds 690, 0 +j_end_of_file: + ; garbage cleaned diff --git a/JumpingJack/ok240/equates.inc b/JumpingJack/ok240/equates.inc new file mode 100644 index 0000000..77ed772 --- /dev/null +++ b/JumpingJack/ok240/equates.inc @@ -0,0 +1,111 @@ +; ====================================================== +; Ocean-240.2 +; Equates for all assembly sources +; +; By Romych 2026-03-10 +; ====================================================== + + IFNDEF _EQUATES + DEFINE _EQUATES + +ASCII_BELL EQU 0x07 ; Make Beep +ASCII_BS EQU 0x08 ; Move cursor left (Back Space) +ASCII_TAB EQU 0x09 ; Move cursor right +8 pos +ASCII_LF EQU 0x0A ; Move cursor down (Line Feed) +ASCII_FF EQU 0x0C ; Move cursor to home (Form Feed) +ASCII_CR EQU 0x0D ; Move gursor to 1st pos (Cariage Return) +ASCII_CAN EQU 0x18 ; Move cursor right +ASCII_EM EQU 0x19 ; Move cursor up +ASCII_SUB EQU 0x1A ; CTRL-Z - end of text file marker +ASCII_ESC EQU 0x1B ; +ASCII_US EQU 0x1F ; Clear screen +ASCII_SP EQU 0x20 +ASCII_DEL EQU 0x7F + + + +; ------------------------------------------------------ +BELL_PIN EQU 0x08 ; DD67 Pin PC3 - "BELL" +; ------------------------------------------------------ +CTRL_A EQU 0x01 +CTRL_B EQU 0x02 +CTRL_C EQU 0x03 ; Warm boot +CTRL_D EQU 0x04 +CTRL_E EQU 0x05 ; Move to beginning of new line (Physical EOL) +CTRL_F EQU 0x06 +CTRL_G EQU 0x07 +CTRL_H EQU 0x08 ; Backspace +CTRL_I EQU 0x09 +CTRL_J EQU 0x0A ; LF - Line Feed +CTRL_K EQU 0x0B +CTRL_L EQU 0x0C +CTRL_M EQU 0x0D ; CR - Carriage Return +CTRL_N EQU 0x0E +CTRL_O EQU 0x0F +CTRL_P EQU 0x10 ; turn on/off printer +CTRL_Q EQU 0x11 +CTRL_R EQU 0x12 ; Repeat current cmd line +CTRL_S EQU 0x13 ; Temporary stop display data to console (aka DC3) +CTRL_T EQU 0x14 +CTRL_U EQU 0x15 ; Cancel (erase) current cmd line +CTRL_V EQU 0x16 +CTRL_W EQU 0x17 +CTRL_X EQU 0x18 ; Cancel (erase) current cmd line +CTRL_Y EQU 0x19 +CTRL_Z EQU 0x1A ; CTRL-Z - end of text file marker + +; ------------------------------------------------------ +TRUE EQU 0xFF +FALSE EQU 0x00 + +; --------------------------------------------------- +; FCB Offsets +; --------------------------------------------------- +FCB_LEN EQU 32 ; length of FCB +FCB_SHF EQU 5 +FN_LEN EQU 12 ; Length of filename in FCB +FCB_DR EQU 0 ; Drive. 0 for default, 1-16 for A-P +FCB_FN EQU 1 ; Fn - Filename, 7-bit ASCII. The top bits - attributes +FCB_FT EQU 9 ; Filetype, 7-bit ASCII. + ; T1' to T3' have the following + ; T1' - Read-Only + ; T2' - System (hidden) + ; T3' - Archive +FCB_EXT EQU 12 ; EX - Set this to 0 when opening a file and then leave it to + ; CP/M. You can rewind a file by setting EX, RC, S2 and CR to 0. +FCB_S1 EQU 13 ; S1 - Reserved. +FCB_S2 EQU 14 ; S2 - Reserved. Bit 7 - wile write flag, [6:0] module number (Extent hi bits) +FCB_RC EQU 15 ; RC - Set this to 0 when opening a file and then leave it to CP/M. +FCB_AL EQU 16 ; AL - Image of the second half of the directory entry, + ; containing the file's allocation (which disc blocks it owns). +FCB_CR EQU 32 ; CR - Current record within extent. It is usually best to set + ; this to 0 immediately after a file has been opened and + ; then ignore it. +FCB_RN EQU 33 ; Rn - Random access record number. A 16-bit (with R2 used for overflow) + + +; ------------------------------------------------------ +IRQ_0 EQU 0x01 +IRQ_1 EQU 0x02 +IRQ_2 EQU 0x04 + +IRQ_KEYBOARD EQU 0x02 +IRQ_PRINTER EQU 0x08 +IRQ_TIMER EQU 0x10 + +KBD_ACK EQU 0x80 +PRINTER_ACK EQU 0x10 + + +KEY_LEFT EQU 0x93 +KEY_RIGHT EQU 0x84 +KEY_UP EQU 0x85 + +TX_READY EQU 0x01 +RX_READY EQU 0x02 + +TMR0_SQWAVE EQU 0x36 + +; ------------------------------------------------------ + + ENDIF \ No newline at end of file diff --git a/MON_Turbo/turbo_mon.asm b/MON_Turbo/turbo_mon.asm index fb3c343..dc24f98 100644 --- a/MON_Turbo/turbo_mon.asm +++ b/MON_Turbo/turbo_mon.asm @@ -3413,7 +3413,7 @@ m_rst1_handler: DI LD (TM_VARS.rst_hl_save), HL LD HL, 0x2 - ADD HL,SP + ADD HL, SP LD (TM_VARS.rst_sp_save), HL POP HL LD SP, TM_VARS.rst_hl_save @@ -3440,7 +3440,7 @@ m_cold_start: LD (TM_VARS.tm_hrg), HL tm_main: LD SP, TM_VARS.tm_stsp - LD DE,esc_64x23_cursor ; FORM61 + LD DE, esc_64x23_cursor ; FORM61 CALL tm_print LD DE, msg_turbo_mon ;= '\f' CALL tm_out_strz diff --git a/MON_Turbo/.vscode/extensions.json b/MON_Turbo_bcac5ca0/.vscode/extensions.json similarity index 100% rename from MON_Turbo/.vscode/extensions.json rename to MON_Turbo_bcac5ca0/.vscode/extensions.json diff --git a/MON_Turbo/.vscode/tasks.json b/MON_Turbo_bcac5ca0/.vscode/tasks.json similarity index 100% rename from MON_Turbo/.vscode/tasks.json rename to MON_Turbo_bcac5ca0/.vscode/tasks.json diff --git a/MON_Turbo/BIN/MON_Turbo_bcac5ca0.BIN b/MON_Turbo_bcac5ca0/BIN/MON_Turbo_bcac5ca0.BIN similarity index 100% rename from MON_Turbo/BIN/MON_Turbo_bcac5ca0.BIN rename to MON_Turbo_bcac5ca0/BIN/MON_Turbo_bcac5ca0.BIN diff --git a/MON_Turbo/README.md b/MON_Turbo_bcac5ca0/README.md similarity index 100% rename from MON_Turbo/README.md rename to MON_Turbo_bcac5ca0/README.md diff --git a/MON_Turbo/bios_entries.inc b/MON_Turbo_bcac5ca0/bios_entries.inc similarity index 100% rename from MON_Turbo/bios_entries.inc rename to MON_Turbo_bcac5ca0/bios_entries.inc diff --git a/MON_Turbo/equates.inc b/MON_Turbo_bcac5ca0/equates.inc similarity index 100% rename from MON_Turbo/equates.inc rename to MON_Turbo_bcac5ca0/equates.inc diff --git a/MON_Turbo/io.inc b/MON_Turbo_bcac5ca0/io.inc similarity index 100% rename from MON_Turbo/io.inc rename to MON_Turbo_bcac5ca0/io.inc diff --git a/MON_Turbo/mon_entries.inc b/MON_Turbo_bcac5ca0/mon_entries.inc similarity index 100% rename from MON_Turbo/mon_entries.inc rename to MON_Turbo_bcac5ca0/mon_entries.inc diff --git a/MON_Turbo/ram.inc b/MON_Turbo_bcac5ca0/ram.inc similarity index 100% rename from MON_Turbo/ram.inc rename to MON_Turbo_bcac5ca0/ram.inc diff --git a/MON_Turbo/tm_vars.inc b/MON_Turbo_bcac5ca0/tm_vars.inc similarity index 100% rename from MON_Turbo/tm_vars.inc rename to MON_Turbo_bcac5ca0/tm_vars.inc diff --git a/MON_Turbo_bcac5ca0/turbo_mon.asm b/MON_Turbo_bcac5ca0/turbo_mon.asm new file mode 100644 index 0000000..fb3c343 --- /dev/null +++ b/MON_Turbo_bcac5ca0/turbo_mon.asm @@ -0,0 +1,4788 @@ +; ====================================================== +; Ocean-240.2 +; Turbo monitor +; +; Disassembled by Romych 2025-09-09 +; ====================================================== + + DEVICE NOSLOT64K + + INCLUDE "io.inc" + INCLUDE "equates.inc" + INCLUDE "ram.inc" + INCLUDE "bios_entries.inc" + + OUTPUT tmon_E000.bin + + + MODULE TURBO_MONITOR + + ORG 0xe000 + +; ------------------------------------------------------ +; Monitor Entry points +; ------------------------------------------------------ + +start: JP m_init ; E000 +mon_cold_start: JP m_cold_start ; E003 +non_con_status: JP m_con_status ; E009 +mon_con_in: JP tm_con_in ; E00C +mon_con_out: JP m_con_out ; E00F +mon_serial_in: JP m_serial_in ; E012 +mon_serial_out: JP m_serial_out ; E015 +mon_char_print: JP tm_char_print ; E018 +mon_tape_read: JP m_tape_read ; E01B +mon_tape_write: JP m_tape_write ; E01E +ram_disk_read: JP m_ramdisk_read ; E021 +ram_disk_write: JP m_ramdisk_write ; E024 +mon_free_fn1: JP m_cold_start ; E027 +mon_free_fn2: JP m_cold_start ; E02A +mon_tape_wait: JP m_tape_wait ; E02D +mon_tape_detect: JP m_tape_blk_detect ; E030 +read_floppy: JP m_read_floppy ; E033 +write_floppy: JP m_write_floppy ; E036 + + +; ------------------------------------------------------ +; Init system devices +; ------------------------------------------------------ +m_init: + DI + LD SP, TM_VARS.rst_ret_JP + LD A, 10000000b ; DD17 all ports to out + OUT (SYS_DD17CTR), A ; VV55 Sys CTR + OUT (DD67CTR), A ; VV55 Video CTR + + CALL m_init_kbd_tape + LD A, 01111111b ; VSU=0, C/M=1, FL=111, COL=111 + OUT (VID_DD67PB), A ; color mode + LD A, 00000001b + OUT (SYS_DD17PB), A ; Access to VRAM + LD B, 0x0 + LD HL, 0x3f00 + LD A, H + ADD A, 65 ; A=128 0x80 + + ; Clear memory from 0x3F00 to 0x7FFF +i_fill_video: + LD (HL), B + INC HL + CP H + JP NZ, i_fill_video + XOR A + OUT (SYS_DD17PB), A ; Disable VRAM + LD A, 00000111b + OUT (SYS_DD17PC), A ; pix shift to 7 + LD (TM_VARS.m_pix_shift), A + XOR A + LD (TM_VARS.m_screen_mode), A + LD (TM_VARS.m_row_shift), A + + ; Set color mode and palette + LD (TM_VARS.m_curr_color+1), A + CPL + LD (TM_VARS.m_curr_color), A + LD A, 00000011b + LD (TM_VARS.m_cur_palette), A + ; VSU=0, C/M=1, FL=000, COL=011 + ; color mode, black border + ; 00-black, 01-red, 10-purple, 11-white + LD A, 01000011b + OUT (VID_DD67PB), A + + ; config LPT + LD A, 0x4 + OUT (DD67PC), A ; bell=1, strobe=0 + LD (TM_VARS.m_strobe_state), A ; store strobe + LD HL,1024 ; 683us + LD (TM_VARS.m_beep_period), HL + LD HL, 320 ; 213us + LD (TM_VARS.m_beep_duration), HL + + ; Config UART + LD A, 11001110b + OUT (UART_DD72RR), A + LD A, 00100101b + OUT (UART_DD72RR), A + + ; Config Timer#1 for UART clock + LD A, 01110110b ; tmr#1, load l+m bin, sq wave + OUT (TMR_DD70CTR), A + + ; 1.5M/10 = 150kHz + LD A, 10 + OUT (TMR_DD70C2), A + XOR A + OUT (TMR_DD70C2), A + + ; Config PIC + LD A,00010010b ; ICW1 edge trigger, interval 8, sin... + OUT (PIC_DD75RS), A + XOR A + OUT (PIC_DD75RM), A ; ICW2 + CPL + OUT (PIC_DD75RM), A ; ICW3 no slave + LD A,00100000b + OUT (PIC_DD75RS), A ; Non-specific EOI command, End of I... + LD A, PIC_POLL_MODE + OUT (PIC_DD75RS), A ; Poll mode, poll on next RD + + ; Init cursor + CALL m_draw_cursor + LD HL, TM_VARS.tm_stsp + LD (TM_VARS.tm_stack_0), HL ; tm_stack_0 - directly not used elsewhere + LD A, JP_OPCODE + LD (RST1), A + LD HL, m_rst1_handler + LD (RST1_handler_addr), HL + + ; Beep + LD C, ASCII_BELL + CALL m_con_out + ; check bios exists + LD A, (BIOS.boot_f) + CP JP_OPCODE + JP Z, BIOS.boot_f + LD HL, msg_hw_mon + CALL m_out_strz + JP m_cold_start + +m_out_strz: + LD C, (HL) + LD A, C + OR A + RET Z + CALL m_con_out + INC HL + JP m_out_strz + +msg_hw_mon: + DB "\r\nHARDWARE MONITOR+ V1\r\n", 0 + DS 3, 0xFF + +m_init_kbd_tape: + LD A, 10010011b + ; Configure KBD/TAPE VV55 + ; A - In, B-Out, Ch-Out, Cl-In + OUT (KBD_DD78CTR), A + LD A, PORT_C4 + OUT (KBD_DD78PC), A + XOR A + OUT (KBD_DD78PC), A + XOR A + LD (TM_VARS.m_last_key), A + RET + +; ------------------------------------------------------ +; Console status +; Out: A = 0 - not ready +; A = 0xFF - ready (key pressed) +; ------------------------------------------------------ +m_con_status: + LD A, (TM_VARS.m_last_key) + OR A + JP Z, mc_check_irq + LD A, 0xff ; ready + RET + + ; ckeck keyboard IRQ +mc_check_irq: + IN A, (PIC_DD75RS) + AND KBD_IRQ + RET Z ; no int from keyboard + + ; read keyboard data + IN A, (KBD_DD78PA) + OR A + JP NZ, mc_has_key + LD A, KBD_ACK ; ACK=1 + OUT (KBD_DD78PC), A + XOR A + OUT (KBD_DD78PC), A ; ACK=0 + XOR A + RET + +mc_has_key: + PUSH BC + LD B, A ; store row in B + IN A, (KBD_DD78PC) + AND 00001111b ; column code + LD C, A + IN A, (KBD_DD78PB) ; [JST3..1, ACK,TAPE5,TAPE4,GK,GC] + RRA + AND 00110000b ; SHIFT+CTRL + OR C + LD C, A ; C=SHIFT+CTRL+IE10 + LD A,KBD_ACK ; ACK=1 + OUT (KBD_DD78PC), A + XOR A ; ACK=0 + OUT (KBD_DD78PC), A + LD A,B ; A = key + LD B, 0xff + + ; decode key +mc_calc_column: + INC B + RRA ; >> [CF] -> 7 + JP NC,mc_calc_column + LD A, C + RLA ; 0 <- [CF] << + RLA + RLA + + ; IE10 shifted + B + AND 01111000b + OR B + INC A + CP KEY_ALF + JP NZ, mc_not_alf + LD A, 0x0 + LD (TM_VARS.mc_stored_key), A + JP mc_fin + +mc_not_alf: + CP 0xc + JP NZ,mc_chk_fix + LD A, 0xff + LD (TM_VARS.mc_stored_key), A + JP mc_fin + +mc_chk_fix: + CP KEY_FIX + JP NZ,mc_plain_key + ; invert fix state + LD A, (TM_VARS.mc_fix_state) + CPL + LD (TM_VARS.mc_fix_state), A + JP mc_fin +mc_plain_key: + LD (TM_VARS.m_last_key), A + LD A, C + AND 0x30 + LD (TM_VARS.m_last_shifts), A + POP BC + LD A, 0xff + RET +mc_fin: + POP BC + XOR A + RET + +; ------------------------------------------------------ +; Read key +; Inp: A +; ------------------------------------------------------ +tm_con_in: + CALL m_con_status + OR A + JP Z, tm_con_in + LD A, (TM_VARS.m_last_key) + PUSH HL + PUSH BC + LD B, A + LD A, (TM_VARS.m_last_shifts) + LD C, A + LD HL, mci_ctrl_tab + AND 0x10 ; Ctrl + JP NZ, mci_is_crtl + LD A, C + LD HL, mci_alt_tab + AND 0x20 ; Shift + JP NZ, mci_is_shift + LD A, (TM_VARS.mc_fix_state) + OR A + JP NZ, mci_is_shift + LD HL, mci_base_tab + ; Calc offset for key decode +mci_is_shift: + LD A, B ; last + ADD A, L + LD L, A + LD A, H + ADC A, 0x0 + LD H, A + LD C, (HL) ; C - decoded + LD A, (TM_VARS.mc_stored_key) + OR A + LD A, C ; A = decoded key + JP Z, mci_key_zero + OR 0x80 +mci_key_zero: + LD C, A + XOR A + LD (TM_VARS.m_last_key), A + ; Return A=C=key + LD A, C + POP BC + POP HL + RET +mci_is_crtl: + LD A,B + ADD A,L + LD L, A + LD A,H + ADC A, 0x0 + LD H, A + LD A, (HL) + JP mci_key_zero + +mci_base_tab equ $-1 + db ',', '-', 0x00, 0x00, 0x00, '7', '8', '9' + db 0x1B, 0x09, 0x00, 0x00, 0x00, '0', '.', "\r" + db '@', 'J', 'F', 'Q', 0x00, '1', '2', '3' + db 0x9E, '1', 'C', 'Y', '^', '4', '5', '6' + db 0x81, '2', 'U', 'W', 'S', '+', 0x7F, 0x03 + db 0x86, '3', 'K', 'A', 'M', "\b", 0x99, 0x8B + db '4', 'E', 'P', 'I', ' ', 0x84, "\r", '/' + db 0x92, '5', 'N', 'R', 'T', 0x98, 0x85, '_' + db 0x83, '6', 'G', 'O', 'X', '.', ':', '-' + db '7', '[', 'L', 'B', 0x93, 0x5C, 'H', '0' + db '8', ']', 'D', ';', ',', 'V', 'Z', '9' + +mci_alt_tab equ $-1 + db ',', '-', 0x00, 0x00, 0x00, '7', '8', '9' + db 0x1B, "\t", 0x00, 0x00, 0x00, '0', '.', "\r" + db '`', 'j', 'f', 'q', 0x00, '1', '2', '3' + db 0x9E, '!', 'c', 'y', '~', '4', '5', '6' + db 0x81, '"', 'u', 'w', 's', '+', 0x7F, 0x03 + db 0x86, '#', 'k', 'a', 'm', "\b", 0x99, 0x8B + db '$', 'e', 'p', 'i', ' ', 0x84, "\r", '?' + db 0x92, '%', 'n', 'r', 't', 0x98, 0x85, '_' + db 0x83, '&', 'g', 'o', 'x', '>', '*', '=' + db 0x27, '{', 'l', 'b', 0x93, '|', 'h', '0' + db '(', '}', 'd', '+', '<', 'v', 'z', ')' + +mci_ctrl_tab equ $-1 + db ',', '-', 0x00, 0x00, 0x00, '7', '8', '9' + db 0x1B, "\t", 0x00, 0x00, 0x00, '0', '.', "\r" + db 0x00, "\n", 0x06, 0x11, 0x00, '1', '2', '3' + db 0x9E, '1', 0x03, 0x19, 0x1E, '4', '5', '6' + db 0x81, '2', 0x15, 0x17, 0x13, '+', 0x7F, 0x03 + db 0x86, '3', "\v", 0x01, "\r", "\b", 0x99, 0x8B + db '4', 0x05, 0x10, "\t", ' ', 0x84, "\r", '/' + db 0x92, '5', 0x0E, 0x12, 0x14, 0x98, 0x85, 0x1F + db 0x83, '6', "\a", 0x0F, 0x18, '.', ':', '-' + db '7', 0x1B, "\f", 0x02, 0x93, 0x1C, "\b", '0' + db '8', 0x1D, 0x04, ';', ',', 0x16, 0x1A, '9' + +; ------------------------------------------------------ +; Out char to console +; Inp: C - char +; ------------------------------------------------------ +m_con_out: + PUSH HL + PUSH DE + PUSH BC + CALL m_con_out_int + POP BC + POP DE + POP HL + RET + +; ------------------------------------------------------ +; Out char C to console +; ------------------------------------------------------ +m_con_out_int: + LD DE, TM_VARS.m_esc_mode + LD A, (DE) + DEC A + OR A + JP M, co_print_no_esc ; standart print no ESC mode + JP NZ, co_exit_esc + + ; handle ESC param + INC DE + LD A, (DE) + OR A + JP P, co_get_esc_param + LD A, C + AND 0xf ; convert char to command code + LD (DE), A + INC DE + XOR A + LD (DE), A + RET + +co_get_esc_param: + LD HL, TM_VARS.m_esc_cmd + LD B, (HL) + ; inc param count + INC HL + LD A, (HL) + INC A + LD (HL), A + ; store new param + LD E, A + LD D, 0x0 + ADD HL, DE + LD (HL), C + ; get params count for esc command + LD HL, m_esc_params_tab + LD E, B ; d=0, b = cmd + ADD HL, DE ; DE - command offset + CP (HL) + ; return if enough + RET M + + ; Entry point for user programs + ; to use graphics with parameters in ASCII form + LD A, (TM_VARS.m_esc_cmd) + AND 0xf ; ??? already applied + CP 15 + JP Z, ge_lbl_1 + CP 11 + LD C, 0x5 + JP Z, ge_lbl_2 + CP 4 + JP P, esc_handler1 +ge_lbl_1: + LD C, 0x4 +ge_lbl_2: + LD HL, TM_VARS.m_esc_param_1 + LD D, H + LD E, L +ge_lbl_3: + + LD A, (HL) + CP 0x3a ; ':' + JP M, ge_is_digit_1 + SUB 0x7 +ge_is_digit_1: + AND 0xf + ADD A, A + ADD A, A + ADD A, A + ADD A, A + LD B, A ; B=A*16 + INC HL + LD A, (HL) + CP ':' + JP M, ge_is_digit_2 + SUB 0x7 +ge_is_digit_2: + AND 0xf + OR B + INC HL + LD (DE), A + INC DE + DEC C + JP NZ, ge_lbl_3 + +esc_handler1: + LD HL, TM_VARS.m_esc_cmd + LD A, (HL) + AND 0xf + LD E, A + DEC HL + OR A + LD (HL), 0x2 + RET Z + LD D, 0x0 + LD (HL), D + DEC DE + ; Calc ESC command handler offset + LD HL, m_esc_handler_tab + ADD HL, DE + ADD HL, DE + LD E, (HL) + INC HL + ; HL = addr of handler func + LD D, (HL) + EX DE, HL + ; It is 1..4 func DRAW_* func? + CP 0x4 + JP P, esc_no_draw_fn + LD A, (TM_VARS.m_screen_mode) + AND 00000111b + ; If not in graphics mode - exit + JP NZ, esc_exit + +esc_no_draw_fn: + LD DE, esc_exit + PUSH DE + + ; Jump to ESC func handler + JP (HL) + +esc_exit: + XOR A + LD (TM_VARS.m_esc_mode), A + RET + + ; Count of parameters for ESC commands +m_esc_params_tab: + db 4, 8, 8, 4, 1, 2, 1, 1 + db 1, 1, 1, 10, 1, 1, 1, 8 + +m_esc_handler_tab: + dw esc_draw_fill_rect ; 1 + dw esc_draw_line ; 2 + dw esc_draw_dot ; 3 + dw esc_set_color ; 4 + dw esc_set_cursor ; 5 + dw esc_set_vmode ; 6 + dw esc_set_charset ; 7 + dw esc_set_palette ; 8 + dw esc_reset_esc ; 9 + dw esc_print_screen ; : + dw esc_fn_b ; ; + dw esc_fn_none ; < + dw esc_fn_none ; = + dw esc_fn_none ; > + dw esc_set_beep ; ? +esc_fn_none: + RET + +esc_set_beep: + LD DE, TM_VARS.m_esc_param_1 + LD A, (DE) + LD H, A + INC DE + LD A, (DE) + LD L, A + LD (TM_VARS.m_beep_period), HL + INC DE + LD A, (DE) + LD H, A + INC DE + LD A, (DE) + LD L, A + LD (TM_VARS.m_beep_duration), HL + RET + +esc_reset_esc: + POP DE + XOR A + LD (TM_VARS.m_esc_mode), A + LD A, (TM_VARS.m_screen_mode) + RET + +esc_print_screen: + LD A, (TM_VARS.m_screen_mode) + AND 00000111b + RET NZ ; ret if not 0 mode + LD DE, 0x30ff + CALL m_print_hor_line + DEC E + LD D, 0xf0 + +fna_chk_keys: + CALL m_con_status + OR A + JP Z, fna_no_keys + CALL tm_con_in + CP ASCII_ESC + RET Z + +fna_no_keys: + CALL m_print_hor_line + DEC E + JP NZ, fna_chk_keys + LD D, 0xe0 + CALL m_print_hor_line + RET + +; ------------------------------------------------------ +; Print line to printer +; D - width +; ------------------------------------------------------ +m_print_hor_line: + LD HL, cmd_esc_set_X0 + + ; Set printer X coordinate = 0 + CALL m_print_cmd + LD HL, 4 + LD (TM_VARS.m_print_pos_x), HL ; Set start coord X = 4 + LD B, 0x0 + +phl_print_next_col: + LD C, 0x0 + ; 1 + CALL m_get_7vpix + AND D + CALL NZ, m_print_vert_7pix + LD HL, (TM_VARS.m_print_pos_x) + INC HL + + ; inc X + LD (TM_VARS.m_print_pos_x), HL + LD C, 0x1 + ; 2 + CALL m_get_7vpix + AND D + CALL NZ, m_print_vert_7pix + LD HL, (TM_VARS.m_print_pos_x) + INC HL + ; inc X + LD (TM_VARS.m_print_pos_x), HL + INC B + LD A, B + CP 236 + JP C, phl_print_next_col + LD HL, cmd_esc_inc_Y2 + CALL m_print_cmd + RET + +; ------------------------------------------------------ +; Send command to printer +; Inp: HL -> to command bytes array +; ------------------------------------------------------ +m_print_cmd: + PUSH BC +ps_print_nxt: + LD A, (HL) + CP ESC_CMD_END + JP Z, ps_cmd_end + LD C, A + CALL m_print_write + INC HL + JP ps_print_nxt +ps_cmd_end: + POP BC + RET + +; ------------------------------------------------------ +; Print 7 vertical pixels to printer +; Inp: A - value to print +; ------------------------------------------------------ +m_print_vert_7pix: + PUSH AF + ; Set coordinate X to 0 + LD HL, cmd_esc_set_X + CALL m_print_cmd + LD HL, (TM_VARS.m_print_pos_x) + LD C,H + CALL m_print_write + LD C,L + CALL m_print_write + ; Set column print mode + LD HL, cmd_esc_print_col + CALL m_print_cmd + POP AF + ; Print 7 vertical pixels + LD C, A + CALL m_print_write + RET + +; ------------------------------------------------------ +; Control codes for printer УВВПЧ-30-004 +; ------------------------------------------------------ +; Zn - Increment Y coordinate +cmd_esc_inc_Y2: + db ASCII_ESC + db 'Z' + db 2h + db ESC_CMD_END + +; Xnn - Set X coordinate +cmd_esc_set_X0: + db ASCII_ESC + db 'X' + db 0h ; 0..479 + db 0h + db ESC_CMD_END +; ------------------------------------------------------ +; X - Start on "Set X coordinate" command +; ------------------------------------------------------ +cmd_esc_set_X: + db ASCII_ESC + db 'X' + db ESC_CMD_END + +; O - Column print (vertical 7 bit) +cmd_esc_print_col: + db ASCII_ESC + db 'O' + db ESC_CMD_END + +; ------------------------------------------------------ +; Get 7 vertical pixels from screen +; Inp: C - sheet +; Out: A - byte +; ------------------------------------------------------ +m_get_7vpix: + LD A, (TM_VARS.m_row_shift) + ADD A, B + ADD A, 19 ; skip first 20pix + LD L, A + PUSH DE + PUSH BC + LD A, E +g7v_calc_pix_no: + AND 0x7 + LD B, A + LD A, E + ; calc hi addr + RRA ; /8 + RRA + RRA + AND 0x1f + ADD A, A ; *2 + ADD A, 64 ; bytes per row + LD H, A + ; select sheet 0|1 + LD A, C + AND 0x1 + ADD A, H + LD H, A + ; HL = pix addr, turn on VRAM access + LD A, 0x1 + OUT (SYS_DD17PB), A + LD E, (HL) ; read pixel + INC H ; HL += 512 + INC H + LD D, (HL) ; read pixel row+1 + + ; turn off VRAM access + XOR A + OUT (SYS_DD17PB), A +g7v_for_all_pix: + DEC B + JP M,g7v_all_shifted + ; shift pixels D >> [CF] >> E + LD A, D + RRA + LD D, A + LD A, E + RRA + LD E, A + JP g7v_for_all_pix +g7v_all_shifted: + LD A, E + LD D,00000000b + RRA + JP NC,g7v_not_1_1 + LD D,00110000b +g7v_not_1_1: + RRA + JP NC,g7v_not_1_2 + LD A, D + OR 11000000b + LD D, A +g7v_not_1_2: + LD A, D + POP BC + POP DE + RET + +esc_set_palette: + LD A, (TM_VARS.m_esc_param_1) + AND 00111111b ; bgcol[2,1,0],pal[2,1,0] + LD (TM_VARS.m_cur_palette), A + LD B, A + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + LD A, 0x0 + JP NZ,esp_no_colr + LD A, 0x40 + +esp_no_colr: + OR B + OUT (VID_DD67PB), A + RET + +esc_set_charset: + LD A, (TM_VARS.m_esc_param_1) + AND 0x3 ; charset 0..3 + LD (TM_VARS.m_codepage), A + RET + +; ------------------------------------------------------ +; Get address for draw symbol glyph +; ------------------------------------------------------ +m_get_glyph: + LD L, A + LD E, A + XOR A + LD D, A + LD H, A + ; HL = DE = A + ADD HL, HL + ADD HL, DE + ADD HL, HL + ADD HL, DE + ; HL = A * 7 + LD A, E ; A = A at proc entry + CP '@' + ; First 64 symbols is same for all codepages + JP M, m_cp_common + LD A, (TM_VARS.m_codepage) + OR A + ; cp=0 - Latin letters + JP Z, m_cp_common + DEC A + ; cp=1 - Russian letters + JP Z, m_cp_russ + ; cp=2 - 0x40..0x5F - displayed as Lat + ; 0x60 - 0x7F - displayed as Rus + LD A, E + CP 0x60 + JP M, m_cp_common +m_cp_russ: + LD DE, 448 ; +448=64*7 Offset for cp1 + ADD HL, DE + +m_cp_common: + LD DE, m_font_cp0-224 ; m_font_cp0-224 + ADD HL, DE ; add symbol glyph offset + RET + +; ------------------------------------------------------ +; Console output +; ------------------------------------------------------ +co_print_no_esc: + LD A, C + AND 0x7f + CP ' ' + JP M, m_print_control_char + CALL m_get_glyph + ; Calc screen address to DE + EX DE, HL + LD HL, (TM_VARS.m_cursor_row) + LD A, (TM_VARS.m_row_shift) + ADD A, L + LD L, A + LD A, H + ADD A, 64 + LD H, A + LD C, 7 + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + JP NZ, co_m_no_color + ; Access to video RAM + LD A, 0x1 + OUT (SYS_DD17PB), A + EX DE, HL + ; draw to both planes + XOR A + LD (DE), A + INC D + LD (DE), A + DEC D + INC E +co_m_colorify: + LD A, (TM_VARS.m_curr_color) + AND (HL) + ADD A, A + LD (DE), A + INC D + LD A, (TM_VARS.m_curr_color+1) + AND (HL) + ADD A, A + LD (DE), A + + ; next font byte + DEC D + INC HL + INC E + DEC C + JP NZ, co_m_colorify + XOR A + ; Remove access to VRAM + OUT (SYS_DD17PB), A + ; Address to draw cursor proc on stack + LD HL, m_draw_cursor + PUSH HL + LD HL, TM_VARS.m_cursor_row + LD A, (TM_VARS.m_screen_mode) + AND 0x8 + JP NZ, m_cursor_rt_2 + +m_psc_fwd_cmn: + INC HL + LD A, (HL) + ADD A, 0x2 + AND 0x3f + LD (HL), A + DEC HL + RET NZ +m_psc_lf_cmn: + LD A, (HL) + ADD A, 0xe + CP 0xfa + JP NC, LAB_ram_e57a + LD (HL), A + RET +LAB_ram_e57a: + LD A, (TM_VARS.m_row_shift) + ADD A, 0xe + OUT (SYS_DD17PA), A + LD (TM_VARS.m_row_shift), A + LD HL, 0x40f0 + ADD A, L + LD L, A + DEC L + DEC L + LD C, H + LD A, 0x1 + OUT (SYS_DD17PB), A + XOR A + LD DE, 0x1240 + +LAB_ram_e594: + LD H, C + LD B, E +LAB_ram_e596: + LD (HL), A + INC H + DEC B + JP NZ, LAB_ram_e596 + INC L + DEC D + JP NZ, LAB_ram_e594 + XOR A + OUT (SYS_DD17PB), A + RET + +m_psc_bksp_cmn: + INC HL + LD A, (HL) + SUB 0x2 + AND 0x3f + LD (HL), A + CP 0x3e + DEC HL + RET NZ + +m_psc_up_cmn: + LD A, (HL) + SUB 14 + JP NC, up_no_minus + LD A, 238 +up_no_minus: + LD (HL), A + RET + +m_psc_tab_cmn: + INC HL + LD A, (HL) + ADD A,16 + AND 0x30 + LD (HL), A + DEC HL + RET NZ + JP m_psc_lf_cmn + +m_psc_tab: + INC HL + LD A, (HL) + ADD A, 16 + AND 0x30 + LD (HL), A + DEC HL + RET NZ + JP m_psc_lf + + ; Move cursor 2 sym right, move to next line if wrap +m_cursor_rt_2: + INC HL + LD A, (HL) + ADD A,2 + AND 0x3f ; screen column 0..63 + LD (HL), A + DEC HL + RET NZ ; Return if no wrap + +m_psc_lf: + LD A, (HL) + ADD A, 12 + CP 16 + JP NC, mp_next_nowr + LD (HL), A + RET + +mp_next_nowr: + LD A, (TM_VARS.m_row_shift) + LD L, A + ADD A, 12 + LD E, A + LD C, 8 + ; Acces VRAM + LD A,1 + OUT (SYS_DD17PB), A +LAB_ram_e5f2: + LD B, 0x40 + LD H, 0x40 + LD D, H +LAB_ram_e5f7: + LD A, (DE) + LD (HL), A + INC H + INC D + DEC B + JP NZ, LAB_ram_e5f7 + INC L + INC E + DEC C + JP NZ, LAB_ram_e5f2 + LD C, 0xc + LD A, (TM_VARS.m_row_shift) + ADD A, 0x8 + LD E, A +LAB_ram_e60d: + LD B, 0x40 + LD D, 0x40 + XOR A +LAB_ram_e612: + LD (DE), A + INC D + DEC B + JP NZ, LAB_ram_e612 + INC E + DEC C + JP NZ, LAB_ram_e60d + XOR A + OUT (SYS_DD17PB), A + RET + +m_psc_bksp: + INC HL + LD A, (HL) + OR A + DEC HL + RET Z + INC HL + SUB 0x2 + AND 0x3f + LD (HL), A + DEC HL + RET + +co_m_no_color: + CP 7 + JP Z, LAB_ram_e6b5 + CP 3 + JP Z, LAB_ram_e6b5 + AND 0x2 + JP NZ, LAB_ram_e7b9 + LD A, 0x1 + OUT (SYS_DD17PB), A + EX DE, HL + XOR A + LD (DE), A + INC E + +LAB_ram_e645: + LD A, (HL) + ADD A, A + LD (DE), A + INC HL + INC E + DEC C + JP NZ, LAB_ram_e645 + XOR A + OUT (SYS_DD17PB), A + LD HL, m_draw_cursor + PUSH HL + LD HL, TM_VARS.m_cursor_row +LAB_ram_e658: + INC HL + LD A, (HL) + ADD A, 0x1 + AND 0x3f + LD (HL), A + DEC HL + RET NZ +LAB_ram_e661: + LD A, (HL) + ADD A, 0xb + CP 0xfa + JP NC, LAB_ram_e66b + LD (HL), A + RET + +LAB_ram_e66b: + LD A, (TM_VARS.m_row_shift) + ADD A, 0xb + OUT (SYS_DD17PA), A + LD (TM_VARS.m_row_shift), A + LD HL, 0x40f0 + ADD A,L + LD L, A + LD C,H + LD A, 0x1 + OUT (SYS_DD17PB), A + XOR A + LD DE, 0x1040 +LAB_ram_e683: + LD H, C + LD B, E +LAB_ram_e685: + LD (HL), A + INC H + DEC B + JP NZ, LAB_ram_e685 + INC L + DEC D + JP NZ, LAB_ram_e683 + XOR A + OUT (SYS_DD17PB), A + RET +LAB_ram_e694: + INC HL + LD A, (HL) + SUB 0x1 + AND 0x3f + LD (HL), A + CP 0x3f + DEC HL + RET NZ +LAB_ram_e69f: + LD A, (HL) + SUB 0xb + JP NC, LAB_ram_e6a7 + LD A, 0xf2 +LAB_ram_e6a7: + LD (HL), A + RET +LAB_ram_e6a9: + INC HL + LD A, (HL) + ADD A, 0x8 + AND 0x38 + LD (HL), A + DEC HL + RET NZ + JP LAB_ram_e661 +LAB_ram_e6b5: + CALL m_calc_addr_40 + LD A, 0x1 + OUT (SYS_DD17PB), A + EX DE, HL + LD A,B + OR B + JP Z, LAB_ram_e6cd + DEC B + JP Z, LAB_ram_e6df + DEC B + JP Z, LAB_ram_e706 + JP LAB_ram_e731 +LAB_ram_e6cd: + XOR A + LD (DE), A + INC E +LAB_ram_e6d0: + LD B, (HL) + LD A, (DE) + AND 0xc0 + OR B + LD (DE), A + INC HL + INC E + DEC C + JP NZ, LAB_ram_e6d0 + JP LAB_ram_e745 +LAB_ram_e6df: + XOR A + LD (DE), A + DEC D + LD (DE), A + INC D + INC E +LAB_ram_e6e5: + LD A, (HL) + RRCA + RRCA + AND 0x7 + LD B, A + LD A, (DE) + AND 0xf0 + OR B + LD (DE), A + LD A, (HL) + RRCA + RRCA + AND 0xc0 + LD B, A + DEC D + LD A, (DE) + AND 0x1f + OR B + LD (DE), A + INC D + INC HL + INC E + DEC C + JP NZ, LAB_ram_e6e5 + JP LAB_ram_e745 +LAB_ram_e706: + XOR A + LD (DE), A + DEC D + LD (DE), A + INC D + INC E +LAB_ram_e70c: + LD A, (HL) + RRCA + RRCA + RRCA + RRCA + AND 0x1 + LD B, A + LD A, (DE) + AND 0xfc + OR B + LD (DE), A + LD A, (HL) + RRCA + RRCA + RRCA + RRCA + AND 0xf0 + LD B, A + DEC D + LD A, (DE) + AND 0x7 + OR B + LD (DE), A + INC D + INC HL + INC E + DEC C + JP NZ, LAB_ram_e70c + JP LAB_ram_e745 +LAB_ram_e731: + DEC D + XOR A + LD (DE), A + INC E +LAB_ram_e735: + LD A, (HL) + RLCA + RLCA + LD B, A + LD A, (DE) + AND 0x1 + OR B + LD (DE), A + INC HL + INC E + DEC C + JP NZ, LAB_ram_e735 + INC D +LAB_ram_e745: + XOR A + OUT (SYS_DD17PB), A + LD HL, m_draw_cursor + PUSH HL + LD HL, TM_VARS.m_cursor_row +LAB_ram_e74f: + INC HL + LD A, (HL) + ADD A, 0x1 + AND 0x7f + LD (HL), A + CP 0x50 + DEC HL + RET M +LAB_ram_e75a: + INC HL + XOR A + LD (HL), A + DEC HL +LAB_ram_e75e: + LD A, (HL) + ADD A, 0xb + CP 0xfa + JP NC, LAB_ram_e66b + LD (HL), A + RET +LAB_ram_e768: + INC HL + LD A, (HL) + SUB 0x1 + AND 0x7f + CP 0x7f + JP Z, LAB_ram_e776 + LD (HL), A + DEC HL + RET +LAB_ram_e776: + LD A, 0x4f + LD (HL), A + DEC HL +LAB_ram_e77a: + LD A, (HL) + SUB 0xb + JP NC, LAB_ram_e782 + LD A, 0xf2 +LAB_ram_e782: + LD (HL), A + RET +LAB_ram_e784: + INC HL + LD A, (HL) + ADD A, 0x8 + AND 0x7f + LD (HL), A + CP 0x50 + DEC HL + RET M + JP LAB_ram_e75a + +; ------------------------------------------------------ +; Calculate text position in 40 column text mode +; Out: HL - addr +; B - bit no +; C = 7 +; ------------------------------------------------------ +m_calc_addr_40: + LD HL, (TM_VARS.m_cursor_row) + LD A, (TM_VARS.m_row_shift) + ADD A,L + LD L, A ; HL = row+shift + LD A,H + CP 4 + LD B, A + JP M, ca_bef_scrn_top + AND 0x3 + LD B, A + LD A,H + OR A + RRA + OR A + RRA + LD C, A + LD H, 0x3 + XOR A + +ca_lbl1: + ADD A,H + DEC C + JP NZ, ca_lbl1 + ADD A,B +ca_bef_scrn_top: + ADD A, 0x40 ; next row + LD H, A + LD C, 0x7 + RET + +LAB_ram_e7b9: + LD A, (TM_VARS.m_cursor_col) + CP 0x40 + JP M, LAB_ram_e7c8 + LD HL, TM_VARS.m_cursor_row + CALL m_draw_cursor + RET +LAB_ram_e7c8: + LD A, 0x1 + OUT (SYS_DD17PB), A + EX DE, HL + XOR A + LD (DE), A + INC E +LAB_ram_e7d0: + LD A, (HL) + ADD A, A + LD (DE), A + INC HL + INC E + DEC C + JP NZ, LAB_ram_e7d0 + XOR A + OUT (SYS_DD17PB), A + LD HL, m_draw_cursor + PUSH HL + LD HL, TM_VARS.m_cursor_row + INC HL + LD A, (HL) + ADD A, 0x1 + CP 0x40 + JP M, LAB_ram_e7ee + LD A, 0x40 +LAB_ram_e7ee: + LD (HL), A + DEC HL + RET + +m_psc_clrscr_cmn: + LD A, (TM_VARS.m_screen_mode) + AND 0x8 + JP NZ,m_clr_color + LD A,01111111b + OUT (VID_DD67PB), A ; C/M=1 FL=111 CL=111 All black + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + LD DE, video_ram + EX DE, HL + LD A,H + ADD A,64 ; row + 1 + LD B, 0x0 + +clr_fill_scrn1: + LD (HL),B + INC HL + CP H + JP NZ, clr_fill_scrn1 + EX DE, HL + LD A, (TM_VARS.m_cur_palette) + LD B, A + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + LD A, 0x0 + JP NZ, clr_rest_no_color + LD A, 01000000b + +clr_rest_no_color: + OR B + ; Restore mode and palette + OUT (VID_DD67PB), A + +m_psc_home_cmn: + XOR A + NOP + NOP + LD (HL), A + INC HL + XOR A + LD (HL), A + DEC HL + XOR A + ; Disable VRAM access + OUT (SYS_DD17PB), A + RET + + ; Clear scr in color mode +m_clr_color: + LD A, (TM_VARS.m_row_shift) + LD L, A + LD C,20 + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A +m_clr_fill_c1: + LD H, 0x40 ; HL = 0x4000 + shift_row + LD B,64 ; 64 bytes at row + XOR A +m_clr_fill_c2: + LD (HL), A + INC H + DEC B + JP NZ, m_clr_fill_c2 + INC L + DEC C + JP NZ, m_clr_fill_c1 + XOR A + ; Disabe VRAM access + OUT (SYS_DD17PB), A + JP m_psc_home_cmn +m_draw_cursor: + LD A, (TM_VARS.m_screen_mode) + AND 0x4 + RET NZ + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + JP NZ, LAB_ram_e884 + EX DE, HL + LD HL, (TM_VARS.m_cursor_row) + LD A, (TM_VARS.m_row_shift) + ADD A, L + LD L, A + LD A, H + ADD A, 0x40 + LD H, A + LD A, 0x1 + OUT (SYS_DD17PB), A + LD BC, 0x7f08 +LAB_ram_e872: + LD A, (HL) + XOR B + LD (HL), A + INC H + LD A, (HL) + XOR B + LD (HL), A + DEC H + INC L + DEC C + JP NZ, LAB_ram_e872 + EX DE, HL + XOR A + OUT (SYS_DD17PB), A + RET +LAB_ram_e884: + CP 0x3 + JP Z, LAB_ram_e8af + EX DE, HL + LD HL, (TM_VARS.m_cursor_row) + LD A, (TM_VARS.m_row_shift) + ADD A, L + LD L, A + LD A, H + CP 0x40 + EX DE, HL + RET P + EX DE, HL + ADD A, 0x40 + LD H, A + LD A, 0x1 + OUT (SYS_DD17PB), A + LD BC, 0x7f08 +LAB_ram_e8a2: + LD A, (HL) + XOR B + LD (HL), A + INC L + DEC C + JP NZ, LAB_ram_e8a2 + EX DE, HL + XOR A + OUT (SYS_DD17PB), A + RET +LAB_ram_e8af: + EX DE, HL + LD HL, (TM_VARS.m_cursor_row) + LD A, H + CP 0x50 + EX DE, HL + RET P + EX DE, HL + CALL m_calc_addr_40 + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, B + OR B + JP Z, LAB_ram_e8d0 + DEC B + JP Z, LAB_ram_e8e6 + DEC B + JP Z, LAB_ram_e908 + JP LAB_ram_e92a +LAB_ram_e8d0: + LD BC, 0x1f08 +LAB_ram_e8d3: + LD A, (HL) + AND 0xc0 + LD B, A + LD A, (HL) + XOR 0x1f + AND 0x1f + OR B + LD (HL), A + INC L + DEC C + JP NZ, LAB_ram_e8d3 + JP LAB_ram_e93e +LAB_ram_e8e6: + LD C, 0x8 +LAB_ram_e8e8: + DEC H + LD A, (HL) + AND 0x1f + LD B, A + LD A, (HL) + XOR 0xc0 + AND 0xc0 + OR B + LD (HL), A + INC H + LD A, (HL) + AND 0xf0 + LD B, A + LD A, (HL) + XOR 0x7 + AND 0x7 + OR B + LD (HL), A + INC L + DEC C + JP NZ, LAB_ram_e8e8 + JP LAB_ram_e93e +LAB_ram_e908: + LD C, 0x8 +LAB_ram_e90a: + DEC H + LD A, (HL) + AND 0x7 + LD B, A + LD A, (HL) + XOR 0xf0 + AND 0xf0 + OR B + LD (HL), A + INC H + LD A, (HL) + AND 0xfc + LD B, A + LD A, (HL) + XOR 0x1 + AND 0x1 + OR B + LD (HL), A + INC L + DEC C + JP NZ, LAB_ram_e90a + JP LAB_ram_e93e +LAB_ram_e92a: + LD C, 0x8 + DEC H +LAB_ram_e92d: + LD A, (HL) + AND 0x1 + LD B, A + LD A, (HL) + XOR 0x7c + AND 0x7c + OR B + LD (HL), A + INC L + DEC C + JP NZ, LAB_ram_e92d + INC H +LAB_ram_e93e: + EX DE, HL + XOR A + OUT (SYS_DD17PB), A ; reset screen shifts + RET + +m_print_control_char: + CP ASCII_ESC + JP NZ,m_psc_std_char + ; turn on ESC mode for next chars + LD HL, TM_VARS.m_esc_mode + LD (HL), 0x1 + INC HL + LD (HL), 0xff + RET + +m_psc_std_char: + CP ASCII_BELL + JP Z, m_beep + LD HL, m_draw_cursor + PUSH HL + LD HL, TM_VARS.m_cursor_row + PUSH AF + CALL m_draw_cursor + LD A, (TM_VARS.m_screen_mode) + AND 0x8 ; mode 40x20? + JP Z, m_psc_no_40x30 ; jump if no + POP AF + CP ASCII_TAB ; TAB + JP Z,m_psc_tab + CP ASCII_BS ; BKSP + JP Z,m_psc_bksp + CP ASCII_CAN ; Cancel + JP Z,m_cursor_rt_2 + CP ASCII_US ; ASCII Unit separator + JP Z,m_clr_color + CP ASCII_LF ; LF + JP Z,m_psc_lf + CP ASCII_CR ; CR + RET NZ ; ret on unknown + INC HL + LD (HL), 0x0 + DEC HL + RET + + ; common for 40x25, 64x25, 80x25 modes +m_psc_no_40x30: + POP AF + CP ASCII_US ; Unit separator + JP Z, m_psc_clrscr_cmn + CP ASCII_FF ; Form feed + JP Z, m_psc_home_cmn + PUSH AF + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + JP NZ, LAB_ram_e9c6 + POP AF + CP ASCII_TAB + JP Z, m_psc_tab_cmn + CP ASCII_BS + JP Z, m_psc_bksp_cmn + CP ASCII_CAN + JP Z, m_psc_fwd_cmn + CP ASCII_EM ; ASCII End of medium + JP Z, m_psc_up_cmn + CP ASCII_SUB + JP Z, m_psc_lf_cmn ; cursor down + CP ASCII_LF + JP Z, m_psc_lf_cmn + CP ASCII_CR + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +LAB_ram_e9c6: + LD A, (TM_VARS.m_screen_mode) + CP 0x3 + JP Z, m_psc_no_40x25 + CP 0x7 + JP Z, m_psc_no_40x25 + AND 0x2 + JP NZ, LAB_ram_e9ff +; For 40x25? + POP AF + CP 0x9 + JP Z, LAB_ram_e6a9 + CP 0x8 + JP Z, LAB_ram_e694 + CP 0x18 + JP Z, LAB_ram_e658 + CP 0x19 + JP Z, LAB_ram_e69f + CP 0x1a + JP Z, LAB_ram_e661 + CP 0xa + JP Z, LAB_ram_e661 + CP 0xd + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +LAB_ram_e9ff: + POP AF + CP 0xa + JP Z, LAB_ram_e661 + CP 0xd + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +m_psc_no_40x25: + POP AF + CP 0x9 + JP Z, LAB_ram_e784 + CP 0x8 + JP Z, LAB_ram_e768 + CP 0x18 + JP Z, LAB_ram_e74f + CP 0x19 + JP Z, LAB_ram_e77a + CP 0x1a + JP Z, LAB_ram_e75e + CP 0xa + JP Z, LAB_ram_e75e + CP 0xd + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +m_beep: + LD HL, (TM_VARS.m_beep_duration) + EX DE, HL + LD HL, (TM_VARS.m_beep_period) + LD A,00110110b ; TMR#0 LSB+MSB Square Wave Generator + OUT (TMR_DD70CTR), A + LD A,L ; LSB + OUT (TMR_DD70C1), A + LD A,H ; MSB + OUT (TMR_DD70C1), A + LD A, (TM_VARS.m_strobe_state) + LD B, A +m_bell_cont: + LD A, D ; DE=duration + OR E + RET Z ; ret if enough + DEC DE + LD A,B + XOR BELL_PIN + LD B, A + OUT (DD67PC), A ; Invert bell pin +m_bell_wait_tmr1: + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; 0x10 + JP NZ,m_bell_wait_tmr1 + LD A,B + XOR BELL_PIN ; Flip pin again + LD B, A + OUT (DD67PC), A +m_bell_wait_tmr2: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP Z,m_bell_wait_tmr2 + JP m_bell_cont + +; ------------------------------------------------------ +; 5 Set cursor position +; ------------------------------------------------------ +esc_set_cursor: + LD A, (TM_VARS.m_screen_mode) + AND 0x8 + RET NZ ; ret if graphics mode + CALL m_draw_cursor ; hide cursor + LD A, (TM_VARS.m_screen_mode) + AND 0x7 ; mode 0-7 + JP NZ,sc_set_64_or_80 + ; Set cursor for 32x18 mode + LD DE, TM_VARS.m_esc_param_1 + LD HL, TM_VARS.m_cursor_col + INC DE + LD A, (DE) ; column + AND 0x1f ; limit column to 0..31 + ADD A, A ; *2 + LD (HL), A + DEC DE + DEC HL + LD A, (DE) ; row + AND 0x1f ; 0..31 + CP 17 + JP C,sc_no_row_limit1 + LD A,17 + +sc_no_row_limit1: + LD B, A + ADD A, A + ADD A,B + ADD A, A + ADD A,B + ADD A, A ; a = a * 14 (font height) + LD (HL), A + CALL m_draw_cursor + RET + +sc_set_64_or_80: + LD A, (TM_VARS.m_screen_mode) + CP 0x3 + JP Z, sc_set_for_80x32 + CP 0x7 + JP Z, sc_set_for_80x32 + AND 0x2 + JP NZ, sc_set_for_65x23 + ; Set for 64 col modes + LD DE, TM_VARS.m_esc_param_1 ; row + LD HL, TM_VARS.m_cursor_col + INC DE + LD A, (DE) ; column + SUB 0x20 + AND 0x3f ; 0..63 + LD (HL), A + DEC DE + DEC HL + LD A, (DE) ; row + ; limit row to 0..22 + AND 0x1f + CP 22 + JP C,sc_no_row_limit2 + LD A,22 +sc_no_row_limit2: + LD B, A + ADD A, A + ADD A, A + ADD A,B + ADD A, A + ADD A,B ; A = A * 11 (font height) + LD (HL), A + CALL m_draw_cursor ; show cursor + RET + +sc_set_for_65x23: + LD DE, TM_VARS.m_esc_param_1 + LD HL, TM_VARS.m_cursor_col + INC DE + LD A, (DE) ; column + SUB 0x20 + CP 64 + JP M,sc_no_col_limit3 + LD A,64 + +sc_no_col_limit3: + LD (HL), A + DEC DE + DEC HL + LD A, (DE) ; row + AND 0x1f + CP 22 + JP C,sc_no_row_limit3 + LD A,22 +sc_no_row_limit3: + LD B, A + ADD A, A + ADD A, A + ADD A,B + ADD A, A + ADD A,B ; A = A * 11 + LD (HL), A + CALL m_draw_cursor ; show cursor + RET + +sc_set_for_80x32: + LD DE, TM_VARS.m_esc_param_1 + LD HL, TM_VARS.m_cursor_col + INC DE + LD A, (DE) + SUB 0x20 + AND 0x7f + CP 79 + JP M, sc_no_row_limit4 + LD A,79 + +sc_no_row_limit4: + LD (HL), A + DEC DE + DEC HL + LD A, (DE) + AND 0x1f + CP 22 + JP C,sc_no_col_limit4 + LD A,22 + +sc_no_col_limit4: + LD B, A + ADD A, A + ADD A, A + ADD A,B + ADD A, A + ADD A,B ; A = A * 11 + LD (HL), A + CALL m_draw_cursor ; show cursor + RET + +; ------------------------------------------------------ +; 6n +; where n is +; 0 - 32x18 with cursor; +; 1,2 - 64x23 with cursor; +; 3 - 80x23 with cursor; +; 4 - 32x18 no cursor; +; 5,6 - 64x23 no cursor; +; 7 - 80x23 no cursor; +; 8 - graphics mode. +; ------------------------------------------------------ +esc_set_vmode: + LD HL, TM_VARS.m_screen_mode + LD A, (TM_VARS.m_cur_palette) + LD B, A ; b = palette + LD A, (TM_VARS.m_esc_param_1) + LD C, A ; c = mode + AND 0x8 ; graph mode? + LD A, C + JP Z,svm_set_text + LD A, 0x8 +svm_set_text: + AND 0xf + LD (HL), A ; save new mode + AND 0x7 ; with cursor? + LD A,00000000b + JP NZ, swm_no_color + LD A,01000000b +swm_no_color: + OR B + OUT (VID_DD67PB), A ; Set C/M and palette + LD HL, TM_VARS.m_cursor_row + CALL m_psc_clrscr_cmn + CALL m_draw_cursor + RET + +; ------------------------------------------------------ +; 4n n=1..4 Set drawing color +; ------------------------------------------------------ +esc_set_color: + LD A, (TM_VARS.m_esc_param_1) + AND 0x3 + RRA + LD B, A + LD A, 0x0 + SBC A, A + LD (TM_VARS.m_curr_color), A + LD A, B + DEC A + CPL + LD (TM_VARS.m_curr_color+1), A + RET + +co_exit_esc: + LD A, (TM_VARS.m_screen_mode) + AND 0x7 + JP NZ, esc_exit + LD A, C + AND 0x7f + LD C, A + CP 0x20 + JP M, esc_exit + LD HL, TM_VARS.m_esc_param_1 + LD A, (HL) + LD E, A + ADD A, 0x8 + JP C, esc_exit + LD (HL), A + INC HL + LD A, 0xf7 + CP (HL) + JP C, esc_exit + LD D, (HL) + CALL SUB_ram_ebe2 + LD A, L + SUB 0x7 + LD L, A + PUSH HL + LD A, C + CALL m_get_glyph + POP DE + LD C, 0x7 + +LAB_ram_eb9b: + PUSH HL + LD A, 0x1 + OUT (SYS_DD17PB), A + LD L, (HL) + LD H, 0x0 + LD A, B + OR A + JP Z, LAB_ram_ebad +LAB_ram_eba8: + ADD HL, HL + DEC A + JP NZ, LAB_ram_eba8 +LAB_ram_ebad: + EX DE, HL + PUSH BC + LD A, (TM_VARS.m_curr_color) + CPL + LD B, A + LD A, (HL) + XOR B + OR E + XOR B + LD (HL), A + INC H + INC H + LD A, (HL) + XOR B + OR D + XOR B + LD (HL), A + DEC H + LD A, (TM_VARS.m_curr_color+1) + CPL + LD B, A + LD A, (HL) + XOR B + OR E + XOR B + LD (HL), A + INC H + INC H + LD A, (HL) + XOR B + OR D + XOR B + LD (HL), A + DEC H + DEC H + DEC H + INC L + EX DE, HL + POP BC + XOR A + OUT (SYS_DD17PB), A + POP HL + INC HL + DEC C + JP NZ, LAB_ram_eb9b + RET +SUB_ram_ebe2: + LD A, (TM_VARS.m_row_shift) + SUB D + DEC A + LD L, A + LD A, E + AND 0x7 + LD B, A + LD A, E + RRA + RRA + AND 0x3e + ADD A, 0x40 + LD H, A + RET + +esc_draw_fill_rect: + LD HL, TM_VARS.m_esc_param_4 + LD DE, TM_VARS.m_esc_param_2 + LD A, (DE) + LD B, (HL) + CP B + JP NC, LAB_ram_ec04 + LD (HL), A + LD A,B + LD (DE), A +LAB_ram_ec04: + DEC DE + DEC HL + LD A, (DE) + LD B, (HL) + CP B + JP C, LAB_ram_ec0f + LD (HL), A + LD A,B + LD (DE), A +LAB_ram_ec0f: + EX DE, HL + LD E, (HL) + INC HL + LD D, (HL) + CALL SUB_ram_ebe2 + PUSH HL + XOR A +LAB_ram_ec18: + SCF + RLA + DEC B + JP P, LAB_ram_ec18 + RRA + LD D, A + LD HL, TM_VARS.m_esc_param_3 + LD A, (HL) + AND 0x7 + LD B, A + XOR A +LAB_ram_ec28: + SCF + RLA + DEC B + JP P, LAB_ram_ec28 + CPL + LD E, A + LD A, (HL) + DEC HL + DEC HL + SUB (HL) + RRCA + RRCA + RRCA + AND 0x1f + LD C, A + INC HL + LD A, (HL) + INC HL + INC HL + SUB (HL) + JP NZ, LAB_ram_ec43 + INC A +LAB_ram_ec43: + LD B, A + POP HL + LD A, E + LD (TM_VARS.m_esc_hex_cmd), A +LAB_ram_ec49: + PUSH DE + PUSH HL + PUSH BC + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, C + OR A + JP NZ, LAB_ram_ec58 + LD A, D + OR E +dr_no_cmd: + LD D, A +LAB_ram_ec58: + LD B, D + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + INC H + LD A, C + OR A + JP Z, LAB_ram_ec81 + DEC C +LAB_ram_ec70: + LD A, (TM_VARS.m_esc_hex_cmd) + JP Z, dr_no_cmd +LAB_ram_ec76: + LD (HL), E + INC H + LD (HL), D + INC H + DEC C + JP NZ, LAB_ram_ec76 + JP LAB_ram_ec70 +LAB_ram_ec81: + XOR A + OUT (SYS_DD17PB), A + POP BC + POP HL + POP DE + INC L + DEC B + JP NZ, LAB_ram_ec49 + RET + +esc_draw_line: + LD HL, TM_VARS.m_esc_param_1 + LD E, (HL) + INC HL + LD D, (HL) + INC HL + LD A, (HL) + INC HL + LD H, (HL) + LD L, A + CP E + JP C, LAB_ram_ec9d + EX DE, HL +LAB_ram_ec9d: + LD (TM_VARS.m_esc_param_1), HL + LD A, E + SUB L + LD L, A + LD A, D + SUB H + LD H, A + PUSH AF + JP NC, LAB_ram_ecad + CPL + INC A + LD H, A +LAB_ram_ecad: + EX DE, HL + LD HL, (TM_VARS.m_esc_param_1) + EX DE, HL + JP Z, LAB_ram_ed96 + LD A, L + OR A + JP Z, LAB_ram_ed4c + LD B, A + POP AF + LD A, 0x0 + ADC A, A + LD (TM_VARS.m_esc_hex_cmd), A + LD E, H + LD C, 0x10 + LD D, 0x0 +LAB_ram_ecc7: + ADD HL, HL + EX DE, HL + ADD HL, HL + EX DE, HL + LD A, D + JP C, LAB_ram_ecd3 + CP B + JP C, LAB_ram_ecd6 +LAB_ram_ecd3: + SUB B + LD D, A + INC HL +LAB_ram_ecd6: + DEC C + JP NZ, LAB_ram_ecc7 + LD DE, 0x0 + PUSH DE + PUSH HL + LD HL, (TM_VARS.m_esc_param_1) + EX DE, HL + LD C,B + CALL SUB_ram_ebe2 + LD A, 0x80 +LAB_ram_ece9: + RLCA + DEC B + JP P, LAB_ram_ece9 + CPL + LD B, A +LAB_ram_ecf0: + POP DE + EX (SP), HL + LD A,H + ADD HL, DE + SUB H + CPL + INC A + EX (SP), HL + PUSH DE + PUSH BC + LD C, A + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (TM_VARS.m_esc_hex_cmd) + OR A + JP NZ, LAB_ram_ed21 +LAB_ram_ed0b: + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A, C + OR A + JP Z, LAB_ram_ed37 + DEC C + DEC L + JP LAB_ram_ed0b +LAB_ram_ed21: + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A, C + OR A + JP Z, LAB_ram_ed37 + DEC C + INC L + JP LAB_ram_ed21 +LAB_ram_ed37: + XOR A + OUT (SYS_DD17PB), A + POP BC + LD A,B + SCF + RLA + JP C, LAB_ram_ed44 + RLA + INC H + INC H +LAB_ram_ed44: + LD B, A + DEC C + JP NZ, LAB_ram_ecf0 + POP HL + POP HL + RET +LAB_ram_ed4c: + LD C,H + CALL SUB_ram_ebe2 + LD A, 0x80 +LAB_ram_ed52: + RLCA + DEC B + JP P, LAB_ram_ed52 + CPL + LD B, A + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + POP AF + LD A, 0x1 + OUT (SYS_DD17PB), A + JP C, LAB_ram_ed7c +LAB_ram_ed66: + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A, C + OR A + JP Z, LAB_ram_ed92 + DEC C + DEC L + JP LAB_ram_ed66 +LAB_ram_ed7c: + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A, C + OR A + JP Z, LAB_ram_ed92 + DEC C + INC L + JP LAB_ram_ed7c +LAB_ram_ed92: + XOR A + OUT (SYS_DD17PB), A + RET +LAB_ram_ed96: + POP AF + LD C,L + LD A,L + OR A + JP NZ, LAB_ram_ed9e + INC C +LAB_ram_ed9e: + CALL SUB_ram_ebe2 + LD A, 0x80 +LAB_ram_eda3: + RLCA + DEC B + JP P, LAB_ram_eda3 + CPL + LD B, A + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + LD A, 0x1 + OUT (SYS_DD17PB), A +LAB_ram_edb3: + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A,B + SCF + RLA + JP C, LAB_ram_edc8 + RLA + INC H + INC H +LAB_ram_edc8: + LD B, A + DEC C + JP NZ, LAB_ram_edb3 + XOR A + OUT (SYS_DD17PB), A + RET +esc_draw_dot: + LD HL, (TM_VARS.m_esc_param_1) + EX DE, HL + CALL SUB_ram_ebe2 + LD A, 0x80 +LAB_ram_edda: + RLCA + DEC B + JP P, LAB_ram_edda + LD B, A + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (HL) + XOR B + LD (HL), A + INC H + LD A, (HL) + XOR B + LD (HL), A + XOR A + OUT (SYS_DD17PB), A + RET +esc_fn_b: + LD A, (TM_VARS.m_esc_param_3) + LD B, A + OR A + RET Z + LD A, 0x7f + CP B + RET M + XOR A + LD D, A + LD E,B + CALL SUB_ram_ee53 + LD A, 0x1 + LD H, A + SUB B + LD C, A + LD A,B + RLCA + LD B, A + LD A, 0x1 + SUB B + LD L, A + CCF +LAB_ram_ee11: + INC D + LD A, E + CP D + JP Z,SUB_ram_ee53 + CALL SUB_ram_ee53 + LD A,H + ADD A, 0x2 + LD H, A + LD A,L + ADD A, 0x2 + LD L, A + LD A, C + ADD A,H + LD C, A + JP NC, LAB_ram_ee11 +LAB_ram_ee28: + CCF + INC D + DEC E + LD A, D + CP E + JP Z,SUB_ram_ee53 + SUB E + CP 0x1 + RET Z + LD A, E + SUB D + CP 0x1 + JP Z,SUB_ram_ee53 + CALL SUB_ram_ee53 + LD A,H + ADD A, 0x2 + LD H, A + LD A,L + ADD A, 0x4 + LD L, A + JP NC, LAB_ram_ee4a + CCF +LAB_ram_ee4a: + LD A, C + ADD A,L + LD C, A + JP NC, LAB_ram_ee11 + JP LAB_ram_ee28 +SUB_ram_ee53: + PUSH HL + PUSH DE + PUSH BC + PUSH DE + CALL SUB_ram_ee6f + LD HL, (TM_VARS.m_esc_param_1) + CALL SUB_ram_eedc + POP DE + CALL SUB_ram_ee8f + LD HL, (TM_VARS.m_esc_param_1) + CALL SUB_ram_ef0b + POP BC + POP DE + POP HL + XOR A + RET +SUB_ram_ee6f: + LD HL, (TM_VARS.m_esc_param_4) + LD A,L + OR A + LD C, D + LD B, E + JP NZ, LAB_ram_ee7f + LD A,H + OR A + JP NZ, LAB_ram_ee88 + RET +LAB_ram_ee7f: + LD A,H + LD H,L + LD E, C +OFF_ram_ee82: + CALL SUB_ram_eeaf + LD C, E + OR A + RET Z +LAB_ram_ee88: + LD H, A + LD E,B + CALL SUB_ram_eeaf + LD B, E + RET +SUB_ram_ee8f: + LD HL, (TM_VARS.m_esc_param_4) + LD A,L + OR A + LD C, D + LD B, E + JP NZ, LAB_ram_ee9f + LD A,H + OR A + JP NZ, LAB_ram_eea8 + RET +LAB_ram_ee9f: + LD A,H + LD H,L + LD E,B + CALL SUB_ram_eeaf + LD B, E + OR A + RET Z +LAB_ram_eea8: + LD H, A + LD E, C + CALL SUB_ram_eeaf + LD C, E + RET +SUB_ram_eeaf: + LD D, 0x0 + LD L, D + ADD HL, HL + JP NC, LAB_ram_eeb7 + ADD HL, DE +LAB_ram_eeb7: + ADD HL, HL + JP NC, LAB_ram_eebc + ADD HL, DE +LAB_ram_eebc: + ADD HL, HL + JP NC, LAB_ram_eec1 + ADD HL, DE +LAB_ram_eec1: + ADD HL, HL + JP NC, LAB_ram_eec6 + ADD HL, DE +LAB_ram_eec6: + ADD HL, HL + JP NC, LAB_ram_eecb + ADD HL, DE +LAB_ram_eecb: + ADD HL, HL + JP NC, LAB_ram_eed0 + ADD HL, DE +LAB_ram_eed0: + ADD HL, HL + JP NC, LAB_ram_eed5 + ADD HL, DE +LAB_ram_eed5: + ADD HL, HL + JP NC, LAB_ram_eeda + ADD HL, DE +LAB_ram_eeda: + LD E,H + RET +SUB_ram_eedc: + LD A,H + ADD A,B + JP C, LAB_ram_eee8 + LD D, A + LD A,L + ADD A, C + LD E, A + CALL SUB_ram_ef3a +LAB_ram_eee8: + LD A,H + ADD A,B + JP C, LAB_ram_eef4 + LD D, A + LD A,L + SUB C + LD E, A + CALL SUB_ram_ef3a +LAB_ram_eef4: + LD A,H + SUB B + JP C, LAB_ram_ef00 + LD D, A + LD A,L + SUB C + LD E, A + CALL SUB_ram_ef3a +LAB_ram_ef00: + LD A,H + SUB B + RET C + LD D, A + LD A,L + ADD A, C + LD E, A + CALL SUB_ram_ef3a + RET +SUB_ram_ef0b: + LD A,H + ADD A, C + JP C, LAB_ram_ef17 + LD D, A + LD A,L + ADD A,B + LD E, A + CALL SUB_ram_ef3a +LAB_ram_ef17: + LD A,H + ADD A, C + JP C, LAB_ram_ef23 + LD D, A + LD A,L + SUB B + LD E, A + CALL SUB_ram_ef3a +LAB_ram_ef23: + LD A,H + SUB C + JP C, LAB_ram_ef2f + LD D, A + LD A,L + SUB B + LD E, A + CALL SUB_ram_ef3a +LAB_ram_ef2f: + LD A,H + SUB C + RET C + LD D, A + LD A,L + ADD A,B + LD E, A + CALL SUB_ram_ef3a + RET +SUB_ram_ef3a: + RET C + PUSH HL + PUSH BC + CALL SUB_ram_ebe2 + LD A, 0x80 +LAB_ram_ef42: + RLCA + DEC B + JP P, LAB_ram_ef42 + CPL + LD B, A + EX DE, HL + LD HL, (TM_VARS.m_curr_color) + EX DE, HL + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + XOR A + OUT (SYS_DD17PB), A + POP BC + POP HL + RET + + ; Full charset, Common + Latin letters +m_font_cp0: + db 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04 + db 0x04, 0x04, 0x04, 0x00, 0x00, 0x04, 0x14, 0x14 + db 0x00, 0x00, 0x00, 0x00, 0x00, 0x0A, 0x0A, 0x1F + db 0x0A, 0x1F, 0x0A, 0x0A, 0x04, 0x1E, 0x05, 0x0E + db 0x14, 0x0F, 0x04, 0x03, 0x13, 0x08, 0x04, 0x02 + db 0x19, 0x18, 0x06, 0x09, 0x05, 0x02, 0x15, 0x09 + db 0x16, 0x06, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00 + db 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x02 + db 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00, 0x0A + db 0x04, 0x1F, 0x04, 0x0A, 0x00, 0x00, 0x04, 0x04 + db 0x1F, 0x04, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00 + db 0x06, 0x04, 0x02, 0x00, 0x00, 0x00, 0x1F, 0x00 + db 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06 + db 0x06, 0x00, 0x10, 0x08, 0x04, 0x02, 0x01, 0x00 + db 0x0E, 0x11, 0x19, 0x15, 0x13, 0x11, 0x0E, 0x04 + db 0x06, 0x04, 0x04, 0x04, 0x04, 0x0E, 0x0E, 0x11 + db 0x10, 0x08, 0x04, 0x02, 0x1F, 0x1F, 0x08, 0x04 + db 0x08, 0x10, 0x11, 0x0E, 0x08, 0x0C, 0x0A, 0x09 + db 0x1F, 0x08, 0x08, 0x1F, 0x01, 0x0F, 0x10, 0x10 + db 0x11, 0x0E, 0x0C, 0x02, 0x01, 0x0F, 0x11, 0x11 + db 0x0E, 0x1F, 0x10, 0x08, 0x04, 0x02, 0x02, 0x02 + db 0x0E, 0x11, 0x11, 0x0E, 0x11, 0x11, 0x0E, 0x0E + db 0x11, 0x11, 0x1E, 0x10, 0x08, 0x06, 0x00, 0x06 + db 0x06, 0x00, 0x06, 0x06, 0x00, 0x00, 0x06, 0x06 + db 0x00, 0x06, 0x04, 0x02, 0x08, 0x04, 0x02, 0x01 + db 0x02, 0x04, 0x08, 0x00, 0x00, 0x1F, 0x00, 0x1F + db 0x00, 0x00, 0x02, 0x04, 0x08, 0x10, 0x08, 0x04 + db 0x02, 0x0E, 0x11, 0x10, 0x08, 0x04, 0x00, 0x04 + db 0x0E, 0x11, 0x10, 0x16, 0x15, 0x15, 0x0E, 0x04 + db 0x0A, 0x11, 0x11, 0x1F, 0x11, 0x11, 0x0F, 0x11 + db 0x11, 0x0F, 0x11, 0x11, 0x0F, 0x0E, 0x11, 0x01 + db 0x01, 0x01, 0x11, 0x0E, 0x07, 0x09, 0x11, 0x11 + db 0x11, 0x09, 0x07, 0x1F, 0x01, 0x01, 0x0F, 0x01 + db 0x01, 0x1F, 0x1F, 0x01, 0x01, 0x0F, 0x01, 0x01 + db 0x01, 0x0E, 0x11, 0x01, 0x1D, 0x11, 0x11, 0x1E + db 0x11, 0x11, 0x11, 0x1F, 0x11, 0x11, 0x11, 0x0E + db 0x04, 0x04, 0x04, 0x04, 0x04, 0x0E, 0x1C, 0x08 + db 0x08, 0x08, 0x08, 0x09, 0x06, 0x11, 0x09, 0x05 + db 0x03, 0x05, 0x09, 0x11, 0x01, 0x01, 0x01, 0x01 + db 0x01, 0x01, 0x1F, 0x11, 0x1B, 0x15, 0x15, 0x11 + db 0x11, 0x11, 0x11, 0x11, 0x13, 0x15, 0x19, 0x11 + db 0x11, 0x0E, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0E + db 0x0F, 0x11, 0x11, 0x0F, 0x01, 0x01, 0x01, 0x0E + db 0x11, 0x11, 0x11, 0x15, 0x09, 0x16, 0x0F, 0x11 + db 0x11, 0x0F, 0x05, 0x09, 0x11, 0x1E, 0x01, 0x01 + db 0x0E, 0x10, 0x10, 0x0F, 0x1F, 0x04, 0x04, 0x04 + db 0x04, 0x04, 0x04, 0x11, 0x11, 0x11, 0x11, 0x11 + db 0x11, 0x0E, 0x11, 0x11, 0x11, 0x11, 0x0A, 0x0A + db 0x04, 0x11, 0x11, 0x11, 0x15, 0x15, 0x15, 0x0A + db 0x11, 0x11, 0x0A, 0x04, 0x0A, 0x11, 0x11, 0x11 + db 0x11, 0x11, 0x0A, 0x04, 0x04, 0x04, 0x1F, 0x10 + db 0x08, 0x04, 0x02, 0x01, 0x1F, 0x0E, 0x02, 0x02 + db 0x02, 0x02, 0x02, 0x0E, 0x00, 0x01, 0x02, 0x04 + db 0x08, 0x10, 0x00, 0x0E, 0x08, 0x08, 0x08, 0x08 + db 0x08, 0x0E, 0x0E, 0x11, 0x00, 0x00, 0x00, 0x00 + db 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1F + db 0x1C, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00 + db 0x00, 0x0E, 0x10, 0x1E, 0x13, 0x1E, 0x01, 0x01 + db 0x0D, 0x13, 0x11, 0x11, 0x0F, 0x00, 0x00, 0x0E + db 0x01, 0x01, 0x01, 0x0E, 0x10, 0x10, 0x16, 0x19 + db 0x11, 0x11, 0x1E, 0x00, 0x00, 0x0E, 0x11, 0x1F + db 0x01, 0x0E, 0x18, 0x04, 0x04, 0x0E, 0x04, 0x04 + db 0x04, 0x00, 0x0E, 0x11, 0x11, 0x1E, 0x10, 0x0E + db 0x01, 0x01, 0x0D, 0x13, 0x11, 0x11, 0x11, 0x04 + db 0x00, 0x04, 0x04, 0x04, 0x04, 0x04, 0x08, 0x00 + db 0x08, 0x08, 0x08, 0x08, 0x06, 0x01, 0x01, 0x09 + db 0x05, 0x03, 0x05, 0x09, 0x04, 0x04, 0x04, 0x04 + db 0x04, 0x04, 0x08, 0x00, 0x00, 0x0F, 0x15, 0x15 + db 0x15, 0x15, 0x00, 0x00, 0x09, 0x13, 0x11, 0x11 + db 0x11, 0x00, 0x00, 0x0E, 0x11, 0x11, 0x11, 0x0E + db 0x00, 0x00, 0x0E, 0x11, 0x11, 0x0F, 0x01, 0x00 + db 0x00, 0x0E, 0x11, 0x11, 0x1E, 0x10, 0x00, 0x00 + db 0x0D, 0x13, 0x01, 0x01, 0x01, 0x00, 0x00, 0x1E + db 0x01, 0x0E, 0x10, 0x0F, 0x04, 0x04, 0x0E, 0x04 + db 0x04, 0x04, 0x18, 0x00, 0x00, 0x11, 0x11, 0x11 + db 0x19, 0x16, 0x00, 0x00, 0x11, 0x11, 0x0A, 0x0A + db 0x04, 0x00, 0x00, 0x11, 0x15, 0x15, 0x15, 0x0A + db 0x00, 0x00, 0x11, 0x0A, 0x04, 0x0A, 0x11, 0x00 + db 0x00, 0x11, 0x11, 0x1E, 0x10, 0x0C, 0x00, 0x00 + db 0x1F, 0x08, 0x04, 0x02, 0x1F, 0x10, 0x08, 0x08 + db 0x04, 0x08, 0x08, 0x10, 0x04, 0x04, 0x04, 0x04 + db 0x04, 0x04, 0x04, 0x04, 0x08, 0x08, 0x10, 0x08 + db 0x08, 0x04, 0x00, 0x02, 0x15, 0x08, 0x00, 0x00 + db 0x00, 0x15, 0x00, 0x15, 0x00, 0x15, 0x00, 0x15 + db 0x00, 0x00, 0x09, 0x15, 0x17, 0x15, 0x09, 0x00 + db 0x00, 0x06, 0x08, 0x0E, 0x09, 0x16, 0x06, 0x01 + db 0x01, 0x06, 0x09, 0x09, 0x06, 0x00, 0x00, 0x09 + db 0x09, 0x09, 0x1F, 0x10, 0x00, 0x00, 0x0E, 0x0A + db 0x0A, 0x1F, 0x11, 0x00, 0x00, 0x0E, 0x11, 0x1F + db 0x01, 0x1E, 0x00, 0x04, 0x0E, 0x15, 0x15, 0x0E + db 0x04, 0x00, 0x00, 0x0F, 0x09, 0x01, 0x01, 0x01 + db 0x00, 0x00, 0x11, 0x0A, 0x04, 0x0A, 0x11, 0x00 + db 0x00, 0x11, 0x19, 0x15, 0x13, 0x11, 0x0A, 0x04 + db 0x11, 0x19, 0x15, 0x13, 0x11, 0x00, 0x00, 0x11 + db 0x09, 0x07, 0x09, 0x11, 0x00, 0x00, 0x1C, 0x12 + db 0x12, 0x12, 0x11, 0x00, 0x00, 0x11, 0x1B, 0x15 + db 0x11, 0x11, 0x00, 0x00, 0x11, 0x11, 0x1F, 0x11 + db 0x11, 0x00, 0x00, 0x0E, 0x11, 0x11, 0x11, 0x0E + db 0x00, 0x00, 0x1F, 0x11, 0x11, 0x11, 0x11, 0x00 + db 0x00, 0x1E, 0x11, 0x1E, 0x14, 0x12, 0x00, 0x00 + db 0x07, 0x09, 0x07, 0x01, 0x01, 0x00, 0x00, 0x0E + db 0x01, 0x01, 0x01, 0x0E, 0x00, 0x00, 0x1F, 0x04 + db 0x04, 0x04, 0x04, 0x00, 0x00, 0x11, 0x11, 0x1E + db 0x10, 0x0E, 0x00, 0x00, 0x15, 0x15, 0x0E, 0x15 + db 0x15, 0x00, 0x00, 0x03, 0x05, 0x07, 0x09, 0x07 + db 0x00, 0x00, 0x01, 0x01, 0x07, 0x09, 0x07, 0x00 + db 0x00, 0x11, 0x11, 0x13, 0x15, 0x13, 0x00, 0x00 + db 0x0E, 0x11, 0x0C, 0x11, 0x0E, 0x00, 0x00, 0x15 + db 0x15, 0x15, 0x15, 0x1F, 0x00, 0x00, 0x07, 0x08 + db 0x0E, 0x08, 0x07, 0x00, 0x00, 0x15, 0x15, 0x15 + db 0x1F, 0x10, 0x00, 0x00, 0x09, 0x09, 0x0E, 0x08 + db 0x08, 0x00, 0x00, 0x06, 0x05, 0x0C, 0x14, 0x0C + +; 32 chars cp=1 (Russian letters) +m_font_matrix_cp2: + db 0x09, 0x15, 0x15, 0x17, 0x15, 0x15, 0x09, 0x04 + db 0x0A, 0x11, 0x11, 0x1F, 0x11, 0x11, 0x1F, 0x11 + db 0x01, 0x0F, 0x11, 0x11, 0x1F, 0x09, 0x09, 0x09 + db 0x09, 0x09, 0x1F, 0x10, 0x0C, 0x0A, 0x0A, 0x0A + db 0x0A, 0x1F, 0x11, 0x1F, 0x01, 0x01, 0x0F, 0x01 + db 0x01, 0x1F, 0x04, 0x0E, 0x15, 0x15, 0x15, 0x0E + db 0x04, 0x1F, 0x11, 0x01, 0x01, 0x01, 0x01, 0x01 + db 0x11, 0x11, 0x0A, 0x04, 0x0A, 0x11, 0x11, 0x11 + db 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x04, 0x15 + db 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x09, 0x05 + db 0x03, 0x05, 0x09, 0x11, 0x1C, 0x12, 0x12, 0x12 + db 0x12, 0x12, 0x11, 0x11, 0x1B, 0x15, 0x15, 0x11 + db 0x11, 0x11, 0x11, 0x11, 0x11, 0x1F, 0x11, 0x11 + db 0x11, 0x0E, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0E + db 0x1F, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x1E + db 0x11, 0x11, 0x11, 0x1E, 0x12, 0x11, 0x0F, 0x11 + db 0x11, 0x11, 0x0F, 0x01, 0x01, 0x0E, 0x11, 0x01 + db 0x01, 0x01, 0x11, 0x0E, 0x1F, 0x04, 0x04, 0x04 + db 0x04, 0x04, 0x04, 0x11, 0x11, 0x11, 0x11, 0x1E + db 0x10, 0x0E, 0x15, 0x15, 0x15, 0x0E, 0x15, 0x15 + db 0x15, 0x0F, 0x11, 0x11, 0x0F, 0x11, 0x11, 0x0F + db 0x01, 0x01, 0x01, 0x0F, 0x11, 0x11, 0x0F, 0x11 + db 0x11, 0x11, 0x13, 0x15, 0x15, 0x13, 0x0E, 0x11 + db 0x10, 0x0C, 0x10, 0x11, 0x0E, 0x15, 0x15, 0x15 + db 0x15, 0x15, 0x15, 0x1F, 0x0E, 0x11, 0x10, 0x1C + db 0x10, 0x11, 0x0E, 0x15, 0x15, 0x15, 0x15, 0x15 + db 0x1F, 0x10, 0x11, 0x11, 0x11, 0x1E, 0x10, 0x10 + db 0x10, 0x1F, 0x15, 0x1F, 0x15, 0x1F, 0x15, 0x1C + +m_print_write: + LD SP, m_font_cp0+28 + ds 24, 0xFF + +m_ramdisk_read: + PUSH HL + PUSH DE + LD A, D + AND 0x1 + OR 0x2 + LD B, A + XOR A + LD A, E + RRA + LD D, A + LD A, 0x0 + RRA + LD E, A +LAB_ram_f3ee: + LD A,B + OUT (SYS_DD17PB), A + LD A, (DE) + LD C, A + XOR A + OUT (SYS_DD17PB), A + LD (HL), C + INC HL + INC DE + LD A, E + ADD A, A + JP NZ, LAB_ram_f3ee + XOR A + OUT (SYS_DD17PB), A + POP DE + POP HL + RET +m_ramdisk_write: + PUSH HL + PUSH DE + LD A, D + AND 0x1 + OR 0x2 + LD B, A + XOR A + LD A, E + RRA + LD D, A + LD A, 0x0 + RRA + LD E, A +LAB_ram_f414: + XOR A + OUT (SYS_DD17PB), A + LD C, (HL) + LD A,B + OUT (SYS_DD17PB), A + LD A, C + LD (DE), A + INC HL + INC DE + LD A, E + ADD A, A + JP NZ, LAB_ram_f414 + XOR A + OUT (SYS_DD17PB), A + POP DE + POP HL + RET + +; ------------------------------------------------------ +; Write block to Tape +; In: DE - block ID, +; HL -> block of data. +; ------------------------------------------------------ +m_tape_write: + PUSH HL + PUSH DE + PUSH DE + LD BC,2550 + LD A,PIC_POLL_MODE ; pool mode + OUT (PIC_DD75RS), A + LD A,TMR0_SQWAVE ; tmr0, load lsb+msb, sq wave, bin + OUT (TMR_DD70CTR), A + LD A, C + OUT (TMR_DD70C1), A + LD A,B + OUT (TMR_DD70C1), A + ; Write Hi+Lo, Hi+Lo + LD DE, 0x4 ; repeat next 4 times +tw_wait_t0_l1: + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; check rst4 from timer#0 + JP NZ,tw_wait_t0_l1 + LD A, D + CPL + LD D, A + OR A + LD A,TL_HIGH ; tape level hi + JP NZ,tw_set_tape_lvl + LD A,TL_LOW ; tape level low +tw_set_tape_lvl: + OUT (DD67PC), A ; set tape level + LD A,TMR0_SQWAVE ; tmr0, load lsb+msb, swq, bin + ; timer on + OUT (TMR_DD70CTR), A + LD A, C + OUT (TMR_DD70C1), A + LD A,B + OUT (TMR_DD70C1), A + DEC E + JP NZ,tw_wait_t0_l1 +tw_wait_t0_l2: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ,tw_wait_t0_l2 + ; Write 00 at start + LD A, 0x0 + CALL m_tape_wr_byte + ; Write 0xF5 marker + LD A, 0xf5 + CALL m_tape_wr_byte + LD E, 0x0 ; checksum=0 + ; Write block ID + POP BC + LD A, C + CALL m_tape_wr_byte + LD A,B + CALL m_tape_wr_byte + ; Write 128 data bytes + LD B,128 +tw_wr_next_byte: + LD A, (HL) + CALL m_tape_wr_byte + INC HL + DEC B + JP NZ,tw_wr_next_byte + ; Write checksum + LD A, E + CALL m_tape_wr_byte + ; Write final zero byte + LD A, 0x0 + CALL m_tape_wr_byte +tw_wait_t0_l3: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ,tw_wait_t0_l3 + LD A,TL_MID ; tape level middle + OUT (DD67PC), A + POP DE + POP HL + RET +; ------------------------------------------------------ +; Write byte to tape +; Inp: A - byte top write +; D - current level +; E - current checksum +; ------------------------------------------------------ +m_tape_wr_byte: + PUSH BC +; calc checksum + LD B, A + LD A, E + SUB B + LD E, A + LD C,8 ; 8 bit in byte +twb_get_bit: + LD A,B + RRA + LD B, A + JP C,twb_bit_hi +twb_wait_t0_l1: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ,twb_wait_t0_l1 + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; program for 360 cycles + LD A, 0x68 + OUT (TMR_DD70C1), A + LD A, 0x1 + OUT (TMR_DD70C1), A + ; change amplitude + LD A, D + CPL + LD D, A + OR A + LD A,TL_HIGH + JP NZ,twb_out_bit_l1 + LD A,TL_LOW +twb_out_bit_l1: + OUT (DD67PC), A + DEC C + JP NZ,twb_get_bit + POP BC + RET +twb_bit_hi: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ,twb_bit_hi + ; program for 660 cycles + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A + LD A, 0x94 + OUT (TMR_DD70C1), A + LD A, 0x2 + OUT (TMR_DD70C1), A + ; change amplitude + LD A, D + CPL + LD D, A + OR A + LD A,TL_HIGH + JP NZ,twb_out_bit_l2 + LD A,TL_LOW +twb_out_bit_l2: + OUT (DD67PC), A + DEC C + JP NZ,twb_get_bit + POP BC + RET + +; ------------------------------------------------------ +; Load block from Tape +; In: HL -> buffer to receive bytes from Tape +; Out: A = 0 - ok, +; 1 - CRC error, +; 2 - unexpected block Id +; 4 - key pressed +; ------------------------------------------------------ +m_tape_read: + PUSH HL + PUSH DE + LD A,PIC_POLL_MODE ; pool mode + OUT (PIC_DD75RS), A + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A ; tmr0, load lsb+msb, sq wave + LD A, 0x0 + ; tmr0 load 0x0000 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + LD C,3 +tr_wait_3_changes: + CALL ccp_read_tape_bit_kbd + INC A + JP Z,tr_key_pressed_l0 + LD A,B + ADD A,4 + JP P,tr_wait_3_changes + DEC C + JP NZ,tr_wait_3_changes +tr_wait_4th_change: + CALL ccp_read_tape_bit_kbd + INC A + JP Z,tr_key_pressed_l0 + LD A,B + ADD A,4 + JP M,tr_wait_4th_change + LD C, 0x0 +tr_wait_f5_marker: + CALL ccp_read_tape_bit_kbd + INC A + JP Z,tr_key_pressed_l0 + DEC A + RRA + LD A, C + RRA + LD C, A + CP 0xf5 + JP NZ,tr_wait_f5_marker + LD E, 0x0 ; checksum = 0 + ; Read blk ID + CALL m_tape_read_byte + JP NC,tr_err_read_id + LD C, D + CALL m_tape_read_byte + JP NC,tr_err_read_id + LD B, D + PUSH BC + ; Read block, 128 bytes + LD C,128 +tr_read_next_b: + CALL m_tape_read_byte + JP NC,tr_err_read_blk + LD (HL), D + INC HL + DEC C + JP NZ,tr_read_next_b + + ; Read checksum + CALL m_tape_read_byte + JP NC,tr_err_read_blk + LD A, E + OR A + JP Z,tr_checksum_ok + LD A, 0x1 ; bad checksum +tr_checksum_ok: + POP BC +tr_return: + POP DE + POP HL + RET +tr_err_read_blk: + POP BC + LD BC, 0x0 +tr_err_read_id: + LD A, 0x2 ; read error + JP tr_return +tr_key_pressed_l0: + CALL tm_con_in + LD C, A ; store key code in C + LD B, 0x0 + LD A, 0x4 + JP tr_return +m_tape_read_byte: + PUSH BC + +; ------------------------------------------------------ +; Read byte from Tape +; Out: D - byte +; CF is set if ok, cleared if error +; ------------------------------------------------------ + LD C,8 +trb_next_bit: + CALL ccp_read_tape_bit + ; push bit from lo to hi in D + RRA + LD A, D + RRA + LD D, A + LD A,4 + ADD A,B + JP NC,trb_ret_err + DEC C + JP NZ,trb_next_bit + ; calc checksum + LD A, D + ADD A, E + LD E, A + SCF +trb_ret_err: + POP BC + RET + +; ------------------------------------------------------ +; Read bit from tape +; Out: A - bit from tape +; B - time from last bit +; ------------------------------------------------------ +ccp_read_tape_bit: + IN A, (KBD_DD78PB) ; Read Tape bit 5 (data) + AND TAPE_P + LD B, A +rtb_wait_change: + IN A, (KBD_DD78PB) + AND TAPE_P + CP B + JP Z,rtb_wait_change + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; [360...480...660] 0x220=544d + IN A, (TMR_DD70C1) ; get tmer#0 lsb + ADD A, 0x20 + IN A, (TMR_DD70C1) ; get tmer#0 msb + LD B, A + ADC A, 0x2 + ; reset timer to 0 + LD A, 0x0 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + ; For 0 - 65535-360+544 -> overflow P/V=1 + ; For 1 - 65535-660+544 -> no overflow P/V=0 + RET P + INC A + RET + +; ------------------------------------------------------ +; Read bit from tape with keyboard interruption +; Out: A - bit from tape +; B - time from last bit +; ------------------------------------------------------ +ccp_read_tape_bit_kbd: + IN A, (KBD_DD78PB) + AND TAPE_P + LD B, A ; save tape bit state + ; wait change with keyboard check +twc_wait_change: + IN A, (PIC_DD75RS) + AND KBD_IRQ + JP NZ,twc_key_pressed + IN A, (KBD_DD78PB) + AND TAPE_P + CP B + JP Z,twc_wait_change + ; measure time + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; read lsb+msb + IN A, (TMR_DD70C1) + ADD A, 0x20 + IN A, (TMR_DD70C1) + LD B, A + ADC A, 0x2 + ; reset timer#0 + LD A, 0x0 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + ; flag P/V is set for 0 + RET P + INC A + RET +twc_key_pressed: + LD A, 0xff + RET + +; ------------------------------------------------------ +; Wait tape block +; Inp: A - periods to wait +; Out: A=4 - interrupded by keyboard, C=key +; ------------------------------------------------------ +m_tape_wait: + OR A + RET Z + PUSH DE + LD B, A +m_wait_t4: + LD C,B + IN A, (KBD_DD78PB) + AND TAPE_P ; Get TAPE4 (Wait det) and save + LD E, A ; store T4 state to E +m_wait_next_2ms: + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A +; load 3072 = 2ms + XOR A + OUT (TMR_DD70C1), A + LD A, 0xc + OUT (TMR_DD70C1), A +m_wait_tmr_key: + IN A, (PIC_DD75RS) + AND KBD_IRQ ; RST1 flag (keyboard) + JP NZ,mt_key_pressed + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; RST4 flag (timer out) + JP Z,m_wait_no_rst4 + IN A, (KBD_DD78PB) + AND TAPE_P ; TAPE4 not changed? + CP E + JP NZ,m_wait_t4 ; continue wait + JP m_wait_tmr_key +m_wait_no_rst4: + DEC C + JP NZ,m_wait_next_2ms + XOR A + POP DE + RET +mt_key_pressed: + CALL tm_con_in + LD C, A ; C = key pressed + LD A, 0x4 ; a=4 interrupted by key + POP DE + RET + +; ------------------------------------------------------ +; Check block marker from Tape +; Out: A=0 - not detected, 0xff - detected +; ------------------------------------------------------ +m_tape_blk_detect: + IN A, (KBD_DD78PB) + AND TAPE_D ; TAPE5 - Pause detector + LD A, 0x0 + RET Z + CPL + RET + +esc_64x23_cursor: + db ASCII_ESC, '6', '1', ASCII_ESC, '8', '0', 0 + +msg_turbo_mon: + db "\f\r\n Turbo MONITOR Ver 1.1 for 13.01.92 (C)Alex Z.\r\n",0 + +m_rst1_handler: + DI + LD (TM_VARS.rst_hl_save), HL + LD HL, 0x2 + ADD HL,SP + LD (TM_VARS.rst_sp_save), HL + POP HL + LD SP, TM_VARS.rst_hl_save + PUSH DE + PUSH BC + PUSH AF + LD (TM_VARS.rst_ret_addr), HL + LD (TM_VARS.tm_hrg), HL + JP tm_main +tm_rst_ret: + LD A, 0xc3 + LD (TM_VARS.rst_ret_JP), A + LD SP, TM_VARS.rst_af_save + POP AF + POP BC + POP DE + POP HL + LD SP, HL + LD HL, (TM_VARS.rst_hl_save) + JP TM_VARS.rst_ret_JP + +m_cold_start: + LD HL, tpa_start + LD (TM_VARS.tm_hrg), HL +tm_main: + LD SP, TM_VARS.tm_stsp + LD DE,esc_64x23_cursor ; FORM61 + CALL tm_print + LD DE, msg_turbo_mon ;= '\f' + CALL tm_out_strz + LD DE, 0x363d ; 54 x '=' + CALL tm_rpt_print + CALL tm_beeep + +tm_mon: + LD DE, 0x300 + CALL tm_screen + CALL tm_lps + LD DE, 0x520 + CALL tm_rpt_print + LD HL, msg_digits ;= "0123456789ABCDEF" + + ; Out '012345789ABCDEF' string +tm_tit: + CALL tm_print_SP + LD C, (HL) + CALL tm_sym_out + INC HL + LD A, (HL) + OR A + JP NZ, tm_tit + LD HL, (TM_VARS.tm_hrg) + LD L, 0x0 +tm_adr: + CALL tm_print_LFCR_hexw + +tm_prh: + LD A, (HL) + CALL tm_hex_b + INC L + LD A,L + AND 0xf + CP 0x0 + JP NZ, tm_prh + LD A, L + SUB 0x10 + LD L, A + CALL tm_print_SP + CALL tm_buk + LD A, L + CP 0x0 + JP NZ, tm_adr + CALL tm_print_LFCR + CALL tm_lpr + LD DE, 0x363d ; 54 x '=' + CALL tm_rpt_print + CALL tm_print_LFCR + LD DE, tm_msg_regs ;= "A,FB,CD,EH,L SP" + LD HL, TM_VARS.rst_af_save + +LAB_ram_f717: + LD B, 0x3 + +LAB_ram_f719: + LD A, (DE) ;= "A,FB,CD,EH,L SP" + LD C, A + CP 0xff + JP Z,tm_out_contacts + CP 0x0 + JP Z, LAB_ram_f744 + CALL tm_sym_out + INC DE + DEC B + JP NZ, LAB_ram_f719 + LD C,'=' + CALL tm_sym_out + INC HL + LD A, (HL) + CALL tm_hex_b + DEC HL + LD A, (HL) + CALL tm_hex_b + INC HL + INC HL + CALL tm_print_SP + JP LAB_ram_f717 +LAB_ram_f744: + INC HL + INC DE + JP LAB_ram_f719 + +tm_msg_regs: + db "A,FB,CD,EH,L SP",0 + db " PC", 0xFF + +tm_out_contacts: + LD DE, m_msg_contacts ;= " (Chernogolovka Mosk.reg. ... + CALL tm_out_strz + LD HL, (TM_VARS.tm_hrg) +tm_kur: + LD DE, 0x405 + LD A, L + AND 0xf0 + RRCA + RRCA + RRCA + RRCA + ADD A, D + LD D, A + LD A, L + AND 0xf + ADD A, A + ADD A, E + LD E, A + CALL tm_screen + LD A, (TM_VARS.tm_tbu) + CP 0x9 + JP Z, tm_tabu + LD B, 0x1 +tm_m2: + CALL tm_con_in + LD C, A + CP 0x3 + JP Z, m_print_log_sep + CALL tm_poke + LD A, B + OR A + JP NZ, tm_m6 + CALL tm_re1 + JP tm_m2 +tm_m6: + LD A, C + CP 0x9 + JP NZ, tm_m7 + LD (TM_VARS.tm_tbu), A + JP tm_kur +tm_tabu: + CALL tm_print_CR + LD E, '&' + LD A, L + AND 0xf + ADD A, E + LD E, A + CALL tm_scr1 +tm_tab: + CALL tm_get_key_ctrl_c + CP ASCII_TAB + JP NZ, tm_m7 + XOR A + LD (TM_VARS.tm_tbu), A + JP tm_kur +tm_m7: + CP 0x8b + JP Z, tm_search + CP 0x9e + JP Z, tm_f1 + CP 0x81 + JP Z, tm_f2 + CP 0x86 + JP Z, tm_f3 + CP 0x92 + JP Z, tm_f4 + CP 0x83 + JP Z, tm_f5 + LD A, (TM_VARS.tm_tbu) + CP 0x9 + LD A, C + JP NZ, tm_m8_monitor + CALL tm_m9 + JP tm_tab +tm_m9: + CP 0x93 + JP Z, tm_leta + CP 0x8 + JP Z, tm_leta + CP 0x84 + JP Z, tm_rgta + CP 0x85 + JP Z, tm_up + CP 0x98 + JP Z, tm_down + AND 0x7f + CP 0x20 + LD (HL), C + JP NC, tm_met1 + LD C, 0x20 + CP ASCII_CR + JP NZ, tm_met1 + CALL tm_sym_out + CALL tm_rigth1 + LD (HL), ASCII_LF + LD C, 0x20 +tm_met1: + CALL tm_sym_out + JP tm_rigth1 +tm_leta: + LD A, L + OR A + RET Z + AND 0xf + JP NZ, tm_left1 + LD C, 0x19 ; EM (End of medium) + CALL tm_sym_out + LD DE, 0x1018 ; 16 x CAN (Cancel) + CALL tm_rpt_print +tm_left1: + DEC L + LD C, 0x8 ; BS (Backspace) + JP tm_sym_out +tm_rgta: + LD C, 0x18 ; CAN + CALL tm_sym_out +tm_rigth1: + INC L + JP Z, tm_left1 +tm_rigth2: + LD A, L + AND 0xf + RET NZ + LD DE, 0x1008 ; 16 x BS + CALL tm_rpt_print + LD C, ASCII_LF + JP tm_sym_out +tm_m8_monitor: + CP ASCII_ESC + JP NZ, tm_m3 + CALL tm_niz + JP tm_rst_ret +tm_m3: + CP ASCII_CR + JP Z, tm_main + CP 0x99 + JP Z, tm_fill + CP 0x7f + JP Z, tm_fill_nxt2 + CP '+' + JP Z, tm_plus + CP '-' + JP Z, tm_minus + CP 'G' + JP NZ, tm_rstr + LD DE, tm_main + PUSH DE + JP (HL) +tm_rstr: + CP 'J' + JP Z, tm_jump + CP 'H' + JP Z, tm_add + CP 'M' + JP Z, tm_move + CP 'R' + JP Z, tm_dsk_read + CP 'W' + JP Z, tm_dsk_write + CP 'T' + JP Z, tm_print_t + CP 'P' + LD (TM_VARS.tm_hrg), HL + JP Z, LAST ; ??? + CP 'p' + JP Z, tm_lprn + CP 0x10 + ; if key 0x10 - turn on duplicate output to printer + JP Z, tm_ltab + CALL tm_met2 + LD (TM_VARS.tm_hrg), HL + JP tm_m2 +tm_met2: + CP 0x93 + JP Z, tm_left + CP 0x8 + JP Z, tm_left + CP 0x84 + JP Z, tm_rght + CP 0x85 + JP Z, tm_up + CP 0x98 + JP Z, tm_down + RET +tm_left: + LD A,B + CP 0x2 + JP Z, tm_le2 + LD A,L + AND 0xf + RET Z +tm_le3: + DEC L + LD B, 0x2 +tm_le1: + LD C, ASCII_BS + JP tm_sym_out +tm_le2: + LD B, 0x1 + JP tm_le1 +tm_rght: + LD C, 0x18 + CALL tm_sym_out + LD A, B + CP 0x1 + LD B, 0x2 + RET Z +tm_re1: + INC L + JP Z, tm_le3 + LD A, L + AND 0xf + LD B, 0x1 + JP Z, tm_print_LFCR_hexw + RET +tm_up: + LD A, L + AND 0xf0 + RET Z + LD A, L + SUB 0x10 + LD L, A + LD C, 0x19 + JP tm_sym_out +tm_down: + LD A, L + ADD A, 0x10 + AND 0xf0 + RET Z + LD A, 0x10 + ADD A, L + LD L, A + LD C, 0xa + JP tm_sym_out + +; ------------------------------------------------------ +; Get nibbles from A and (HL), conver to byte +; put back to (HL), print nibble +; ------------------------------------------------------ +tm_poke: + CP 'G' + RET P + CP '0' + RET M + SUB '0' + CP 10 + JP M, p_is_alpha + SUB 0x7 +p_is_alpha: + PUSH AF + CALL tm_print_hex_nibble + LD A, B + CP 0x2 + JP Z, tm_m5 + LD A, (HL) + AND 0xf + LD B, A + POP AF + RLCA + RLCA + RLCA + RLCA + ADD A, B + LD (HL), A + LD B, 0x2 + RET + +tm_m5: + LD A, (HL) + AND 0xf0 + LD B, A + POP AF + ADD A, B + LD (HL), A + XOR A + LD B, A + RET + +tm_pokh: + CALL tm_pok + DEC HL +tm_pok: + LD B, 0x1 +tm_pk1: + CALL tm_get_key_ctrl_c + CALL tm_poke + LD A, B + OR A + JP NZ, tm_pk1 + RET +tm_buk: + LD A, (HL) + LD C, A + AND 0x7f + CP 0x20 + JP P, tm_m24 + LD C, 0x20 +tm_m24: + CALL tm_sym_out + INC L + LD A, L + AND 0xf + CP 0x0 + JP NZ, tm_buk + RET +m_msg_jump: + db "JAMP\r\n", 0 + +tm_jump: + LD DE, 0x300 + CALL tm_screen + LD DE, m_msg_jump ;= "JAMP\r\n" + CALL tm_print + LD HL, TM_VARS.tm_hrg+1 + CALL tm_pokh + JP tm_mon +m_msg_add: + db "\fADD [", 0 + +tm_add: + LD DE,m_msg_add ;= "\fADD [" + CALL tm_print + LD HL, TM_VARS.tm_strt+1 + CALL tm_pokh + LD C,'+' + CALL tm_sym_out + LD HL, TM_VARS.tm_strt+3 + CALL tm_pokh + LD C,'=' + CALL tm_sym_out + LD HL, (TM_VARS.tm_strt) + EX DE, HL + LD HL, (TM_VARS.tm_strt+2) + ADD HL, DE + CALL tm_hex_hl + CALL tm_con_in + JP tm_main + +m_msg_move: + db "\fMOVE }", 0 + +tm_move: + LD DE,m_msg_move ;= "\fMOVE }" + CALL tm_print + LD HL, TM_VARS.tm_strt+1 + CALL tm_pokh + LD C,'-' + CALL tm_sym_out + LD HL, TM_VARS.tm_strt+3 + CALL tm_pokh + LD C,'=' + CALL tm_sym_out + LD HL, TM_VARS.tm_strt+5 + CALL tm_pokh + LD HL, (TM_VARS.tm_strt) + LD B,H + LD C,L + LD HL, (TM_VARS.tm_strt+2) + LD D,H + LD E,L + INC DE + LD HL, (TM_VARS.tm_strt+4) + +tm_mov_nxt: + LD A, (BC) + LD (HL), A + INC BC + INC HL + LD A, C + CP E + JP NZ, tm_mov_nxt + LD A, B + CP D + JP NZ, tm_mov_nxt + JP tm_main +tm_dsk_read: + LD DE, m_msg_read ;= "Read/" + JP tm_ra4 +tm_dsk_write: + LD DE, m_msg_write ;= "Write/" +tm_ra4: + LD (TM_VARS.tm_rw_disk), A + CALL tm_print_verh + CALL tm_print +tm_ra5: + CALL tm_get_key_ctrl_c + CP 'A' + JP C, tm_ra5 + CP 'F' + JP NC, tm_ra5 + LD (TM_VARS.tm_drive), A + CALL tm_sym_out + LD C, ':' + CALL tm_sym_out + LD A, (TM_VARS.tm_drive) + SUB 65 + LD (TM_VARS.tm_drive), A + JP NZ, tm_disk + LD DE, tm_msg_0123 ;= "0123 ?" + CALL tm_print +tm_rrr: + CALL tm_get_key_ctrl_c + SUB 48 + CP 4 + JP NC, tm_rrr + LD (TM_VARS.tm_strt+15), A + JP tm_main +tm_beeep: + LD BC, 0x6060 +tm_bell_next_p: + LD A,BELL_PIN + OUT (DD67PC), A ; BELL=1 + LD A, C +tm_bell_w1: + DEC A + JP NZ, tm_bell_w1 + OUT (DD67PC), A ; BELL 0 + LD A, C +tm_bell_w2: + DEC A + JP NZ, tm_bell_w2 + DEC B + JP NZ, tm_bell_next_p + RET +tm_msg_0123: + db "0123 ?", 0 + +tm_disk: + LD DE, m_msg_track ;= "/Track-" + CALL tm_print + CALL tm_des_dv + LD (TM_VARS.tm_track_no), A + LD DE, tm_sector ;= "/Sekt-" + CALL tm_print + CALL tm_des_dv + LD (TM_VARS.tm_sector_no), A + LD DE, m_msg_num ;= "/N-" + CALL tm_print + CALL tm_des_dv + LD (TM_VARS.tm_num_sect), A + LD DE, m_msg_io ;= "/(I/O)-" + CALL tm_print +tm_disk_op_unk: + CALL tm_get_key_ctrl_c + CP 'I' + JP Z, tm_disk_inp + CP 'O' + JP NZ, tm_disk_op_unk +tm_disk_inp: + LD (TM_VARS.tm_disk_op), A + CALL tm_sym_out + CALL tm_rd_wr_disk + JP tm_cont +tm_rd_wr_disk: + CALL tm_niz +tm_rd: + CALL tm_print_CR + LD A, (TM_VARS.tm_track_no) + LD D, A + LD A, (TM_VARS.tm_sector_no) + LD E, A + LD A, (TM_VARS.tm_disk_op) + CP 'O' + CALL Z, tm_sect_map + LD A, H + CP 0xac + JP NC, tm_error + LD BC, 0x84 + LD A, (TM_VARS.tm_rw_disk) + CP 'W' + LD A, (TM_VARS.tm_drive) + JP NZ, tm_d3 + LD C, 0xa4 + CALL m_write_floppy + DEC L + JP tm_d4 +tm_d3: + CALL m_read_floppy +tm_d4: + CP 0x0 + JP NZ, tm_error + LD A, (TM_VARS.tm_track_no) + LD D, A + LD A, (TM_VARS.tm_sector_no) + INC A + CP 10 + JP C, tm_wf_nx_trk + INC D + LD A, D + LD (TM_VARS.tm_track_no), A + LD A, 0x1 +tm_wf_nx_trk: + LD (TM_VARS.tm_sector_no), A + LD E, A + CALL tm_print_CR_hexw + CALL tm_dv_des + LD A, (TM_VARS.tm_num_sect) + DEC A + LD (TM_VARS.tm_num_sect), A + JP NZ, tm_rd + RET +tm_error: + PUSH AF + LD DE, m_msg_disk_error ;= "Disk Error - " + CALL tm_print + POP AF + CALL tm_hex_b + LD BC, 0x70ff + CALL tm_bell_next_p + LD DE, m_msg_track ;= "/Track-" + CALL tm_print + LD A, (TM_VARS.tm_track_no) + CALL tm_dva + LD DE, tm_sector ;= "/Sekt-" + CALL tm_print + LD A, (TM_VARS.tm_sector_no) + CALL tm_dva + LD DE, m_msg_retr_abrt ;= "Retry, Abort -?" + CALL tm_print_w_key + CP 'A' + JP Z, tm_main + JP tm_rd_wr_disk +tm_dv_des: + CALL tm_dv1 + LD A, E + +; ------------------------------------------------------ +; Convert to BCD and print? +; ------------------------------------------------------ +tm_dva: + LD D, A +tm_dv1: + LD C, 0 + LD B, 8 +tm_dv2: + LD A, D + RLCA + LD D, A + LD A, C + ADC A, C + DAA + LD C, A + DEC B + JP NZ, tm_dv2 + +OFF_ram_fb76: + JP tm_hex_b + +tm_sec_map_t: + db 1, 8, 6, 4, 2, 9, 7, 5, 3 + +; ------------------------------------------------------ +; Map sectors +; Inp: E - sector +; Out: E - sector +; ------------------------------------------------------ +tm_sect_map: + LD BC, tm_sec_map_t-1 + LD A, E + ADD A, C + LD C, A + JP NC, tm_tbl_noc + INC B +tm_tbl_noc: + LD A, (BC) + LD E, A + RET +tm_des_dv: + CALL SUB_ram_fb9f + RLCA + RLCA + RLCA + LD B, A + RRCA + RRCA + ADD A,B + LD B, A + CALL SUB_ram_fb9f + ADD A,B + RET +SUB_ram_fb9f: + CALL tm_get_key_ctrl_c + SUB 0x30 + JP M,SUB_ram_fb9f + CP 0xa + JP P,SUB_ram_fb9f + PUSH AF + CALL tm_sym_out + POP AF + RET + +; ------------------------------------------------------ +; Read data from floppy +; Inp: A = 0..4 - select drives +; HL -> buffer +; C - command (0x84) READ_SEC, single, 15ms delay +; Out: A=0 if ok +; CF is set if error +; ------------------------------------------------------ +m_read_floppy: + CALL m_select_drive + CALL m_start_floppy + RET C + CALL m_fdc_seek_trk + RET C + CALL m_fdc_read_c_bytes + RET C + XOR A + RET + +; ------------------------------------------------------ +; Write data to floppy +; Inp: A = 0..4 - select drives +; HL -> buffer +; C - command (0xA4) WRITE_SEC, single, 15ms delay +; Out: A=0 if ok +; CF is set if error +; ------------------------------------------------------ +m_write_floppy: + CALL m_select_drive + CALL m_start_floppy + RET C + CALL m_fdc_seek_trk + RET C + CALL m_fdc_write_bytes + RET C + XOR A + RET + +; ------------------------------------------------------ +; Select or disable drive +; Inp: A = 0 - disable drives +; A = 1 - select + drsel + motor0 en +; A = 2 - select + motor0 enanle +; A = 3 - select +; A = 4 - select + drsel +; ------------------------------------------------------ +m_select_drive: + PUSH BC + LD B, 00000111b ; DRSEL, DSEL1, DSEL0 + CP 0x1 + JP Z, mal_out_to_flop + LD B, 00100111b ; MOT0_EN, DRSEL, DSEL1, DSEL0 + CP 0x2 + JP Z, mal_out_to_flop + LD B, 00000011b ; DSEL1, DSEL0 + CP 0x3 + JP Z, mal_out_to_flop + LD B, 00100011b ; MOT0_EN, DSEL1, DSEL0 + CP 0x4 + JP Z, mal_out_to_flop + LD B, 00000000b ; Turn off and deselect drives +mal_out_to_flop: + LD A, B + OUT (FLOPPY), A + POP BC + RET + +; ------------------------------------------------------ +; Start floppy +; Out: +; CF is set, A=0x20 if INTRQ +; CF not set, A=0x00 if READY +; ------------------------------------------------------ +m_start_floppy: + IN A, (FLOPPY) ; Get floppy ctrl state + RLCA + JP C, .start_motor + IN A, (FDC_CMD) + AND FDC_NOT_READY + RET Z + +.start_motor: + PUSH BC + LD BC, 64000 ; timeout + CALL m_fdc_set_init + +.wait_mot_start: + IN A, (FDC_CMD) + AND FDC_NOT_READY + JP Z, .delay_for_spin_up + IN A, (FLOPPY) + ; Check motor start bit + RLCA + JP NC, .wait_mot_start + ; Time is out or not started + LD A, 0x20 + JP .ok_exit + ; Delay for spindle spin-up +.delay_for_spin_up: + DEC C + JP NZ, .delay_for_spin_up + DEC B + JP NZ, .delay_for_spin_up + XOR A +.ok_exit: + POP BC + RET + +; ------------------------------------------------------ +; Send INIT to FDC +; ------------------------------------------------------ +m_fdc_set_init: + IN A, (FLOPPY) + AND 01001110b ; Read SSEL, DDEN, MOT1, MOT0 + RRA + OUT (FLOPPY), A ; SSEL DRSEL MOT1 MOT0 + OR 00001000b ; INIT + OUT (FLOPPY), A + RET + +; ------------------------------------------------------ +; Seek track on floppy +; Inp: DE - track/sector +; ------------------------------------------------------ +m_fdc_seek_trk: + PUSH BC + LD B, 0x2 ; try 2 times if error +fs_seek_again: + LD A, D + OUT (FDC_DATA), A ; Set track to search + LD A,FDC_SEEK_LV ; Seek, Load Head, Verify on dst track + OUT (FDC_CMD), A + NOP + NOP + IN A, (FDC_WAIT) + IN A, (FDC_CMD) + AND 00011001b ; SEEK error, CRC error, BUSY flags + CP 0x0 + JP Z, fs_seek_ok + LD A, 0x20 + SCF ; set erro flag + DEC B + JP Z, fs_seek_ok + LD A, FDC_RESTORE_L ; restore with load head + OUT (FDC_CMD), A + NOP + NOP + IN A, (FDC_WAIT) + JP fs_seek_again +fs_seek_ok: + PUSH AF + LD A, E + OUT (FDC_SECT), A + POP AF + POP BC + RET + +; ------------------------------------------------------ +; Write bytes to FDC +; Inp: C - count of bytes +; HL -> buffer +; Out: CF set if error, +; C - error code if CF is set +; ------------------------------------------------------ +m_fdc_write_bytes: + LD A, C + OUT (FDC_CMD), A +fw_next_byte: + IN A, (FDC_WAIT) + RRCA + LD A, (HL) + OUT (FDC_DATA), A + INC HL + JP C,fw_next_byte + JP m_floppy_chk_error + +; ------------------------------------------------------ +; Read bytes from FDC +; Inp: C - command code for VG93 +; HL -> buffer +; Out: CF set if error, +; C - error code if CF is set +; ------------------------------------------------------ +m_fdc_read_c_bytes: + LD A, C + OUT (FDC_CMD), A + JP .skip_first_inc +.read_next_byte: + LD (HL), A + INC HL +.skip_first_inc: + IN A, (FDC_WAIT) + RRCA + IN A, (FDC_DATA) + JP C, .read_next_byte + +m_floppy_chk_error: + IN A, (FDC_CMD) + AND 11011111b ; mask 5th bit Write fault... ??? + CP 0x0 + RET Z ; retutn in no errors + IN A, (FDC_CMD) + LD C, A + SCF + RET + +m_msg_disk_error: + db "Disk Error - ", 0 + +m_msg_retr_abrt: + db "Retry, Abort -?", 0 + +m_msg_read: + db "Read/", 0 + +m_msg_write: + db "Write/", 0 + +m_msg_track: + db "/Track-", 0 + +tm_sector: + db "/Sekt-", 0 + +m_msg_num: + db "/N-", 0 + +m_msg_b_ok: + db " {OK}", 0 + +m_msg_io: + db "/(I/O)-", 0 + +esc_cmd_kod: + db ASCII_ESC, '@', ASCII_ESC, 'R', 3, ESC_CMD_END + +tm_fill: + LD C, (HL) + LD A, 0xb0 +.fill_nxt1: + LD (HL), C + INC HL + CP H + JP NZ, .fill_nxt1 + JP tm_mon +tm_fill_nxt2: + LD C, (HL) +.fill_nxt3: + LD (HL), C + INC L + JP NZ, .fill_nxt3 + JP tm_mon + EX DE, HL + CALL tm_hex_hl + EX DE, HL + RET + +; ------------------------------------------------------ +; Print word as hex +; Inp: HL - value to print +; ------------------------------------------------------ +tm_hex_hl: + LD A, H + CALL tm_hex_b + LD A, L + +; ------------------------------------------------------ +; Print byte in HEX +; Inp: A - Byte to print +; ------------------------------------------------------ +tm_hex_b: + PUSH AF + AND 0xf0 + RRCA + RRCA + RRCA + RRCA + CALL tm_print_hex_nibble + POP AF + PUSH AF + AND 0xf + CALL tm_print_hex_nibble + POP AF + RET + +tm_print_hex_nibble: + PUSH DE + LD DE,msg_digits ;= "0123456789ABCDEF" + ADD A, E + JP NC, .no_cf + INC D +.no_cf: + LD E, A + LD A, (DE) + LD C, A + CALL tm_sym_out + POP DE + RET + +msg_digits: + db "0123456789ABCDEF", 0 + +tm_print_LFCR_hexw: + LD C, ASCII_LF + CALL tm_sym_out + +tm_print_CR_hexw: + CALL tm_print_CR + CALL tm_hex_hl + +tm_print_SP: + LD C, ' ' + JP tm_sym_out + +tm_print_LFCR: + LD C, ASCII_LF + CALL tm_sym_out + +tm_print_CR: + LD C, ASCII_CR + JP tm_sym_out + +; ------------------------------------------------------ +; Get key from keyboard. Return to monitor +; if Ctrl+C pressed +; Out: C=A - key +; ------------------------------------------------------ +tm_get_key_ctrl_c: + CALL tm_con_in + LD C, A + CP 0x3 + JP Z, tm_main + RET + +; TYPE +tm_print_t: + LD C, ASCII_US + CALL tm_sym_out + EX DE, HL + CALL tm_print +tm_cont: + LD DE, m_msg_b_ok ;= " {OK}" + CALL tm_print_w_key + JP tm_main + +; ------------------------------------------------------ +; Print message and wait key +; Ctrl+C to cansel current op and +; return to monitor +; Inp: DE -> strz +; Out: A - key +; ------------------------------------------------------ +tm_print_w_key: + CALL tm_out_strz + JP tm_get_key_ctrl_c + +tm_out_strz: + CALL tm_print_LFCR +tm_print: + LD B,16 +p11_print_next: + LD A, (DE) + OR A + RET Z + CP ASCII_CR + JP NZ, p11_no_CR + DEC B + JP NZ, p11_no_CR + CALL tm_get_key_ctrl_c + LD B, 16 + LD A, (DE) +p11_no_CR: + LD C, A + CALL tm_sym_out + INC DE + JP p11_print_next + +; ------------------------------------------------------ +; Out symbol +; Inp: C - symbol +; ------------------------------------------------------ +tm_sym_out: + LD A, C + AND 0x80 + JP Z, tm_rus + LD A, 0x1 + +tm_rus: + LD (TM_VARS.m_codepage), A + CALL m_con_out + LD A, (TM_VARS.tm_ltb+1) ; if 0x10, return, no out to printer; + CP 0x10 + RET NZ + JP tm_char_print + +; ------------------------------------------------------ +; Print FS (FileSeparator) +; ------------------------------------------------------ +tm_print_verh: + LD C, 0xc + JP tm_sym_out +tm_screen: + CALL tm_print_verh + LD A, D + OR A +tm_scr0: + JP Z,tm_scr1 + LD C, ASCII_LF + CALL tm_sym_out + DEC D + JP tm_scr0 + +; ------------------------------------------------------ +; Print CAN symbol E times +; ------------------------------------------------------ +tm_scr1: + LD A, E + OR A + RET Z + LD C, ASCII_CAN ; CAN (Cancel) + CALL tm_sym_out + DEC E + JP tm_scr1 + +tm_niz: + LD DE, 0x1500 ; 21 x 0 + CALL tm_screen + LD DE, 0x7f20 ; 126 x ' ' + CALL tm_rpt_print + LD DE, 0x1500 ; 21 x 0 + JP tm_screen + +; ------------------------------------------------------ +; Print the character the specified number of times +; Inp: E - character +; D - count +; ------------------------------------------------------ +tm_rpt_print: + LD C, E ; DE=363D +rpt_next: + CALL tm_sym_out + DEC D + RET Z + JP rpt_next + +; Turn on duplicate output to printer +tm_ltab: + LD A,10h + LD (TM_VARS.tm_ltb), A + JP tm_mon + +tm_lps: + LD A, (TM_VARS.tm_ltb) + CP 0x10 + RET NZ + LD (TM_VARS.tm_ltb+1), A + LD DE,esc_cmd_kod ;= 1Bh + JP tm_lprint + +tm_lpr: + XOR A + LD (TM_VARS.tm_ltb), A + LD (TM_VARS.tm_ltb+1), A + RET + +tm_lprn: + EX DE, HL + CALL tm_lprint + JP tm_mon + +; ------------------------------------------------------ +; Print string until SUB symbol +; Inp: DE -> string ended with SUB (0x1A) +; ------------------------------------------------------ +tm_lprint: + LD A, (DE) + LD C, A + CP ASCII_SUB + RET Z + CALL tm_char_print + INC DE + JP tm_lprint + +; ------------------------------------------------------ +; Send character to printer +; Inp: C - character +; ------------------------------------------------------ +tm_char_print: + IN A, (PIC_DD75RS) + AND PRINTER_IRQ + JP Z, tm_char_print ; Wait printer ready +cp_wait_ack: + IN A, (KBD_DD78PB) + AND PRINTER_ACK + JP NZ, cp_wait_ack + LD A, C + CPL + OUT (LPT_DD67PA), A + LD A, 00001001b ; set Printer Strobe (port C 4th bit) + OUT (DD67CTR), A + LD A, 00001000b ; reset Printer Strobe + OUT (DD67CTR), A + RET + +; ------------------------------------------------------ +; Wait and read data from UART +; Out: A - 7 bit data +; ------------------------------------------------------ +m_serial_in: + IN A, (UART_DD72RR) + AND RX_READY + JP Z, m_serial_in ; wait for rx data ready + IN A, (UART_DD72RD) + AND 0x7f ; leave 7 bits + RET + +; ------------------------------------------------------ +; Send data by UART +; Inp: C - data to transmitt +; ------------------------------------------------------ +m_serial_out: + IN A, (UART_DD72RR) + AND TX_READY + JP Z, m_serial_out ; Wait for TX ready + LD A, C + OUT (UART_DD72RD), A + RET +tm_plus: + LD HL, (TM_VARS.tm_hrg) + INC H + JP tm_ff +tm_minus: + LD HL, (TM_VARS.tm_hrg) + DEC H + JP tm_ff +tm_f1: + LD H, 0x1 + JP tm_ff +tm_f2: + LD H, 0x40 + JP tm_ff +tm_f3: + LD H, 0xb0 + JP tm_ff +tm_ff: + XOR A + LD L, A + LD (TM_VARS.tm_hrg), HL + JP tm_mon +tm_f4: + LD A,H + ADD A, 0x10 + JP tm_fa +tm_f5: + LD A,H + SUB 0x10 +tm_fa: + LD H, A + JP tm_ff + +tm_msg_search: + db "\fSEARCH [", 0 + +tm_search: + LD (TM_VARS.tm_hrg), HL +tm_search0: + LD DE, tm_msg_search ;= "\fSEARCH [" + CALL tm_print + LD HL, TM_VARS.tm_stack +tm_s0: + LD B, 0x1 +tm_s1: + CALL tm_get_key_ctrl_c + CP ASCII_BS + JP Z, tm_search0 + CP ASCII_CR + JP Z, tm_do_search + CP '*' + JP Z, tm_s4 + LD A, (TM_VARS.tm_tbu) + CP ASCII_TAB + JP NZ, tm_s2 +tm_s4: + LD (HL), C + CALL tm_sym_out + JP tm_s5 +tm_s2: + LD A, C + CALL tm_poke + LD A, B + OR A + JP NZ, tm_s1 +tm_s5: + INC L + JP tm_s0 + +tm_do_search: + LD B,L + LD D,H + XOR A + LD E, A + LD HL, (TM_VARS.tm_hrg) + INC HL + ADD A,B + JP Z, tm_sea1 + LD (TM_VARS.tm_stack+16), A +tm_sea1: + LD A, (DE) + CP (HL) + JP NZ, tm_s3 +tm_s6: + DEC B + JP Z, tm_aga + INC E +tm_sea2: + INC L + JP NZ, tm_sea1 + INC H + JP NZ, tm_sea1 + JP tm_main +tm_s3: + LD A, (DE) + CP '*' + JP Z, tm_s6 + LD A, (TM_VARS.tm_stack+16) + LD B, A + LD E, 0x0 + JP tm_sea2 + +tm_aga: + LD A, (TM_VARS.tm_stack+16) + +tm_ogo: + DEC A + JP Z, tm_rets + DEC HL + JP tm_ogo + +tm_rets: + LD (TM_VARS.tm_hrg), HL + JP tm_main + +m_print_log_sep: + LD C, ASCII_US + CALL tm_sym_out + JP warm_boot + +m_msg_contacts: + db " (Chernogolovka Mosk.reg. Tel 51-24)", 0 + +LAST EQU $ +CODE_SIZE EQU LAST-0xE000 +FILL_SIZE EQU 8192-CODE_SIZE + + DISPLAY "Code size is: ",/A,CODE_SIZE + +FILLER + DS FILL_SIZE, 0xFF + DISPLAY "Filler size is: ",/A,FILL_SIZE + + ENDMODULE + + OUTEND + + INCLUDE "tm_vars.inc" diff --git a/MON_r6_291f2b76/io.inc b/MON_r6_291f2b76/io.inc index 2a401a7..0eb915a 100644 --- a/MON_r6_291f2b76/io.inc +++ b/MON_r6_291f2b76/io.inc @@ -41,7 +41,7 @@ FDC_SECT EQU 0x22 FDC_DATA EQU 0x23 ; -FDC_WAIT EQU 0x24 +FDC_DRQ EQU 0x24 ; Controller port FLOPPY EQU 0x25 @@ -85,8 +85,8 @@ TMR_DD70C3 EQU 0x62 TMR_DD70CTR EQU 0x63 ; Programable Interrupt controller PIC KR580VV59 -PIC_DD75RS EQU 0x80 -PIC_DD75RM EQU 0x81 +PIC_DD75A EQU 0x80 +PIC_DD75B EQU 0x81 ; ------------------------------------------------------- ; КР580ВВ51 DD72 diff --git a/MON_r6_291f2b76/m_vars.inc b/MON_r6_291f2b76/m_vars.inc index 74281bd..4aa099f 100644 --- a/MON_r6_291f2b76/m_vars.inc +++ b/MON_r6_291f2b76/m_vars.inc @@ -59,6 +59,7 @@ esc_param: DS 10 ; bfe2 screen_mode: DS 1 ; bfec +cursor_pos: ; as word cursor_row: DS 1 ; bfed cursor_col: @@ -81,7 +82,7 @@ strobe_state: DS 1 ; bff9 ul_var0: DS 1 ; bffa -ul_var1: +head_loaded: DS 1 ; bffb ul_var2: DS 1 ; bffc diff --git a/MON_r6_291f2b76/monitor.asm b/MON_r6_291f2b76/monitor.asm index 97904ac..ded716b 100644 --- a/MON_r6_291f2b76/monitor.asm +++ b/MON_r6_291f2b76/monitor.asm @@ -15,6 +15,8 @@ OUTPUT mon_E000.bin + DEFINE CHECK_INTEGRITY + MODULE MONITOR ORG 0xe000 @@ -121,17 +123,27 @@ conf_uart: XOR A OUT (TMR_DD70C2), A conf_pic: + ; ---------------------------------------------- ; Config PIC - LD A,00010010b ; ICW1 edge trigger, interval 8, sin... - OUT (PIC_DD75RS), A + ; ---------------------------------------------- + ; Send Init Control Words + ; ICW1 0x12 - Low ISR address A7:A5 = 000b, + ; ISR Interval 8 byte, Single controller + LD A,00010010b + OUT (PIC_DD75A), A + ; ICW2 = 0x00 Hi ISR address XOR A - OUT (PIC_DD75RM), A ; ICW2 + OUT (PIC_DD75B), A + // No ICW3 in single mode + // OCW1 = 0xff , bits [7:0] - Mask 1-Set, 0-Reset CPL - OUT (PIC_DD75RM), A ; ICW3 no slave + OUT (PIC_DD75B), A + // OCWZ = 0x20 Non-specific EOI command - reset highest ISR bit LD A,00100000b - OUT (PIC_DD75RS), A ; Non-specific EOI command, End of I... - LD A, PIC_POLL_MODE - OUT (PIC_DD75RS), A ; Poll mode, poll on next RD + OUT (PIC_DD75A), A + // OCW3 Polled mode read IRR + LD A, PIC_POLL_MODE ; 0000-1010 P=1 - poll mode, RR=1+RIS=0 -> read IRR on next RD + OUT (PIC_DD75A), A ; Poll mode, poll on next RD ; Config KBD LD A, 0x80 OUT (KBD_DD78PC), A ; TODO: - Check using this 7th bit @@ -187,7 +199,7 @@ msg_hw_mon: ; --------------------------------------------------- reset_m_stack: - LD HL, M_VARS.stor_e + LD HL, M_VARS.stor_de LD SP, HL CALL get_cmd_letter INC HL @@ -196,13 +208,13 @@ reset_m_stack: ; Monitor entry point ; --------------------------------------------------- m_cold_start: - LD HL, M_VARS.stor_e + LD HL, M_VARS.stor_de LD SP, HL DI CALL get_a_ref_sp CALL get_cmd_letter LD L, 205 - DB 0xdd + DB 0xdd ; 0x13 INC DE in previous r5 version PUSH AF CP ASCII_CR JP Z, m_cold_start @@ -484,7 +496,7 @@ registers_tab: ; A = 0xFF - ready (key pressed) ; ------------------------------------------------------ m_con_status: - IN A, (PIC_DD75RS) ; Read PIC status + IN A, (PIC_DD75A) ; Read PIC status NOP AND KBD_IRQ ; Check keyboard request RST1 LD A, 0 @@ -572,7 +584,7 @@ get_cmd_letter: ; ------------------------------------------------------ m_char_print: ; wait printer ready - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND PRINTER_IRQ JP Z, m_char_print @@ -585,7 +597,7 @@ m_char_print: .wait_lp: ; wait printer ack - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND PRINTER_IRQ JP NZ, .wait_lp ; remove LP strobe @@ -1471,41 +1483,42 @@ m2_lf: ; Access to VRAM LD A, 0x1 OUT (SYS_DD17PB), A - -.cas_l5: + ; Scroll one line 8 px +scroll_nxt_y: LD B, 0x40 LD H, 0x40 ; TODO: LD H, B save 1b 3t LD D, H -.cas_l6: +scroll_nxt_x: LD A, (DE) LD (HL), A INC H INC D DEC B - JP NZ, .cas_l6 + JP NZ, scroll_nxt_x INC L INC E DEC C - JP NZ, .cas_l5 + JP NZ, scroll_nxt_y + ; correct row shift value LD C, 11 LD A, (M_VARS.row_shift) ADD A, 8 LD E, A - -.cas_l7: + ; clear new line +clr_nxt_y: LD B, 0x40 LD D, 0x40 ; TODO: LD D, B save 1b 3t XOR A -.cas_l8: +clr_nxt_x: LD (DE), A INC D DEC B - JP NZ, .cas_l8 + JP NZ, clr_nxt_x INC E DEC C - JP NZ, .cas_l7 + JP NZ, clr_nxt_y LD A, 0 OUT (SYS_DD17PB), A RET @@ -1998,6 +2011,7 @@ m_clear_screen: LD A, 0x0 JP NZ, .mono_mode LD A, 01000000b + .mono_mode: OR B ; Restore mode and palette @@ -2538,7 +2552,7 @@ m_bell_cont: LD B, A OUT (DD67PC), A ; Invert bell pin m_bell_wait_tmr1: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ ; 0x10 JP NZ, m_bell_wait_tmr1 LD A, B @@ -2546,7 +2560,7 @@ m_bell_wait_tmr1: LD B, A OUT (DD67PC), A m_bell_wait_tmr2: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ JP Z,m_bell_wait_tmr2 JP m_bell_cont @@ -4167,7 +4181,7 @@ m_tape_write: PUSH DE LD BC, 2550 LD A, PIC_POLL_MODE ; pool mode - OUT (PIC_DD75RS), A + OUT (PIC_DD75A), A LD A,TMR0_SQWAVE ; tmr0, load lsb+msb, sq wave, bin OUT (TMR_DD70CTR), A LD A, C @@ -4177,7 +4191,7 @@ m_tape_write: ; Write Hi+Lo, Hi+Lo LD DE, 4 ; repeat next 4 times .l1: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ ; check rst4 from timer#0 JP NZ, .l1 LD A, D @@ -4200,7 +4214,7 @@ m_tape_write: JP NZ, .l1 .l2: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ JP NZ, .l2 @@ -4232,7 +4246,7 @@ m_tape_write: LD A, 0x0 CALL m_tape_wr_byte .wait_end: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ JP NZ, .wait_end LD A, TL_MID ; tape level middle @@ -4262,7 +4276,7 @@ m_tape_wr_byte: LD B, A JP C, .bit_hi .wait_t: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ JP NZ, .wait_t LD A, TMR0_SQWAVE @@ -4287,7 +4301,7 @@ m_tape_wr_byte: POP BC RET .bit_hi: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ JP NZ, .bit_hi ; program for 660 cycles @@ -4324,7 +4338,7 @@ m_tape_read: PUSH HL PUSH DE LD A, PIC_POLL_MODE ; pool mode - OUT (PIC_DD75RS), A + OUT (PIC_DD75A), A LD A, TMR0_SQWAVE OUT (TMR_DD70CTR), A ; tmr0, load lsb+msb, sq wave LD A, 0x0 @@ -4478,7 +4492,7 @@ read_tape_bit_kbd: LD B, A ; save tape bit state ; wait change with keyboard check .wait_change: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND KBD_IRQ JP NZ, .key_pressed IN A, (KBD_DD78PB) @@ -4530,10 +4544,10 @@ m_tape_wait: LD A, 0xc OUT (TMR_DD70C1), A .wait_tmr_key: - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND KBD_IRQ ; RST1 flag (keyboard) JP NZ, .key_pressed - IN A, (PIC_DD75RS) + IN A, (PIC_DD75A) AND TIMER_IRQ ; RST4 flag (timer out) JP Z, .wait_no_rst4 IN A, (KBD_DD78PB) @@ -4570,26 +4584,26 @@ m_tape_blk_detect: ; ====================================================== ; FDC DRIVER ; ====================================================== -fdc_unload_head: +fdc_load_head: LD A,0x0 OUT (FDC_DATA),A LD A,0x3 OUT (FDC_CMD),A NOP NOP -fuh.wait_no_busy: +.wait_no_busy: IN A,(FDC_CMD) AND 0x5 ; TR0. BYSY CP 0x4 ; - JP Z,fuh.tr0_ok + JP Z, .tr0_ok IN A,(FLOPPY) RLCA ; MOT_ST -> CF - JP NC,fuh.wait_no_busy - LD A,0x20 + JP NC, .wait_no_busy + LD A, 0x20 RET -fuh.tr0_ok: - LD A,0x1 - LD (M_VARS.ul_var1),A +.tr0_ok: + LD A, 1 + LD (M_VARS.head_loaded), A XOR A RET @@ -4746,36 +4760,39 @@ fdc_init: ; Inp: DE - track/sector ; --------------------------------------------------- m_fdc_seek_trk: - LD A, (M_VARS.ul_var1) + ; check and load head + LD A, (M_VARS.head_loaded) AND 0x1 - CALL Z, fdc_unload_head + CALL Z, fdc_load_head + ; send track no to data register LD A, D OUT (FDC_DATA), A + ; send seek track command LD A, 0x1f OUT (FDC_CMD), A NOP NOP - IN A, (FDC_WAIT) + IN A, (FDC_DRQ) IN A, (FDC_CMD) - AND ASCII_EM - CP 0x0 - JP NZ, .l1 - JP .l2 -.l1: + AND 00011001b ; Seek Error, CRC Error, Busy + CP 0 + JP NZ, .seek_sec_err + JP .seek_sec_ok +.seek_sec_err: LD A, D OUT (FDC_DATA), A LD A, 0x2f OUT (FDC_CMD), A NOP NOP - IN A, (FDC_WAIT) + IN A, (FDC_DRQ) IN A, (FDC_CMD) - AND ASCII_EM + AND 00011001b CP 0x0 - JP Z, .l2 + JP Z, .seek_sec_ok SCF LD A, 0x40 -.l2: +.seek_sec_ok: PUSH AF LD A, E OUT (FDC_SECT), A @@ -4789,7 +4806,7 @@ m_fdc_write_bytes: LD A, C OUT (FDC_CMD), A .w_next: - IN A, (FDC_WAIT) + IN A, (FDC_DRQ) RRCA LD A, (HL) OUT (FDC_DATA), A @@ -4799,7 +4816,11 @@ m_fdc_write_bytes: RET ; --------------------------------------------------- -; +; Read byte(s) to [HL] until DRQ is set +; Inp: C - FDC read command +; HL -> to buffer +; Out: CF set if error +; A - error code if CF set ; --------------------------------------------------- m_fdc_read_c_bytes: LD A, C @@ -4809,8 +4830,8 @@ m_fdc_read_c_bytes: LD (HL), A INC HL .l2: - IN A, (FDC_WAIT) - RRCA + IN A, (FDC_DRQ) + RRCA ; CF = DRQ state IN A, (FDC_DATA) JP C, .l1 CALL fdc_check_status ; TODO: replace call+ret to jp @@ -4821,27 +4842,27 @@ m_fdc_read_c_bytes: ; Out: CF set if errors ; --------------------------------------------------- fdc_check_status: - IN A,(FDC_CMD) - AND 11011111b + IN A, (FDC_CMD) + AND 11011111b ; check status of CP 0x0 - JP Z,fdc_ret - IN A,(FDC_CMD) + JP Z, fdc_ret + IN A, (FDC_CMD) CP 0x80 - LD C,0x80 - JP Z,fcs_error + LD C, 0x80 + JP Z, fcs_error CP 0x40 - LD C,0x3 - JP Z,fcs_error + LD C, 0x3 + JP Z, fcs_error CP 0x10 - LD C,0x4 - JP Z,fcs_error + LD C, 0x4 + JP Z, fcs_error CP 0x8 - LD C,0x9 - JP Z,fcs_error - LD C,0x10 + LD C, 0x9 + JP Z, fcs_error + LD C, 0x10 fcs_error: SCF - LD A,C + LD A, C fdc_ret: RET @@ -4853,71 +4874,71 @@ LAST EQU $ CODE_SIZE EQU LAST-0xe000 FILL_SIZE EQU ROM_CHIP_SIZE-CODE_SIZE + IFDEF CHECK_INTEGRITY + ASSERT m_start = 0xe036 + ASSERT conf_uart = 0xe08c + ASSERT conf_pic = 0xe09f + ASSERT jump_bios = 0xe0d6 + ASSERT m_out_strz = 0xe0e7 + ASSERT m_cold_start = 0xe10c + ASSERT registers_tab = 0xe27e + ASSERT m_char_print = 0xe2e8 + ASSERT m_con_out = 0xe307 + ASSERT m_con_out_int = 0xe311 + ASSERT get_esc_param = 0xe32b + ASSERT esc_params_tab = 0xe3ae + ASSERT esc_set_beep = 0xe3dd + ASSERT esc_print_screen = 0xe3fb + ASSERT m_print_hor_line = 0xe424 + ASSERT m_get_7vpix = 0xe49e + ASSERT esc_set_palette = 0xe4e8 + ASSERT m_get_glyph = 0xe50a + ASSERT m_print_no_esc = 0xe533 + ASSERT calc_addr_40 = 0xe6b2 + ASSERT mp_mode_64 = 0xe72e + ASSERT scroll_up = 0xe777 + ASSERT mp_mode_80 = 0xe7c2 + ASSERT m80_rt = 0xe85d + ASSERT calc_addr_80 = 0xe8a0 + ASSERT m_clear_screen = 0xe900 + ASSERT m_cursor_home = 0xe933 + ASSERT m_draw_cursor = 0xe961 + ASSERT m_handle_esc_code = 0xeb04 + ASSERT handle_cc_common = 0xeb4c + ASSERT handle_cc_mono = 0xeb87 + ASSERT handle_cc_80x25 = 0xebce + ASSERT m_beep = 0xebf5 + ASSERT esc_set_cursor = 0xec2b + ASSERT esc_set_vmode = 0xec8b + ASSERT esc_set_color = 0xecbc + ASSERT m_print_at_xy = 0xecd0 + ASSERT calc_px_addr = 0xed4b + ASSERT esc_draw_fill_rect = 0xed5e + ASSERT esc_draw_line = 0xedf7 + ASSERT esc_draw_dot = 0xef3e + ASSERT esc_draw_circle = 0xef62 + ASSERT dc_put_pixel = 0xf0a8 + ASSERT get_key_with_check = 0xf5ce + ASSERT m_tape_write_ram = 0xf654 + ASSERT m_tape_read_ram = 0xf6a4 + ASSERT m_ramdisk_read = 0xf76a + ASSERT m_ramdisk_write = 0xf794 + ASSERT m_tape_write = 0xf7be + ASSERT m_tape_wr_byte = 0xf835 + ASSERT m_tape_read = 0xf88e + ASSERT m_read_tape_bit = 0xf92f + ASSERT m_tape_wait = 0xf97f + ASSERT m_select_drive = 0xf9e8 - ASSERT m_start = 0xe036 - ASSERT conf_uart = 0xe08c - ASSERT conf_pic = 0xe09f - ASSERT jump_bios = 0xe0d6 - ASSERT m_out_strz = 0xe0e7 - ASSERT m_cold_start = 0xe10c - ASSERT registers_tab = 0xe27e - ASSERT m_char_print = 0xe2e8 - ASSERT m_con_out = 0xe307 - ASSERT m_con_out_int = 0xe311 - ASSERT get_esc_param = 0xe32b - ASSERT esc_params_tab = 0xe3ae - ASSERT esc_set_beep = 0xe3dd - ASSERT esc_print_screen = 0xe3fb - ASSERT m_print_hor_line = 0xe424 - ASSERT m_get_7vpix = 0xe49e - ASSERT esc_set_palette = 0xe4e8 - ASSERT m_get_glyph = 0xe50a - ASSERT m_print_no_esc = 0xe533 - ASSERT calc_addr_40 = 0xe6b2 - ASSERT mp_mode_64 = 0xe72e - ASSERT scroll_up = 0xe777 - ASSERT mp_mode_80 = 0xe7c2 - ASSERT m80_rt = 0xe85d - ASSERT calc_addr_80 = 0xe8a0 - ASSERT m_clear_screen = 0xe900 - ASSERT m_cursor_home = 0xe933 - ASSERT m_draw_cursor = 0xe961 - ASSERT m_handle_esc_code = 0xeb04 - ASSERT handle_cc_common = 0xeb4c - ASSERT handle_cc_mono = 0xeb87 - ASSERT handle_cc_80x25 = 0xebce - ASSERT m_beep = 0xebf5 - ASSERT esc_set_cursor = 0xec2b - ASSERT esc_set_vmode = 0xec8b - ASSERT esc_set_color = 0xecbc - ASSERT m_print_at_xy = 0xecd0 - ASSERT calc_px_addr = 0xed4b - ASSERT esc_draw_fill_rect = 0xed5e - ASSERT esc_draw_line = 0xedf7 - ASSERT esc_draw_dot = 0xef3e - ASSERT esc_draw_circle = 0xef62 - ASSERT dc_put_pixel = 0xf0a8 - ASSERT get_key_with_check = 0xf5ce - ASSERT m_tape_write_ram = 0xf654 - ASSERT m_tape_read_ram = 0xf6a4 - ASSERT m_ramdisk_read = 0xf76a - ASSERT m_ramdisk_write = 0xf794 - ASSERT m_tape_write = 0xf7be - ASSERT m_tape_wr_byte = 0xf835 - ASSERT m_tape_read = 0xf88e - ASSERT m_read_tape_bit = 0xf92f - ASSERT m_tape_wait = 0xf97f - ASSERT m_select_drive = 0xf9e8 - - ASSERT m_read_floppy = 0xfa36 - ASSERT m_write_floppy = 0xfa47 - ASSERT m_start_floppy = 0xfa61 - ASSERT fdc_init = 0xfa90 - ASSERT m_fdc_seek_trk = 0xfa9c - ASSERT m_fdc_write_bytes = 0xfad8 - ASSERT m_fdc_read_c_bytes = 0xfae9 - ASSERT fdc_check_status = 0xfafd - + ASSERT m_read_floppy = 0xfa36 + ASSERT m_write_floppy = 0xfa47 + ASSERT m_start_floppy = 0xfa61 + ASSERT fdc_init = 0xfa90 + ASSERT m_fdc_seek_trk = 0xfa9c + ASSERT m_fdc_write_bytes = 0xfad8 + ASSERT m_fdc_read_c_bytes = 0xfae9 + ASSERT fdc_check_status = 0xfafd + ENDIF ;DISPLAY "m_handle_esc_code: ", /H, m_handle_esc_code diff --git a/MON_r7_93bd95bd/.vscode/tasks.json b/MON_r7_93bd95bd/.vscode/tasks.json index ed01311..4d74d1c 100644 --- a/MON_r7_93bd95bd/.vscode/tasks.json +++ b/MON_r7_93bd95bd/.vscode/tasks.json @@ -13,17 +13,7 @@ "--fullpath", "monitor.asm" ], - "problemMatcher": { - "owner": "sjasmplus", - "fileLocation": "autoDetect", - "pattern": { - "regexp": "^(.*)\\((\\d+)\\):\\s+(warning|error):\\s+(.*)$", - "file": 1, - "line": 2, - "severity": 3, - "message": 4 - } - }, + "problemMatcher": "$problem-matcher-sjasmplus", "group": { "kind": "build", "isDefault": true diff --git a/MON_r7_93bd95bd/monitor.asm b/MON_r7_93bd95bd/monitor.asm index 482a29a..42954fd 100644 --- a/MON_r7_93bd95bd/monitor.asm +++ b/MON_r7_93bd95bd/monitor.asm @@ -15,6 +15,8 @@ OUTPUT mon_E000.bin + ; Check original labels position + DEFINE CHECK_INTEGRITY MODULE MONITOR @@ -5173,56 +5175,59 @@ LAST EQU $ CODE_SIZE EQU LAST-0xe000 FILL_SIZE EQU ROM_CHIP_SIZE-CODE_SIZE + IFDEF CHECK_INTEGRITY - ASSERT m_hot_start = 0xe039 - ASSERT m_out_strz = 0xe0d9 - ASSERT m_char_print = 0xe130 - ASSERT m_con_out = 0xe14a - ASSERT m_con_out_int = 0xe154 - ASSERT get_esc_param = 0xe16e - ASSERT esc_params_tab = 0xe1b2 - ASSERT esc_handler_tab = 0xe1c2 - ASSERT esc_set_beep = 0xe1e0 - ASSERT esc_print_screen = 0xe1f8 - ASSERT m_print_hor_line = 0xe221 - ASSERT m_get_7vpix = 0xe29b - ASSERT esc_set_palette = 0xe2e5 - ASSERT m_get_glyph = 0xe307 - ASSERT m_print_no_esc = 0xe330 - ASSERT calc_addr_40 = 0xe420 - ASSERT mp_mode_64 = 0xe49f - ASSERT calc_addr_80 = 0xe5f9 - ASSERT m_clear_screen = 0xe620 - ASSERT m_cursor_home = 0xe653 - ASSERT m_draw_cursor = 0xe681 - ASSERT m_handle_esc_code = 0xe763 - ASSERT handle_cc_common = 0xe7ab - ASSERT handle_cc_80x25 = 0xe81a - ASSERT m_beep = 0xe841 - ASSERT esc_set_cursor = 0xe877 - ASSERT esc_set_vmode = 0xe8d6 - ASSERT esc_set_color = 0xe91c - ASSERT m_print_at_xy = 0xe930 - ASSERT game_sprite_tab = 0xea26 - ASSERT calc_px_addr = 0xeb46 - ASSERT esc_draw_fill_rect = 0xeb59 - ASSERT esc_paint = 0xebd4 - ASSERT draw_line_h = 0xee8d - ASSERT esc_draw_line = 0xeec7 - ASSERT esc_draw_dot = 0xf00e - ASSERT esc_picture = 0xf121 - ASSERT esc_draw_circle = 0xf2e1 - ASSERT dc_put_pixel = 0xf427 - ASSERT esc_get_put_image = 0xf0b5 - ASSERT me_out_strz = 0xf9cb - ASSERT m_ramdisk_read = 0xf9d8 - ASSERT m_ramdisk_write = 0xfa02 - ASSERT m_tape_write = 0xfa2c - ASSERT m_tape_wr_byte = 0xfaa3 - ASSERT m_tape_read = 0xfafc - ASSERT m_read_tape_bit = 0xfb9d - ASSERT m_tape_wait = 0xfbed - ASSERT m_select_drive = 0xfc66 + ASSERT m_hot_start = 0xe039 + ASSERT m_out_strz = 0xe0d9 + ASSERT m_char_print = 0xe130 + ASSERT m_con_out = 0xe14a + ASSERT m_con_out_int = 0xe154 + ASSERT get_esc_param = 0xe16e + ASSERT esc_params_tab = 0xe1b2 + ASSERT esc_handler_tab = 0xe1c2 + ASSERT esc_set_beep = 0xe1e0 + ASSERT esc_print_screen = 0xe1f8 + ASSERT m_print_hor_line = 0xe221 + ASSERT m_get_7vpix = 0xe29b + ASSERT esc_set_palette = 0xe2e5 + ASSERT m_get_glyph = 0xe307 + ASSERT m_print_no_esc = 0xe330 + ASSERT calc_addr_40 = 0xe420 + ASSERT mp_mode_64 = 0xe49f + ASSERT calc_addr_80 = 0xe5f9 + ASSERT m_clear_screen = 0xe620 + ASSERT m_cursor_home = 0xe653 + ASSERT m_draw_cursor = 0xe681 + ASSERT m_handle_esc_code = 0xe763 + ASSERT handle_cc_common = 0xe7ab + ASSERT handle_cc_80x25 = 0xe81a + ASSERT m_beep = 0xe841 + ASSERT esc_set_cursor = 0xe877 + ASSERT esc_set_vmode = 0xe8d6 + ASSERT esc_set_color = 0xe91c + ASSERT m_print_at_xy = 0xe930 + ASSERT game_sprite_tab = 0xea26 + ASSERT calc_px_addr = 0xeb46 + ASSERT esc_draw_fill_rect = 0xeb59 + ASSERT esc_paint = 0xebd4 + ASSERT draw_line_h = 0xee8d + ASSERT esc_draw_line = 0xeec7 + ASSERT esc_draw_dot = 0xf00e + ASSERT esc_picture = 0xf121 + ASSERT esc_draw_circle = 0xf2e1 + ASSERT dc_put_pixel = 0xf427 + ASSERT esc_get_put_image = 0xf0b5 + ASSERT me_out_strz = 0xf9cb + ASSERT m_ramdisk_read = 0xf9d8 + ASSERT m_ramdisk_write = 0xfa02 + ASSERT m_tape_write = 0xfa2c + ASSERT m_tape_wr_byte = 0xfaa3 + ASSERT m_tape_read = 0xfafc + ASSERT m_read_tape_bit = 0xfb9d + ASSERT m_tape_wait = 0xfbed + ASSERT m_select_drive = 0xfc66 + + ENDIF ; DISPLAY "esc_paint: ", /H, esc_paint diff --git a/MON_r8_9c6c6546/bios_entries.inc b/MON_r8_9c6c6546/bios_entries.inc index 117a2c8..8b3091d 100644 --- a/MON_r8_9c6c6546/bios_entries.inc +++ b/MON_r8_9c6c6546/bios_entries.inc @@ -33,7 +33,8 @@ tape_read_f EQU 0xD639 tape_write_f EQU 0xD63C tape_wait_f EQU 0xD63F -bios_var04 EQU 0xD64B +drive_B_tracks EQU 0xD64B +drive_C_tracks EQU 0xD64C ENDMODULE diff --git a/MON_r8_9c6c6546/equates.inc b/MON_r8_9c6c6546/equates.inc index b1b5622..52d0122 100644 --- a/MON_r8_9c6c6546/equates.inc +++ b/MON_r8_9c6c6546/equates.inc @@ -39,16 +39,32 @@ CCP_SIZE EQU 0x809 CPM_VERSION EQU 0x22 ; Version of CP/M as byte nibbles '2.2' CTRL EQU 0x5E ; ^ +CTRL_A EQU 0x01 +CTRL_B EQU 0x02 CTRL_C EQU 0x03 ; Warm boot -CTRL_H EQU 0x08 ; Backspace +CTRL_D EQU 0x04 CTRL_E EQU 0x05 ; Move to beginning of new line (Physical EOL) +CTRL_F EQU 0x06 +CTRL_G EQU 0x07 +CTRL_H EQU 0x08 ; Backspace +CTRL_I EQU 0x09 CTRL_J EQU 0x0A ; LF - Line Feed +CTRL_K EQU 0x0B +CTRL_L EQU 0x0C CTRL_M EQU 0x0D ; CR - Carriage Return +CTRL_N EQU 0x0E +CTRL_O EQU 0x0F CTRL_P EQU 0x10 ; turn on/off printer +CTRL_Q EQU 0x11 CTRL_R EQU 0x12 ; Repeat current cmd line CTRL_S EQU 0x13 ; Temporary stop display data to console (aka DC3) +CTRL_T EQU 0x14 CTRL_U EQU 0x15 ; Cancel (erase) current cmd line +CTRL_V EQU 0x16 +CTRL_W EQU 0x17 CTRL_X EQU 0x18 ; Cancel (erase) current cmd line +CTRL_Y EQU 0x19 +CTRL_Z EQU 0x1A ; CTRL-Z - end of text file marker ; ------------------------------------------------------ DBPLIST EQU 0x0F @@ -69,9 +85,10 @@ FDC_DD80RB EQU 0x21 FDC_NOT_READY EQU 0x80 FDC_RESTORE_L EQU 0x08 FDC_SEEK_LV EQU 0x1C -FDC_RESTORE_UH_NV EQU 0x03 ; Restore Unload Head, No Verify, 15ms Rate +FDC_RESTORE EQU 0x03 ; Restore Unload Head, No Verify, 15ms Rate FILE_DELETED EQU 0xE5 FWF_MASK EQU 0x80 ; File Write Flag mask +FLOPPY_SSEL EQU 0x20 ; --------------------------------------------------- ; FCB Offsets @@ -109,7 +126,11 @@ IRQ_2 EQU 0x04 ;LP_IRQ EQU 0x08 KBD_IRQ EQU 0x02 -KBD_ACK EQU 0x10 +KBD_ACK EQU 0x80 + +IRQ_KEYBOARD EQU 0x02 +IRQ_PRINTER EQU 0x08 +IRQ_TIMER EQU 0x10 KEY_ALF EQU 0x0D KEY_FIX EQU 0x15 diff --git a/MON_r8_9c6c6546/io.inc b/MON_r8_9c6c6546/io.inc index d884e0b..ebba20c 100644 --- a/MON_r8_9c6c6546/io.inc +++ b/MON_r8_9c6c6546/io.inc @@ -28,22 +28,26 @@ USR_DD79CTR EQU 0x03 ; ------------------------------------------------------- ; КР1818ВГ93 ; ------------------------------------------------------- -; CMD + +; WR: FDC CMD +; RD: STATUS FDC_CMD EQU 0x20 -; TRACK +; FDC TRACK FDC_TRACK EQU 0x21 -; SECTOR +; FDC SECTOR FDC_SECT EQU 0x22 -; DATA +; FDC DATA FDC_DATA EQU 0x23 -; +; RD: Bit 0 - DRQ FDC_WAIT EQU 0x24 ; Controller port +; RD: [MOTST,SSEL,x,x,DRSEL,MOT1,MOT0,INTRQ] +; WR: [x,x,SSEL,#DDEN,INIT,DRSEL,MOT1,MOT0] FLOPPY EQU 0x25 diff --git a/MON_r8_9c6c6546/m8_all.map b/MON_r8_9c6c6546/m8_all.map new file mode 100644 index 0000000..c45f937 --- /dev/null +++ b/MON_r8_9c6c6546/m8_all.map @@ -0,0 +1,496 @@ +MONITOR.mon_start 0xe000 f +MONITOR.mon_hexb 0xe003 f +MONITOR.non_con_status 0xe006 f +MONITOR.mon_con_in 0xe009 f +MONITOR.mon_con_out 0xe00c f +MONITOR.mon_serial_in 0xe00f f +MONITOR.mon_serial_out 0xe012 f +MONITOR.mon_char_print 0xe015 f +MONITOR.mon_tape_read 0xe018 f +MONITOR.mon_tape_write 0xe01b f +MONITOR.mon_ram_disk_read 0xe01e f +MONITOR.mon_ram_disk_write 0xe021 f +MONITOR.mon_tape_read_ram 0xe024 f +MONITOR.mon_tape_write_ram 0xe027 f +MONITOR.mon_tape_wait 0xe02a f +MONITOR.mon_tape_detect 0xe02d f +MONITOR.mon_read_floppy 0xe030 f +MONITOR.mon_write_floppy 0xe033 f +MONITOR.mon_out_str_z 0xe036 f +MONITOR.m_start 0xe051 f +MONITOR.m_start.fill_video 0xe06c f +MONITOR.m_start.conf_uart 0xe0a7 f +MONITOR.m_start.conf_pic 0xe0ba f +MONITOR.m_out_strz 0xe0f1 f +MONITOR.mgs_system_nf 0xe0fc f +MONITOR.m_sys_halt 0xe111 f +MONITOR.m_con_status 0xe112 f +MONITOR.m_serial_in 0xe11c f +MONITOR.m_con_in 0xe128 f +MONITOR.m_serial_out 0xe13d f +MONITOR.m_char_print 0xe148 f +MONITOR.m_char_print.wait_lp 0xe157 f +MONITOR.m_con_out 0xe163 f +MONITOR.m_con_out_int 0xe16d f +MONITOR.get_esc_param 0xe187 f +MONITOR.esc_no_draw_fn 0xe1c1 f +MONITOR.esc_exit 0xe1c6 f +MONITOR.esc_params_tab 0xe1cb f +MONITOR.esc_handler_tab 0xe1db f +MONITOR.esc_set_beep 0xe1f9 f +MONITOR.esc_set_cursor2 0xe20e f +MONITOR.esc_print_screen 0xe211 f +MONITOR.esc_print_screen.chk_keys 0xe220 f +MONITOR.esc_print_screen.no_keys 0xe22d f +MONITOR.m_print_hor_line 0xe23a f +MONITOR.m_print_hor_line.print_next_col 0xe248 f +MONITOR.m_print_cmd 0xe276 f +MONITOR.m_print_cmd.print_nxt 0xe277 f +MONITOR.m_print_cmd.cmd_end 0xe285 f +MONITOR.m_print_vert_7pix 0xe287 f +MONITOR.cmd_esc_inc_Y2 0xe2a5 f +MONITOR.cmd_esc_set_X0 0xe2a9 f +MONITOR.cmd_esc_set_X 0xe2ae f +MONITOR.cmd_esc_print_col 0xe2b1 f +MONITOR.m_get_7vpix 0xe2b4 f +MONITOR.m_get_7vpix.calc_pix_no 0xe2be f +MONITOR.m_get_7vpix.for_all_pix 0xe2dc f +MONITOR.m_get_7vpix.all_shifted 0xe2e9 f +MONITOR.m_get_7vpix.not_1_1 0xe2f2 f +MONITOR.m_get_7vpix.not_1_2 0xe2fa f +MONITOR.esc_set_palette 0xe2fe f +MONITOR.esp_no_colr 0xe313 f +MONITOR.esc_set_charset 0xe317 f +MONITOR.m_get_glyph 0xe320 f +MONITOR.m_get_glyph.cp_rus 0xe340 f +MONITOR.m_get_glyph.cp_common 0xe344 f +MONITOR.m_print_no_esc 0xe349 f +MONITOR.m_print_no_esc.l1 0xe377 f +MONITOR.m_print_no_esc.l2 0xe381 f +MONITOR.m_print_no_esc.l3 0xe389 f +MONITOR.m_print_no_esc.l4 0xe391 f +MONITOR.m_print_no_esc.l5 0xe396 f +MONITOR.m_print_no_esc.sym_draw 0xe39a f +MONITOR.m_print_no_esc.pne_l7 0xe3a5 f +MONITOR.m_print_no_esc.pne_l8 0xe3aa f +MONITOR.m40_rt 0xe3ee f +MONITOR.m40_wrap_rt 0xe3f9 f +MONITOR.m40_lf 0xe405 f +MONITOR.m40_bksp 0xe40f f +MONITOR.m40_bksp.wrap 0xe41d f +MONITOR.m40_up 0xe421 f +MONITOR.m40_up.up_no_minus 0xe429 f +MONITOR.m20_tab 0xe42b f +MONITOR.calc_addr_40 0xe439 f +MONITOR.calc_addr_40.l1 0xe454 f +MONITOR.calc_addr_40.l2 0xe45a f +MONITOR.m2_lf 0xe464 f +MONITOR.m2_lf.lf_nowr 0xe46e f +MONITOR.m2_lf.cas_l5 0xe47b f +MONITOR.m2_lf.cas_l6 0xe480 f +MONITOR.m2_lf.cas_l7 0xe496 f +MONITOR.m2_lf.cas_l8 0xe49b f +MONITOR.m20_bksp 0xe4ab f +MONITOR.mp_mode_64 0xe4b8 f +MONITOR.mp_mode_64.next_row 0xe4d3 f +MONITOR.m64_rt 0xe4e7 f +MONITOR.m64_lf 0xe4f0 f +MONITOR.scroll_up 0xe4fa f +MONITOR.scroll_up.next_row 0xe512 f +MONITOR.scroll_up.next_col 0xe514 f +MONITOR.m64_bs 0xe524 f +MONITOR.m64_up 0xe52f f +MONITOR.m64_up.no_wrap 0xe537 f +MONITOR.m64_tab 0xe539 f +MONITOR.mp_mode_80 0xe545 f +MONITOR.mp_mode_80.l1 0xe55e f +MONITOR.mp_mode_80.l2 0xe56d f +MONITOR.mp_mode_80.l3 0xe58e f +MONITOR.mp_mode_80.l4 0xe5b3 f +MONITOR.mp_mode_80.l5 0xe5b4 f +MONITOR.mp_mode_80.l6 0xe5c4 f +MONITOR.m80_rt 0xe5cf f +MONITOR.m80_col_wrap 0xe5da f +MONITOR.m80_lf 0xe5de f +MONITOR.m80_bs 0xe5e8 f +MONITOR.m80_bs.wrap 0xe5f6 f +MONITOR.m80_up 0xe5fa f +MONITOR.m80_up.no_wrap 0xe602 f +MONITOR.m80_tab 0xe604 f +MONITOR.calc_addr_80 0xe612 f +MONITOR.mns_l1 0xe62d f +MONITOR.mns_ep_fm_0 0xe633 f +MONITOR.m_clear_screen 0xe639 f +MONITOR.m_clear_screen.fill_scrn 0xe652 f +MONITOR.m_clear_screen.mono_mode 0xe669 f +MONITOR.m_cursor_home 0xe66c f +MONITOR.m_clear_20_rows 0xe679 f +MONITOR.m_clear_20_rows.next_row 0xe683 f +MONITOR.m_clear_20_rows.next_col 0xe688 f +MONITOR.m_draw_cursor 0xe69a f +MONITOR.m_draw_cursor.dc_rt2 0xe6cf f +MONITOR.m_draw_cursor.dc_mid 0xe6d7 f +MONITOR.m_draw_cursor.dc_lt 0xe6dd f +MONITOR.m_draw_cursor.dc_rt1 0xe6e3 f +MONITOR.m_draw_cursor.dc_put 0xe6e6 f +MONITOR.m_draw_cursor.dc_mode_64 0xe703 f +MONITOR.m_draw_cursor.cur_64_next 0xe721 f +MONITOR.m_draw_cursor.dc_mode_80 0xe72f f +MONITOR.m_draw_cursor.dc_1_byte 0xe75e f +MONITOR.m_draw_cursor.dc_2_byte 0xe769 f +MONITOR.m_draw_cursor.dc_80_end 0xe776 f +MONITOR.m_handle_esc_code 0xe77c f +MONITOR.m_handle_control_code 0xe78a f +MONITOR.handle_cc_common 0xe7c4 f +MONITOR.handle_cc_common.handle_cc_mono 0xe7ff f +MONITOR.handle_cc_80x25 0xe833 f +MONITOR.m_beep 0xe85a f +MONITOR.m_bell_cont 0xe86f f +MONITOR.m_bell_wait_tmr1 0xe879 f +MONITOR.m_bell_wait_tmr2 0xe886 f +MONITOR.esc_set_cursor 0xe890 f +MONITOR.esc_set_cursor.mode_40 0xe8bf f +MONITOR.esc_set_cursor.mode_80 0xe8ca f +MONITOR.esc_set_cursor.common 0xe8d2 f +MONITOR.esc_le_24 0xe8df f +MONITOR.esc_set_vmode 0xe8e9 f +MONITOR.esc_set_vmode.set_color_mode 0xe90f f +MONITOR.esc_set_vmode.skip_for_mono_mode 0xe911 f +MONITOR.esc_set_vmode.draw_cursor 0xe91a f +MONITOR.esc_set_vmode.cursor_hide 0xe91e f +MONITOR.esc_set_vmode.cursor_show 0xe928 f +MONITOR.esc_set_color 0xe92f f +MONITOR.m_set_color 0xe932 f +MONITOR.m_print_at_xy 0xe943 f +MONITOR.m_print_at_xy.mode_sp 0xe986 f +MONITOR.m_print_at_xy.out_sp 0xe99b f +MONITOR.m_print_at_xy.next_line 0xe9a2 f +MONITOR.m_print_at_xy.l04 0xe9af f +MONITOR.m_print_at_xy.l05 0xe9b4 f +MONITOR.m_print_at_xy.sprites_en 0xe9e2 f +MONITOR.mode2_exit 0xe9e6 f +MONITOR.co_ex_l08 0xe9ed f +MONITOR.out_no_xor 0xe9f1 f +MONITOR.out_no_xor.l10 0xe9fe f +MONITOR.out_no_xor.l11 0xea03 f +MONITOR.game_sprite_tab 0xea39 f +MONITOR.calc_px_addr 0xeb51 f +MONITOR.esc_draw_fill_rect 0xeb64 f +MONITOR.esc_draw_fill_rect.non_zero_h 0xeb73 f +MONITOR.esc_draw_fill_rect.shift_mask_l 0xeb78 f +MONITOR.esc_draw_fill_rect.shift_mask_r 0xeb8d f +MONITOR.esc_draw_fill_rect.next_line 0xebb7 f +MONITOR.esc_draw_fill_rect.rectangle_xor 0xebc6 f +MONITOR.esc_draw_fill_rect.edf_l6 0xebd5 f +MONITOR.esc_draw_fill_rect.next_8px 0xebdf f +MONITOR.esc_draw_fill_rect.w_ne_0 0xebe0 f +MONITOR.esc_draw_fill_rect.r_mask 0xebf6 f +MONITOR.esc_draw_fill_rect.next_full 0xebfc f +MONITOR.esc_draw_fill_rect.complete 0xec0b f +MONITOR.esc_paint 0xec18 f +MONITOR.esc_paint.l1 0xec57 f +MONITOR.ep_fm_0 0xec8b f +MONITOR.ep_task_end 0xec9a f +MONITOR.ep_l4 0xecb5 f +MONITOR.ep_l5 0xecbd f +MONITOR.ep_l6 0xecc5 f +MONITOR.ep_f_fast 0xecd7 f +MONITOR.ep_l8 0xece5 f +MONITOR.ep_l9 0xed1d f +MONITOR.ep_l10 0xed2c f +MONITOR.ep_l11 0xed3d f +MONITOR.paint_find_next_right 0xed77 f +MONITOR.paint_find_next_right.l1 0xed84 f +MONITOR.paint_find_next_right.l2 0xed90 f +MONITOR.paint_find_next_left 0xed9a f +MONITOR.paint_find_next_left.l1 0xeda7 f +MONITOR.paint_find_next_left.l2 0xedb3 f +MONITOR.ep_l12 0xedbd f +MONITOR.ep_l13 0xedd6 f +MONITOR.ep_l14 0xede8 f +MONITOR.ep_l15 0xedf1 f +MONITOR.ep_l16 0xedfa f +MONITOR.paint_find_right 0xedfd f +MONITOR.paint_find_right.in_byte 0xee0a f +MONITOR.paint_find_left 0xee18 f +MONITOR.paint_find_left.in_byte 0xee24 f +MONITOR.get_pixel 0xee32 f +MONITOR.get_pixel.bit1_set 0xee48 f +MONITOR.get_pixel.bit2_set 0xee57 f +MONITOR.get_pixel.bit12_set 0xee5f f +MONITOR.paint_task 0xee67 f +MONITOR.paint_task.lmp_mask 0xee7e f +MONITOR.paint_task.rmp_mask 0xee97 f +MONITOR.paint_task.lmi_mask 0xeea3 f +MONITOR.paint_task.rmi_mask 0xeeac f +MONITOR.paint_exit 0xeec6 f +MONITOR.draw_line_h 0xeed1 f +MONITOR.draw_line_h.next_byte 0xeedc f +MONITOR.draw_line_h.width_ne0 0xeedd f +MONITOR.draw_line_h.r_mask 0xeef5 f +MONITOR.draw_line_h.full_8 0xeefb f +MONITOR.draw_line_h.complete 0xef06 f +MONITOR.esc_draw_line 0xef0b f +MONITOR.esc_draw_line.x1_le_x2 0xef1b f +MONITOR.esc_draw_line.pos_height 0xef2b f +MONITOR.esc_draw_line.next_16 0xef45 f +MONITOR.esc_draw_line.edl_l4 0xef51 f +MONITOR.esc_draw_line.edl_l5 0xef54 f +MONITOR.esc_draw_line.roll_l 0xef67 f +MONITOR.esc_draw_line.edl_l7 0xef6e f +MONITOR.esc_draw_line.next_up 0xef89 f +MONITOR.esc_draw_line.next_down 0xef9f f +MONITOR.esc_draw_line.is_last 0xefb5 f +MONITOR.esc_draw_line.edl_l11 0xefc3 f +MONITOR.esc_draw_line.width0 0xefcb f +MONITOR.esc_draw_line.edl_l13 0xefd1 f +MONITOR.esc_draw_line.next_row_up 0xefe5 f +MONITOR.esc_draw_line.next_row_down 0xeffb f +MONITOR.close_vram_ret 0xf011 f +MONITOR.height0 0xf016 f +MONITOR.height0.len_ne0 0xf01e f +MONITOR.height0.edl_l19 0xf023 f +MONITOR.height0.next_col 0xf033 f +MONITOR.height0.edl_l21 0xf048 f +MONITOR.esc_draw_dot 0xf052 f +MONITOR.edd_l1 0xf05b f +MONITOR.edd_ep_fm_0 0xf084 f +MONITOR.edd_ep_task_end 0xf09d f +MONITOR.esc_picture 0xf0a4 f +MONITOR.pict_sub1 0xf0d6 f +MONITOR.pict_clr 0xf0f3 f +MONITOR.ehd_l1 0xf104 f +MONITOR.m_fn_39 0xf10f f +MONITOR.m_fn_39.l1 0xf12e f +MONITOR.m_fn_39.l2 0xf148 f +MONITOR.m_fn_39.l3 0xf15f f +MONITOR.get_image_hdr 0xf177 f +MONITOR.esc_get_put_image 0xf1b5 f +MONITOR.get_image 0xf1e1 f +MONITOR.get_image.next_row 0xf1e3 f +MONITOR.get_image.l2 0xf1f2 f +MONITOR.put_image 0xf201 f +MONITOR.put_image.next_row 0xf203 f +MONITOR.put_image.l2 0xf213 f +MONITOR.img_task_end 0xf21e f +MONITOR.fn39_sub2 0xf223 f +MONITOR.fn39_sub2.l1 0xf224 f +MONITOR.fn39_sub2.l2 0xf225 f +MONITOR.fn39_sub2.l3 0xf233 f +MONITOR.fn39_sub2.l4 0xf238 f +MONITOR.fn39_sub2.l5 0xf245 f +MONITOR.fn39_sub2.l6 0xf24a f +MONITOR.gih_rt 0xf266 f +MONITOR.gih_rt.l1 0xf289 f +MONITOR.gih_rt.l2 0xf28d f +MONITOR.gih_rt.l3 0xf291 f +MONITOR.gih_bs 0xf2bd f +MONITOR.gih_bs.l1 0xf2dd f +MONITOR.gih_bs.l2 0xf2e9 f +MONITOR.gih_bs.l3 0xf2ed f +MONITOR.gih_ctrl_z 0xf319 f +MONITOR.gih_ctrl_z.l1 0xf32e f +MONITOR.gih_ctrl_z.l2 0xf332 f +MONITOR.gih_ctrl_z.l3 0xf345 f +MONITOR.gih_ctrl_z.l4 0xf34a f +MONITOR.gih_ctrl_z.l5 0xf35a f +MONITOR.gih_up 0xf368 f +MONITOR.gih_up.l1 0xf378 f +MONITOR.gih_up.l2 0xf390 f +MONITOR.gih_up.l3 0xf394 f +MONITOR.gih_up.l4 0xf3a7 f +MONITOR.gih_up.l5 0xf3ac f +MONITOR.gih_up.l6 0xf3bc f +MONITOR.pict_sub2 0xf3ca f +MONITOR.pict_sub2.l1 0xf3f2 f +MONITOR.pict_sub2.l2 0xf3f7 f +MONITOR.pict_sub2.l3 0xf3fb f +MONITOR.pict_sub2.l4 0xf426 f +MONITOR.mov_hl_bc 0xf43b f +MONITOR.mov_hl_bc.next 0xf442 f +MONITOR.esc_draw_circle 0xf44c f +MONITOR.esc_draw_circle.l1 0xf469 f +MONITOR.esc_draw_circle.l2 0xf480 f +MONITOR.esc_draw_circle.l3 0xf4a2 f +MONITOR.dc_draw_8px 0xf4ab f +MONITOR.dc_aspect_ratio_1 0xf4c7 f +MONITOR.dc_aspect_ratio_1.dc_ax_ne0 0xf4d7 f +MONITOR.dc_aspect_ratio_1.dc_ay_ne0 0xf4e0 f +MONITOR.dc_aspect_ratio2 0xf4e7 f +MONITOR.dc_aspect_ratio2.dc_ax_ne0 0xf4f7 f +MONITOR.dc_aspect_ratio2.dc_ay_ne0 0xf500 f +MONITOR.dc_mul_e_h 0xf507 f +MONITOR.dc_mul_e_h.l1 0xf50f f +MONITOR.dc_mul_e_h.l2 0xf514 f +MONITOR.dc_mul_e_h.l3 0xf519 f +MONITOR.dc_mul_e_h.l4 0xf51e f +MONITOR.dc_mul_e_h.l5 0xf523 f +MONITOR.dc_mul_e_h.l6 0xf528 f +MONITOR.dc_mul_e_h.l7 0xf52d f +MONITOR.dc_mul_e_h.l8 0xf532 f +MONITOR.dc_draw_4px_bc 0xf534 f +MONITOR.dc_draw_4px_bc.l1 0xf540 f +MONITOR.dc_draw_4px_bc.l2 0xf54c f +MONITOR.dc_draw_4px_bc.l3 0xf558 f +MONITOR.dc_draw_4px_cb 0xf563 f +MONITOR.dc_draw_4px_cb.l1 0xf56f f +MONITOR.dc_draw_4px_cb.l2 0xf57b f +MONITOR.l3 0xf587 f +MONITOR.dc_put_pixel 0xf592 f +MONITOR.dc_put_pixel.roll 0xf59a f +MONITOR.m_font_cp0 0xf5bc f +MONITOR.m_font_cp1 0xf85c f +MONITOR.conv_nibble 0xfa1c f +MONITOR.m_hexb 0xfa26 f +MONITOR.out_hex 0xfa2f f +MONITOR.m_tape_write_ram2 0xfa36 f +MONITOR.m_tape_write_ram2.cl_stack 0xfa3b f +MONITOR.m_tape_write_ram2.nxt_blk 0xfa5d f +MONITOR.twr2_delay 0xfa73 f +MONITOR.twr2_delay.delay 0xfa76 f +MONITOR.m_tape_read_ram2 0xfa7d f +MONITOR.m_tape_read_ram2.srch_first 0xfa88 f +MONITOR.m_tape_read_ram2.rd_next 0xfaa6 f +MONITOR.m_tape_read_ram2.not_found 0xfac5 f +MONITOR.m_tape_read_ram2.rd_error 0xfacc f +MONITOR.m_tape_read_ram2.inv_id 0xfae1 f +MONITOR.m_tape_read_ram2.err_ubi 0xfaed f +MONITOR.m_tape_read_ram2.err_ibu 0xfaf5 f +MONITOR.m_tape_read_ram2.end 0xfaf6 f +MONITOR.out_hexw 0xfafd f +MONITOR.msg_no_start_rec 0xfb08 f +MONITOR.msg_checksum 0xfb18 f +MONITOR.msg_sequence 0xfb22 f +MONITOR.msg_ibg 0xfb2c f +MONITOR.msg_break 0xfb30 f +MONITOR.me_out_strz 0xfb36 f +MONITOR.m_ramdisk_read 0xfb43 f +MONITOR.m_ramdisk_read.read 0xfb55 f +MONITOR.m_ramdisk_write 0xfb6d f +MONITOR.m_ramdisk_write.wr_byte 0xfb7f f +MONITOR.m_tape_write 0xfb97 f +MONITOR.m_tape_write.l1 0xfbae f +MONITOR.m_tape_write.set_lvl 0xfbc0 f +MONITOR.m_tape_write.l2 0xfbd0 f +MONITOR.m_tape_write.next_byte 0xfbee f +MONITOR.m_tape_write.wait_end 0xfc00 f +MONITOR.m_tape_wr_byte 0xfc0e f +MONITOR.m_tape_wr_byte.get_bit 0xfc15 f +MONITOR.m_tape_wr_byte.wait_t 0xfc1b f +MONITOR.m_tape_wr_byte.out_bit 0xfc39 f +MONITOR.m_tape_wr_byte.bit_hi 0xfc41 f +MONITOR.m_tape_wr_byte.out_bit_hi 0xfc5f f +MONITOR.m_tape_read 0xfc67 f +MONITOR.m_tape_read.wait_3_changes 0xfc79 f +MONITOR.m_tape_read.wait_4th_change 0xfc8a f +MONITOR.m_tape_read.wait_f5_marker 0xfc99 f +MONITOR.m_tape_read.read_next_b 0xfcbd f +MONITOR.m_tape_read.checksum_ok 0xfcd6 f +MONITOR.m_tape_read.return 0xfcd7 f +MONITOR.m_tape_read.err_read_blk 0xfcda f +MONITOR.m_tape_read.err_read_id 0xfcde f +MONITOR.m_tape_read.key_pressed 0xfce3 f +MONITOR.m_tape_read_byte 0xfcee f +MONITOR.m_tape_read_byte.next_bit 0xfcf1 f +MONITOR.m_tape_read_byte.ret_err 0xfd06 f +MONITOR.m_read_tape_bit 0xfd08 f +MONITOR.m_read_tape_bit.wait_change 0xfd0d f +MONITOR.read_tape_bit_kbd 0xfd2b f +MONITOR.read_tape_bit_kbd.wait_change 0xfd30 f +MONITOR.read_tape_bit_kbd.key_pressed 0xfd55 f +MONITOR.m_tape_wait 0xfd58 f +MONITOR.m_tape_wait.wait_t4 0xfd5c f +MONITOR.m_tape_wait.wait_next_2ms 0xfd62 f +MONITOR.m_tape_wait.wait_tmr_key 0xfd6d f +MONITOR.m_tape_wait.wait_no_rst4 0xfd86 f +MONITOR.m_tape_wait.key_pressed 0xfd8d f +MONITOR.m_tape_blk_detect 0xfd95 f +MONITOR.floppy_reset 0xfd9e f +MONITOR.floppy_reset.wait_no_busy 0xfda8 f +MONITOR.floppy_reset.tr0_ok 0xfdba f +MONITOR.floppy_reset.b1 0xfdc9 f +MONITOR.m_select_drive 0xfdd1 f +MONITOR.m_select_drive.sel_A 0xfddf f +MONITOR.m_select_drive.sel_B 0xfde1 f +MONITOR.m_select_drive.dpar_a 0xfdf6 f +MONITOR.m_select_drive.dpar_b 0xfdf9 f +MONITOR.m_select_drive.l_le 0xfe15 f +MONITOR.delay_136uS 0xfe24 f +MONITOR.delay_b 0xfe26 f +MONITOR.delay_1.4mS 0xfe2b f +MONITOR.m_read_floppy 0xfe30 f +MONITOR.m_write_floppy 0xfe43 f +MONITOR.m_start_seek_track 0xfe56 f +MONITOR.m_start_floppy 0xfe5f f +MONITOR.m_start_floppy.need_m_start 0xfe6b f +MONITOR.m_start_floppy.wait_motor 0xfe76 f +MONITOR.m_start_floppy.wait_rdy1 0xfe7d f +MONITOR.m_start_floppy.long_delay 0xfe8f f +MONITOR.m_start_floppy.mst_exi 0xfe95 f +MONITOR.fdc_init 0xfe97 f +MONITOR.m_fdc_seek_trk 0xfea3 f +MONITOR.m_fdc_seek_trk.drv_b 0xfebc f +MONITOR.m_fdc_seek_trk.cmn 0xfecd f +MONITOR.m_fdc_seek_trk.l1 0xfef5 f +MONITOR.m_fdc_seek_trk.l2 0xff06 f +MONITOR.m_fdc_seek_trk.l3 0xff1d f +MONITOR.m_fdc_seek_trk.l4 0xff20 f +MONITOR.m_fdc_write_bytes 0xff26 f +MONITOR.m_fdc_write_bytes.w_next 0xff29 f +MONITOR.m_fdc_read_c_bytes 0xff37 f +MONITOR.m_fdc_read_c_bytes.l1 0xff3d f +MONITOR.m_fdc_read_c_bytes.l2 0xff3f f +MONITOR.fdc_check_status 0xff4b f +MONITOR.fdc_ret 0xff55 f +MONITOR.filler1 0xff56 f +MONITOR.LAST 0xff57 l +MONITOR.CODE_SIZE 0x1f57 l +MONITOR.FILL_SIZE 0xa9 l +MONITOR.FILLER 0xff57 f +M_VARS.buffer 0xbf00 f +M_VARS.paint_stack 0xbfa4 l +M_VARS.stack1 0xbfc4 l +M_VARS.paint_var1 0xbfc5 f +M_VARS.paint_var2 0xbfc6 f +M_VARS.paint_var3 0xbfc7 f +M_VARS.paint_var4 0xbfc8 f +M_VARS.paint_var5 0xbfc9 f +M_VARS.paint_y 0xbfca f +M_VARS.paint_var7 0xbfcb f +M_VARS.cmp_color 0xbfcc f +M_VARS.paint_sp_save 0xbfcd f +M_VARS.pixel_mask_r 0xbfcf f +M_VARS.tmp_color 0xbfd0 f +M_VARS.rect_var2 0xbfd1 f +M_VARS.stack_0 0xbfd2 l +M_VARS.rect_var3 0xbfd2 f +M_VARS.esc_mode 0xbfd3 f +M_VARS.esc_cmd 0xbfd4 f +M_VARS.esc_param_cnt 0xbfd5 f +M_VARS.esc_param 0xbfd6 f +M_VARS.pixel_mask_l_i 0xbfdd f +M_VARS.pixel_mask_r_i 0xbfde f +M_VARS.pixel_mask_l 0xbfdf f +M_VARS.screen_mode 0xbfe0 f +M_VARS.cursor_row 0xbfe1 f +M_VARS.cursor_col 0xbfe2 f +M_VARS.curr_color 0xbfe3 f +M_VARS.esc_hex_cmd 0xbfe5 f +M_VARS.row_shift 0xbfe5 f +M_VARS.codepage 0xbfe6 f +M_VARS.cur_palette 0xbfe7 f +M_VARS.beep_period 0xbfe8 f +M_VARS.beep_duration 0xbfea f +M_VARS.pix_shift 0xbfec f +M_VARS.strobe_state 0xbfed f +M_VARS.prn_start_x 0xbfee f +M_VARS.drv_B_inited 0xbfef f +M_VARS.drv_C_inited 0xbff0 f +M_VARS.drv_current 0xbff1 f +M_VARS.drv_B_track 0xbff2 f +M_VARS.drv_C_track 0xbff3 f +M_VARS.drv_dir_inout 0xbff4 f +M_VARS.esc_var0 0xbff5 f +M_VARS.esc_var1 0xbff6 f +M_VARS.esc_var2 0xbff7 f +M_VARS.esc_var3 0xbff8 f diff --git a/MON_r8_9c6c6546/m8_vars.map b/MON_r8_9c6c6546/m8_vars.map new file mode 100644 index 0000000..c07ea36 --- /dev/null +++ b/MON_r8_9c6c6546/m8_vars.map @@ -0,0 +1,47 @@ +buffer 0xbf00 l +paint_stack 0xbfa4 l +stack1 0xbfc4 l +paint_var1 0xbfc5 l +paint_var2 0xbfc6 l +paint_var3 0xbfc7 l +paint_var4 0xbfc8 l +paint_var5 0xbfc9 l +paint_y 0xbfca l +paint_var7 0xbfcb l +cmp_color 0xbfcc l +paint_sp_save 0xbfcd l +pixel_mask_r 0xbfcf l +tmp_color 0xbfd0 l +rect_var2 0xbfd1 l +stack_0 0xbfd2 l +rect_var3 0xbfd2 l +esc_mode 0xbfd3 l +esc_cmd 0xbfd4 l +esc_param_cnt 0xbfd5 l +esc_param 0xbfd6 l +pixel_mask_l_i 0xbfdd l +pixel_mask_r_i 0xbfde l +pixel_mask_l 0xbfdf l +screen_mode 0xbfe0 l +cursor_row 0xbfe1 l +cursor_col 0xbfe2 l +curr_color 0xbfe3 l +esc_hex_cmd 0xbfe5 l +row_shift 0xbfe5 l +codepage 0xbfe6 l +cur_palette 0xbfe7 l +beep_period 0xbfe8 l +beep_duration 0xbfea l +pix_shift 0xbfec l +strobe_state 0xbfed l +prn_start_x 0xbfee l +drv_B_inited 0xbfef l +drv_C_inited 0xbff0 l +drv_current 0xbff1 l +drv_B_track 0xbff2 l +drv_C_track 0xbff3 l +drv_dir_inout 0xbff4 l +esc_var0 0xbff5 l +esc_var1 0xbff6 l +esc_var2 0xbff7 l +esc_var3 0xbff8 l diff --git a/MON_r8_9c6c6546/m_vars.inc b/MON_r8_9c6c6546/m_vars.inc index 578bddd..7d31229 100644 --- a/MON_r8_9c6c6546/m_vars.inc +++ b/MON_r8_9c6c6546/m_vars.inc @@ -18,13 +18,13 @@ paint_stack EQU $ ; 0xbfa4 DS 32 stack1: EQU $ ; 0xbfc4 DS 1 -paint_var1 DS 1 ; 0xbfc5 -paint_var2 DS 1 ; 0xbfc6 -paint_var3 DS 1 ; 0xbfc7 -paint_var4 DS 1 ; 0xbfc8 -paint_var5 DS 1 ; 0xbfc9 -paint_y DS 1 ; 0xbfca -paint_var7 DS 1 ; 0xbfcb +paint_var1 DS 1 ; 0xbfc5 +paint_var2 DS 1 ; 0xbfc6 +paint_var3 DS 1 ; 0xbfc7 +paint_var4 DS 1 ; 0xbfc8 +paint_var5 DS 1 ; 0xbfc9 +paint_y DS 1 ; 0xbfca +paint_var7 DS 1 ; 0xbfcb cmp_color DS 1 ; 0xbfcc paint_sp_save DS 2 @@ -43,12 +43,13 @@ esc_param DS 7 ; 0xbfd6 ; Left inverse pixel mask ex: 00011111 pixel_mask_l_i DS 1 ; Right inverse pixel mask ex: 00011111 -pixel_mask_r_i DS 1 +pixel_mask_r_i DS 1 ; Left pixel mask ex: 11100000 -pixel_mask_l DS 1 +pixel_mask_l DS 1 ; Current screen mode, bit 3 - hide/show cursor, bit 4 - only 20 rows screen_mode DS 1 ; 0xbfe0 +cursor_pos: cursor_row DS 1 ; 0xbfe1 Cursor Y position cursor_col DS 1 ; 0xbfe2 Cursor X position curr_color DS 2 ; 0xbfe3 Current color low and hi bytes @@ -62,13 +63,13 @@ beep_period DS 2 ; 0xbfe8 beep_duration DS 2 ; 0xbfea pix_shift DS 1 ; 0xbfec strobe_state DS 1 ; 0xbfed -ul_var0 DS 1 ; 0xbfee -ul_A_var1 DS 1 ; 0xbfef -ul_B_var2 DS 1 ; 0xbff0 -ul_var3 DS 1 ; 0xbff1 -ul_A_var4 DS 1 ; 0xbff2 -ul_B_var5 DS 1 ; 0xbff3 -ul_var6 DS 1 ; 0xbff4 +prn_start_x DS 1 ; 0xbfee +drv_B_inited DS 1 ; 0xbfef +drv_C_inited DS 1 ; 0xbff0 +drv_current DS 1 ; 0xbff1 +drv_B_track DS 1 ; 0xbff2 +drv_C_track DS 1 ; 0xbff3 +drv_dir_inout DS 1 ; 0xbff4 esc_var0 DS 1 ; 0xbff5 esc_var1 DS 1 ; 0xbff6 esc_var2 DS 1 ; 0xbff7 @@ -89,7 +90,7 @@ esc_var3 DS 1 ; 0xbff8 ASSERT esc_mode = 0xbfd3 ASSERT screen_mode = 0xbfe0 ASSERT cur_palette = 0xbfe7 - ASSERT ul_var0 = 0xbfee + ASSERT prn_start_x = 0xbfee ASSERT paint_stack = 0xbfa4 ASSERT esc_var3 = 0xbff8 diff --git a/MON_r8_9c6c6546/mon_only.map b/MON_r8_9c6c6546/mon_only.map index 04f9873..63681ba 100644 --- a/MON_r8_9c6c6546/mon_only.map +++ b/MON_r8_9c6c6546/mon_only.map @@ -405,10 +405,10 @@ MONITOR.m_tape_wait.wait_tmr_key 0xfd6d f MONITOR.m_tape_wait.wait_no_rst4 0xfd86 f MONITOR.m_tape_wait.key_pressed 0xfd8d f MONITOR.m_tape_blk_detect 0xfd95 f -MONITOR.fdc_unload_head 0xfd9e f -MONITOR.fdc_unload_head.wait_no_busy 0xfda8 f -MONITOR.fdc_unload_head.tr0_ok 0xfdba f -MONITOR.fdc_unload_head.b1 0xfdc9 f +MONITOR.floppy_reset 0xfd9e f +MONITOR.floppy_reset.wait_no_busy 0xfda8 f +MONITOR.floppy_reset.tr0_ok 0xfdba f +MONITOR.floppy_reset.b1 0xfdc9 f MONITOR.m_select_drive 0xfdd1 f MONITOR.m_select_drive.sel_A 0xfddf f MONITOR.m_select_drive.sel_B 0xfde1 f diff --git a/MON_r8_9c6c6546/monitor.asm b/MON_r8_9c6c6546/monitor.asm index c669604..4c423a0 100644 --- a/MON_r8_9c6c6546/monitor.asm +++ b/MON_r8_9c6c6546/monitor.asm @@ -13,7 +13,9 @@ INCLUDE "ram.inc" INCLUDE "bios_entries.inc" - OUTPUT mon_E000.bin + DEFINE CHECK_INTEGRITY + + OUTPUT mon_E000.bin MODULE MONITOR @@ -224,9 +226,8 @@ m_con_in: NOP ; do not reset hi bit NOP PUSH AF - ; TODO: Check if it is keyboard ACK - ; PC7 Set Hi (ACK?) - LD A, 0x80 + ; PC7 Set Hi - ACK + LD A, KBD_ACK OUT (KBD_DD78PC), A ; PC7 Set Lo XOR A @@ -467,7 +468,7 @@ m_print_hor_line: ; Set printer X coordinate = 0 CALL m_print_cmd LD HL, 4 - LD (M_VARS.ul_var0), HL ; Set start coord X = 4 + LD (M_VARS.prn_start_x), HL ; Set start coord X = 4 LD B, 0x0 ; TODO: LD B, H (save 1b 3t) .print_next_col: @@ -476,20 +477,20 @@ m_print_hor_line: CALL m_get_7vpix AND D CALL NZ, m_print_vert_7pix - LD HL, (M_VARS.ul_var0) + LD HL, (M_VARS.prn_start_x) INC HL ; inc X - LD (M_VARS.ul_var0), HL + LD (M_VARS.prn_start_x), HL LD C, 0x1 ; 2 CALL m_get_7vpix AND D CALL NZ, m_print_vert_7pix - LD HL, (M_VARS.ul_var0) + LD HL, (M_VARS.prn_start_x) INC HL ; inc X - LD (M_VARS.ul_var0), HL + LD (M_VARS.prn_start_x), HL INC B LD A, B CP 236 @@ -525,7 +526,7 @@ m_print_vert_7pix: ; Set coordinate X to 0 LD HL, cmd_esc_set_X CALL m_print_cmd - LD HL, (M_VARS.ul_var0) + LD HL, (M_VARS.prn_start_x) LD C,H CALL m_char_print LD C,L @@ -5188,98 +5189,123 @@ m_tape_blk_detect: ; FDC DRIVER ; ====================================================== - -fdc_unload_head: - LD A, 0x0 +; ------------------------------------------------------ +; Set drive head to Track-0 and wait to complete +; Inp: B = drive 0-B, 1-C +; Out: CF set if error +; A = 0x20 if timeout +; ------------------------------------------------------ +floppy_init: + ; reset data register + LD A, 0 OUT (FDC_DATA), A - LD A, FDC_RESTORE_UH_NV + ; send seek track 0 command + LD A, FDC_RESTORE OUT (FDC_CMD), A + ; wait NOP NOP .wait_no_busy: IN A, (FDC_CMD) - AND 00000101b ; Track0 , Busy + AND 00000101b ; TR0, Busy CP 00000100b JP Z, .tr0_ok - + ; IN A, (FLOPPY) RLCA ; MOTST -> CF JP NC, .wait_no_busy + ; timeout LD A, 0x20 RET + + ; ok, head at track 0 + ; set flags .tr0_ok: LD A, B DEC A - LD A, 0x1 + LD A, 1 JP Z, .b1 - LD (M_VARS.ul_A_var1), A + LD (M_VARS.drv_B_inited), A XOR A - LD (M_VARS.ul_A_var4), A + LD (M_VARS.drv_B_track), A RET .b1: - LD (M_VARS.ul_B_var2), A + LD (M_VARS.drv_C_inited), A XOR A - LD (M_VARS.ul_B_var5), A + LD (M_VARS.drv_C_track), A RET ; --------------------------------------------------- -; +; Inp: A - Drive +; C - FD1793 CMD +; D - Track ; --------------------------------------------------- m_select_drive: PUSH AF CALL delay_1.4mS CP 0x1 ; TODO: DEC A to save 1b 3t - JP Z, .sel_A + JP Z, .sel_b LD A, 0x2 - JP .sel_B -.sel_A + JP .sel_c +.sel_b: LD A, 0x5 -.sel_B +.sel_c: LD B, A ; 010b or 101b IN A, (FLOPPY) ; read Floppy controller reg AND 0x40 ; SSEL RRA ; SSEL for out OR B ; 0x22 or 0x25 if WP - OUT (FLOPPY), A ; Select drive A or B + OUT (FLOPPY), A ; Select drive B or C LD B, A POP AF + ; ckeck drive A = B-0, C-1 DEC A - JP Z, .dpar_a - LD A, (bios_var2) - JP .dpar_b -.dpar_a - LD A, (BIOS.bios_var04) -.dpar_b + JP Z, .side_b + LD A, (disk_C_tracks) + JP .side_c +.side_b: + LD A, (BIOS.drive_B_tracks) +.side_c: PUSH BC - LD B, A ; B = dpar_A or B - LD A, D ; compare with D? + LD B, A ; B - track_no + LD A, D ; D - track CP B - JP C, .l_le ; D < B + JP C, .side_0 ; track < track_count -> side_0 SUB B LD D, A POP BC + ; Set hi bit of sector to 1 LD A, C OR 0x8 LD C, A + ; A = ssel+drsel+mot_x LD A, B - AND 0x20 + ; get SSEL (Side Selected) + AND FLOPPY_SSEL OR A + ; return if already side 1 RET NZ + ; else select side 1 LD A, B - OR 0x20 ; set SSEL to 1 + OR FLOPPY_SSEL ; set SSEL to 1 OUT (FLOPPY), A CALL delay_136uS RET -.l_le +.side_0: POP BC + ; A = ssel+drsel+mot_x LD A, B - AND 0x20 + ; get SSEL + AND FLOPPY_SSEL OR A + ; return if already side 0 (SSEL=0) RET Z + ; else select side 0 (set SSEL=0) LD A, B - AND 0x7 + ; mask only drsel+mot_x + AND 0x07 OUT (FLOPPY), A CALL delay_136uS RET @@ -5320,7 +5346,9 @@ m_read_floppy: RET ; --------------------------------------------------- -; +; Write data to floppy drive +; Inp: A - Drive No +; HL -> buffer ; --------------------------------------------------- m_write_floppy: PUSH AF @@ -5334,25 +5362,31 @@ m_write_floppy: RET ; --------------------------------------------------- -; +; Start floppy and seek track +; Inp: A - drive +; D - track +; E - sector ; --------------------------------------------------- m_start_seek_track: CALL m_start_floppy RET C CALL m_fdc_seek_trk - RET C - RET ; TODO: remove + RET C ; TODO: remove + RET ; --------------------------------------------------- -; +; Start floppy motor +; Inp: A - drive +; Out: A = 0 if ok, A = 0x20 if timeout to start motor ; --------------------------------------------------- m_start_floppy: LD B, A - LD A, (M_VARS.ul_var3) + LD A, (M_VARS.drv_current) CP B JP Z, .need_m_start CALL .wait_motor ; TODO: replace call+ret to jp RET + .need_m_start: IN A, (FLOPPY) RLCA ; check MOTST @@ -5361,112 +5395,136 @@ m_start_floppy: AND FDC_NOT_READY ; not ready flag RET Z -; --------------------------------------------------- -; -; --------------------------------------------------- .wait_motor: PUSH BC LD BC, 65535 CALL fdc_init + .wait_rdy1: IN A, (FDC_CMD) AND FDC_NOT_READY - JP Z, .long_delay + ; stop wait if FDC ready + JP Z, .stop_wait + + ; wait motor start IN A, (FLOPPY) RLCA ; CF<-A[7] MOTST flag JP NC, .wait_rdy1 + LD A, 0x20 - JP .mst_exi + JP .exit + +.stop_wait: + .long_delay: DEC BC LD A, B OR A JP NZ, .long_delay -.mst_exi: + ; exit with A=0 if no error +.exit: POP BC RET ; --------------------------------------------------- -; +; Init floppy controller ; --------------------------------------------------- fdc_init: + ; get controller register state IN A, (FLOPPY) AND 01001110b ; Get SSEL, DRSEL, MOT1, MOT0 RRA OUT (FLOPPY), A - OR 0x08 ; Set INIT bit + ; Set INIT bit + OR 0x08 + ; Sent to controller OUT (FLOPPY), A RET ; --------------------------------------------------- ; Seek track on floppy -; Inp: DE - track/sector +; Inp: B - floppy drive 0-B, 1-C +; DE - track/sector ; --------------------------------------------------- m_fdc_seek_trk: LD A, B DEC A - JP Z, .drv_b - LD A, (M_VARS.ul_A_var1) + JP Z, .drv_c + ; check init flag and init drive if needed + LD A, (M_VARS.drv_B_inited) OR A - CALL Z, fdc_unload_head + CALL Z, floppy_init + ; return if init error RET C - LD A, (M_VARS.ul_A_var4) + ; out previous track to FDC + LD A, (M_VARS.drv_B_track) OUT (FDC_TRACK), A + ; store new track no LD A, D - LD (M_VARS.ul_A_var4), A + LD (M_VARS.drv_B_track), A JP .cmn -.drv_b: - LD A, (M_VARS.ul_B_var2) +.drv_c: + LD A, (M_VARS.drv_C_inited) OR A - CALL Z, fdc_unload_head + CALL Z, floppy_init RET C - LD A, (M_VARS.ul_B_var5) + LD A, (M_VARS.drv_C_track) OUT (FDC_TRACK), A LD A, D - LD (M_VARS.ul_B_var5), A + .cmn: - LD A, (M_VARS.ul_var3) + LD A, (M_VARS.drv_current) CP B LD A, B - LD (M_VARS.ul_var3), A - JP NZ, .l2 + ; set new current drive + LD (M_VARS.drv_current), A + ; seek track if drive changed + JP NZ, .set_track + ; compare new and current track no IN A, (FDC_TRACK) CP D - JP Z, .l2 + JP Z, .set_track + JP C, .l1 - LD A, (M_VARS.ul_var6) + ; new track < prev + LD A, (M_VARS.drv_dir_inout) OR A - JP NZ, .l2 + JP NZ, .set_track LD B, 0xff CALL delay_b LD A, 0x1 - LD (M_VARS.ul_var6), A - JP .l2 + LD (M_VARS.drv_dir_inout), A + JP .set_track .l1: - LD A, (M_VARS.ul_var6) + ; new track > prev + LD A, (M_VARS.drv_dir_inout) OR A - JP Z, .l2 + JP Z, .set_track LD B, 0xff CALL delay_b LD A, 0x0 - LD (M_VARS.ul_var6), A -.l2: + LD (M_VARS.drv_dir_inout), A +.set_track: + ; set track no to FDC LD A, D OUT (FDC_DATA), A + ; seek track command to FDC (Load head & verify trk) LD A, 0x1f OUT (FDC_CMD), A + ; wait NOP NOP + ; check status IN A, (FDC_WAIT) IN A, (FDC_CMD) - AND 0x19 - CP 0x0 - JP NZ, .l3 - JP .l4 -.l3: + AND 0b00011001 ; SEEK_ERR, CRC_ERR, BUSY + CP 0 + JP NZ, .seek_errs + JP .seek_ok +.seek_errs: SCF LD A, 0x40 -.l4: +.seek_ok: PUSH AF LD A, E OUT (FDC_SECT), A @@ -5474,36 +5532,49 @@ m_fdc_seek_trk: RET ; --------------------------------------------------- -; +; Write bytes to floppy +; Inp: C - write sector command +; HL -> byte buffer ; --------------------------------------------------- m_fdc_write_bytes: + ; Send command to FDC LD A, C OUT (FDC_CMD), A .w_next: + ; DRQ -> CF IN A, (FDC_WAIT) RRCA + ; Send byte to FDC LD A, (HL) OUT (FDC_DATA), A INC HL + ; repeat until DRQ active JP C, .w_next + CALL fdc_check_status ; TODO: replace call+ret to jp RET ; --------------------------------------------------- -; +; Read bytes from floppy +; Inp: C - read sector command +; HL -> byte buffer ; --------------------------------------------------- m_fdc_read_c_bytes: + ; Send command to FDC LD A, C OUT (FDC_CMD), A - JP .l2 -.l1: + JP .get_drq +.read_next: + ; put byte to buffer LD (HL), A INC HL -.l2: +.get_drq: + ; DRQ -> CF IN A, (FDC_WAIT) RRCA + ; read byte from FDC IN A, (FDC_DATA) - JP C, .l1 + JP C, .read_next CALL fdc_check_status ; TODO: replace call+ret to jp RET @@ -5512,10 +5583,13 @@ m_fdc_read_c_bytes: ; Out: CF set if errors ; --------------------------------------------------- fdc_check_status: + ; get FDC Status of last command IN A, (FDC_CMD) + ; mask Write Protect AND 11011111b - CP 0x0 + CP 0 JP Z, fdc_ret + ; error found, set CF SCF fdc_ret: RET @@ -5533,51 +5607,52 @@ CODE_SIZE EQU LAST-0xE000 FILL_SIZE EQU ROM_CHIP_SIZE-CODE_SIZE - ASSERT m_start = 0xe051 - ASSERT m_out_strz = 0xe0f1 - ASSERT m_con_out_int = 0xe16d - ASSERT get_esc_param = 0xe187 - ASSERT esc_params_tab = 0xe1cb - ASSERT esc_handler_tab = 0xe1db - ASSERT esc_set_beep = 0xe1f9 - ASSERT m_print_hor_line = 0xe23a - ASSERT m_get_7vpix = 0xe2b4 - ASSERT esc_set_palette = 0xe2fe - ASSERT m_get_glyph = 0xe320 - ASSERT m_print_no_esc = 0xe349 - ASSERT calc_addr_40 = 0xe439 - ASSERT mp_mode_64 = 0xe4b8 - ASSERT calc_addr_80 = 0xe612 - ASSERT m_clear_screen = 0xe639 - ASSERT m_cursor_home = 0xe66c - ASSERT m_draw_cursor = 0xe69a - ASSERT m_handle_esc_code = 0xe77c - ASSERT handle_cc_common = 0xe7c4 - ASSERT handle_cc_80x25 = 0xe833 - ASSERT m_beep = 0xe85a - ASSERT esc_set_cursor = 0xe890 - ASSERT esc_set_vmode = 0xe8e9 - ASSERT esc_set_color = 0xe92f - ASSERT m_print_at_xy = 0xe943 - ASSERT game_sprite_tab = 0xea39 - ASSERT esc_draw_fill_rect = 0xeb64 - ASSERT draw_line_h = 0xeed1 - ASSERT esc_draw_line = 0xef0b - ASSERT esc_draw_dot = 0xf052 - ASSERT esc_picture = 0xf0a4 - ASSERT m_fn_39 = 0xf10f - ASSERT get_image_hdr = 0xf177 - ASSERT esc_get_put_image = 0xf1b5 - ASSERT pict_sub2 = 0xf3ca - ASSERT m_font_cp0 = 0xf5bc - ASSERT me_out_strz = 0xfb36 - ASSERT m_ramdisk_write = 0xfb6d - ASSERT m_tape_write = 0xfb97 - ASSERT m_tape_wr_byte = 0xfc0e - ASSERT m_tape_read_byte = 0xfcee - ASSERT m_read_tape_bit = 0xfd08 - ASSERT m_tape_wait = 0xfd58 - + IFDEF CHECK_INTEGRITY + ASSERT m_start = 0xe051 + ASSERT m_out_strz = 0xe0f1 + ASSERT m_con_out_int = 0xe16d + ASSERT get_esc_param = 0xe187 + ASSERT esc_params_tab = 0xe1cb + ASSERT esc_handler_tab = 0xe1db + ASSERT esc_set_beep = 0xe1f9 + ASSERT m_print_hor_line = 0xe23a + ASSERT m_get_7vpix = 0xe2b4 + ASSERT esc_set_palette = 0xe2fe + ASSERT m_get_glyph = 0xe320 + ASSERT m_print_no_esc = 0xe349 + ASSERT calc_addr_40 = 0xe439 + ASSERT mp_mode_64 = 0xe4b8 + ASSERT calc_addr_80 = 0xe612 + ASSERT m_clear_screen = 0xe639 + ASSERT m_cursor_home = 0xe66c + ASSERT m_draw_cursor = 0xe69a + ASSERT m_handle_esc_code = 0xe77c + ASSERT handle_cc_common = 0xe7c4 + ASSERT handle_cc_80x25 = 0xe833 + ASSERT m_beep = 0xe85a + ASSERT esc_set_cursor = 0xe890 + ASSERT esc_set_vmode = 0xe8e9 + ASSERT esc_set_color = 0xe92f + ASSERT m_print_at_xy = 0xe943 + ASSERT game_sprite_tab = 0xea39 + ASSERT esc_draw_fill_rect = 0xeb64 + ASSERT draw_line_h = 0xeed1 + ASSERT esc_draw_line = 0xef0b + ASSERT esc_draw_dot = 0xf052 + ASSERT esc_picture = 0xf0a4 + ASSERT m_fn_39 = 0xf10f + ASSERT get_image_hdr = 0xf177 + ASSERT esc_get_put_image = 0xf1b5 + ASSERT pict_sub2 = 0xf3ca + ASSERT m_font_cp0 = 0xf5bc + ASSERT me_out_strz = 0xfb36 + ASSERT m_ramdisk_write = 0xfb6d + ASSERT m_tape_write = 0xfb97 + ASSERT m_tape_wr_byte = 0xfc0e + ASSERT m_tape_read_byte = 0xfcee + ASSERT m_read_tape_bit = 0xfd08 + ASSERT m_tape_wait = 0xfd58 + ENDIF ; DISPLAY "Code size is: ", /A, CODE_SIZE diff --git a/MON_r8_9c6c6546/ram.inc b/MON_r8_9c6c6546/ram.inc index 8c6c08e..d757c61 100644 --- a/MON_r8_9c6c6546/ram.inc +++ b/MON_r8_9c6c6546/ram.inc @@ -28,7 +28,7 @@ ;reserve1 EQU 0x003b @bios_var0 EQU 0x0040 ; 0xaa - bios init r8 @bios_var1 EQU 0x0041 ; 0xaa - bios init r8 -@bios_var2 EQU 0x0042 ; 0x00 - bios init r8 +@disk_C_tracks EQU 0x0042 ; 0x00 - bios init r8 @bios_var3 EQU 0x0043 ; 0xff - bios init r8 @interleave_0 EQU 0x0044 ;reserve2 EQU 0x0050 diff --git a/Mon_r9/.vscode/extensions.json b/Mon_r9/.vscode/extensions.json new file mode 100644 index 0000000..1fdc4e8 --- /dev/null +++ b/Mon_r9/.vscode/extensions.json @@ -0,0 +1,9 @@ +{ + "recommendations": [ + "maziac.asm-code-lens", + "maziac.dezog", + "maziac.hex-hover-converter", + "maziac.z80-instruction-set", + "maziac.sna-fileviewer" + ] +} diff --git a/Mon_r9/.vscode/launch.json b/Mon_r9/.vscode/launch.json new file mode 100644 index 0000000..99a521e --- /dev/null +++ b/Mon_r9/.vscode/launch.json @@ -0,0 +1,42 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "type": "dezog", + "request": "launch", + "name": "Simulator - ZX48K Spectrum", + "remoteType": "zsim", + "zsim": { + "visualMemory": true, + "memoryModel": "ZX48K", + "ulaScreen": "spectrum", + "zxKeyboard": "spectrum", + "zxBeeper": true + }, + "sjasmplus": [ + { + "path": "monitor.sld" + } + ], + "commandsAfterLaunch": [], + "history": { + "reverseDebugInstructionCount": 1000000, + "spotCount": 10, + "codeCoverageEnabled": true + }, + "startAutomatically": false, + "rootFolder": "${workspaceFolder}", + + "topOfStack": "stack_top", + + "loadObjs": [ + { "path": "mon_E000.bin", "start": "0xe000" } + ], + "execAddress": "0xe021" + + } + ] +} \ No newline at end of file diff --git a/Mon_r9/.vscode/tasks.json b/Mon_r9/.vscode/tasks.json new file mode 100644 index 0000000..eee328f --- /dev/null +++ b/Mon_r9/.vscode/tasks.json @@ -0,0 +1,32 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "label": "make MONITOR (sjasmplus)", + "type": "shell", + "command": "sjasmplus", + "args": [ + "--exp=monitor.inc", + "--fullpath", + "--nofakes", + "--i8080", + "monitor.asm" + ], + "problemMatcher": { + "owner": "sjasmplus", + "fileLocation": "autoDetect", + "pattern": { + "regexp": "^(.*)\\((\\d+)\\):\\s+(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "severity": 3, + "message": 4 + } + }, + "group": { + "kind": "build", + "isDefault": true + } + } + ] +} \ No newline at end of file diff --git a/Mon_r9/BIN/MON_r8_9c6c6546.BIN b/Mon_r9/BIN/MON_r8_9c6c6546.BIN new file mode 100644 index 0000000..c11004f Binary files /dev/null and b/Mon_r9/BIN/MON_r8_9c6c6546.BIN differ diff --git a/Mon_r9/README.md b/Mon_r9/README.md new file mode 100644 index 0000000..a096e49 --- /dev/null +++ b/Mon_r9/README.md @@ -0,0 +1,19 @@ +# Ocean-240.2 ROM Monitor V8 checksum 9c6c6546 + +Source codes of Monitor v8 for Ocean-240.2 with Floppy controller. +In Z80 mnemonics, but limited for i8080 instruction set. + +## Differences + +1) Font. Other russian letters б and д; +2) Calculate values for extended ram access in procedures m_ramdisk_read, m_ramdisk_write. +3) Don't reset hi bit when read keyboard +4) Other params count at last esc commands + +## Compile + +Code is located in memory at address: 0xE000..0xFFFF + + sjasmplus --sld=monitor.sld --sym=monitor.labels --raw=monitor.obj --fullpath monitor.asm + +To compile sources, use [sjasmplus Z80 assembler](https://github.com/z00m128/sjasmplus). diff --git a/Mon_r9/bios_entries.inc b/Mon_r9/bios_entries.inc new file mode 100644 index 0000000..117a2c8 --- /dev/null +++ b/Mon_r9/bios_entries.inc @@ -0,0 +1,41 @@ + +; ======================================================= +; Ocean-240.2 +; Definition of CPM BIOS entries to compile depended +; modules +; +; By Romych 2025-09-09 +; ====================================================== + IFNDEF _BIOS + DEFINE _BIOS + + MODULE BIOS + +boot_f EQU 0xD600 +wboot_f EQU 0xD603 +const_f EQU 0xD606 +conin_f EQU 0xD609 +conout_f EQU 0xD60C +list_f EQU 0xD60F +punch_f EQU 0xD612 +reader_f EQU 0xD615 +home_f EQU 0xD618 +seldsk_f EQU 0xD61B +settrk_f EQU 0xD61E +setsec_f EQU 0xD621 +setdma_f EQU 0xD624 +read_f EQU 0xD627 +write_f EQU 0xD62A +sectran_f EQU 0xD630 +reserved_f1 EQU 0xD633 +reserved_f2 EQU 0xD636 +tape_read_f EQU 0xD639 +tape_write_f EQU 0xD63C +tape_wait_f EQU 0xD63F + +bios_var04 EQU 0xD64B + + ENDMODULE + + + ENDIF diff --git a/Mon_r9/config.inc b/Mon_r9/config.inc new file mode 100644 index 0000000..64b2c55 --- /dev/null +++ b/Mon_r9/config.inc @@ -0,0 +1,17 @@ + +; ======================================================= +; Ocean-240.2 +; Configuration +; +; By Romych 2026-02-2 +; ====================================================== + IFNDEF _CONF + DEFINE _CONF + + DEFINE DEFAULT_KB_ACK ; if defined, KB_ACK on pin PC4 DD78, else on pin PC7 + DEFINE RAM_DISK_192K + ;DEFINE CHECK_INTEGRITY ; if defined, check original labels offset + + + + ENDIF \ No newline at end of file diff --git a/Mon_r9/equates.inc b/Mon_r9/equates.inc new file mode 100644 index 0000000..f96bc00 --- /dev/null +++ b/Mon_r9/equates.inc @@ -0,0 +1,157 @@ +; ====================================================== +; Ocean-240.2 +; Equates for all assembly sources +; +; By Romych 2025-09-09 +; ====================================================== + + INCLUDE "config.inc" + + IFNDEF _EQUATES + DEFINE _EQUATES + + +ADDLIST EQU 0x08 +ASCII_BELL EQU 0x07 ; Make Beep +ASCII_BS EQU 0x08 ; Move cursor left (Back Space) +ASCII_TAB EQU 0x09 ; Move cursor right +8 pos +ASCII_LF EQU 0x0A ; Move cursor down (Line Feed) +ASCII_FF EQU 0x0C ; Move cursor to home (Form Feed) +ASCII_CR EQU 0x0D ; Move gursor to 1st pos (Cariage Return) +ASCII_CAN EQU 0x18 ; Move cursor right +ASCII_EM EQU 0x19 ; Move cursor up +ASCII_SUB EQU 0x1A ; CTRL-Z - end of text file marker +ASCII_ESC EQU 0x1B ; +ASCII_US EQU 0x1F ; Clear screen +ASCII_SP EQU 0x20 +ASCII_DEL EQU 0x7F + +; ------------------------------------------------------ +BDOS_NFUNCS EQU 41 +BELL_PIN EQU 0x08 ; DD67 Pin PC3 - "BELL" +; ------------------------------------------------------ +CCP_COMMAND_SIZE EQU 5 ; max length of CCP command +CCP_COMMAND_COUNT EQU 3 ; Count of CCP commands +CCP_COMMAND_CNT EQU 6 +CCP_COMMAND_LEN EQU 4 + +CCP_SRC_ADDR EQU 0xc000 ; Address of CCP resident part in ROM +CCP_DST_ADDR EQU 0xb200 ; Address of CCP resident part in RAM +CCP_SIZE EQU 0x809 + +CPM_VERSION EQU 0x22 ; Version of CP/M as byte nibbles '2.2' + +CTRL EQU 0x5E ; ^ +CTRL_C EQU 0x03 ; Warm boot +CTRL_H EQU 0x08 ; Backspace +CTRL_E EQU 0x05 ; Move to beginning of new line (Physical EOL) +CTRL_J EQU 0x0A ; LF - Line Feed +CTRL_M EQU 0x0D ; CR - Carriage Return +CTRL_P EQU 0x10 ; turn on/off printer +CTRL_R EQU 0x12 ; Repeat current cmd line +CTRL_S EQU 0x13 ; Temporary stop display data to console (aka DC3) +CTRL_U EQU 0x15 ; Cancel (erase) current cmd line +CTRL_X EQU 0x18 ; Cancel (erase) current cmd line + +; ------------------------------------------------------ +DBPLIST EQU 0x0F +DEF_DISK_A_SIZE EQU 0x3F +DEF_DISK_B_SIZE EQU 0x0168 +DIR_BUFF_SIZE EQU 128 +DSK_MAP EQU 0x10 +DSK_MSK EQU 0x03 +DSK_SHF EQU 0x02 +DMA_BUFF_SIZE EQU 0x80 +; ------------------------------------------------------ +ENDDIR EQU 0xFFFF +ESC_CMD_END EQU 0x1A +;EXT_NUM EQU 12 ; Extent byte offset +; ------------------------------------------------------ +FALSE EQU 0x00 +FDC_DD80RB EQU 0x21 +FDC_NOT_READY EQU 0x80 +FDC_RESTORE_L EQU 0x08 +FDC_SEEK_LV EQU 0x1C +FDC_RESTORE_UH_NV EQU 0x03 ; Restore Unload Head, No Verify, 15ms Rate +FILE_DELETED EQU 0xE5 +FWF_MASK EQU 0x80 ; File Write Flag mask + +; --------------------------------------------------- +; FCB Offsets +; --------------------------------------------------- +FCB_LEN EQU 32 ; length of FCB +FCB_SHF EQU 5 +FN_LEN EQU 12 ; Length of filename in FCB + +FCB_DR EQU 0 ; Drive. 0 for default, 1-16 for A-P +FCB_FN EQU 1 ; Fn - Filename, 7-bit ASCII. The top bits - attributes +FCB_FT EQU 9 ; Filetype, 7-bit ASCII. + ; T1' to T3' have the following + ; T1' - Read-Only + ; T2' - System (hidden) + ; T3' - Archive +FCB_EXT EQU 12 ; EX - Set this to 0 when opening a file and then leave it to + ; CP/M. You can rewind a file by setting EX, RC, S2 and CR to 0. +FCB_S1 EQU 13 ; S1 - Reserved. +FCB_S2 EQU 14 ; S2 - Reserved. Bit 7 - wile write flag, [6:0] module number (Extent hi bits) +FCB_RC EQU 15 ; RC - Set this to 0 when opening a file and then leave it to CP/M. +FCB_AL EQU 16 ; AL - Image of the second half of the directory entry, + ; containing the file's allocation (which disc blocks it owns). +FCB_CR EQU 32 ; CR - Current record within extent. It is usually best to set + ; this to 0 immediately after a file has been opened and + ; then ignore it. +FCB_RN EQU 33 ; Rn - Random access record number. A 16-bit (with R2 used for overflow) + + +; ------------------------------------------------------ +JP_OPCODE EQU 0xC3 +; ------------------------------------------------------ +IRQ_0 EQU 0x01 +IRQ_1 EQU 0x02 +IRQ_2 EQU 0x04 +;LP_IRQ EQU 0x08 +KBD_IRQ EQU 0x02 + + IFDEF DEFAULT_KB_ACK +KBD_ACK EQU 0x10 + ELSE +KBD_ACK EQU 0x80 + ENDIF + +KEY_ALF EQU 0x0D +KEY_FIX EQU 0x15 +; ------------------------------------------------------ +LST_REC EQU 0x7F +; ------------------------------------------------------ +MAX_EXT EQU 0x1F +MAX_MOD EQU 0x0F +;MOD_NUM EQU 0x0E +; ------------------------------------------------------ +FCB_INFO_LEN EQU 15 ; length of FCB info bytes to match +;NXT_REC EQU 0x20 +; ------------------------------------------------------ +PIC_POLL_MODE EQU 0x0A +PORT_C4 EQU 0x10 +PRINTER_ACK EQU 0x10 +PRINTER_IRQ EQU 0x08 +; ------------------------------------------------------ +;RAN_REC EQU 0x21 +;FCB_RC EQU 0x0F +RO_FILE EQU 0x09 +ROM_CHIP_SIZE EQU 8192 ; ROM Size, used to limit monitor code size + +RX_READY EQU 0x02 +; ------------------------------------------------------ +TAPE_D EQU 0x08 +TAPE_P EQU 0x04 +TIMER_IRQ EQU 0x10 +TL_HIGH EQU 0x05 +TL_LOW EQU 0x03 +TL_MID EQU 0x04 +TMR0_SQWAVE EQU 0x36 +TRUE EQU 0xFF +TX_READY EQU 0x01 +; ------------------------------------------------------ +stack_top EQU 0x100 + + ENDIF \ No newline at end of file diff --git a/Mon_r9/font-6x7.inc b/Mon_r9/font-6x7.inc new file mode 100644 index 0000000..221a101 --- /dev/null +++ b/Mon_r9/font-6x7.inc @@ -0,0 +1,165 @@ + ; 96 symbols 6x7, with codes 0x20..0x7f KOI-7 H0 +m_font_cp0: + DB 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ; ' ' - 0x20 + DB 0x04, 0x04, 0x04, 0x04, 0x00, 0x00, 0x04 ; '!' - 0x21 + DB 0x14, 0x14, 0x00, 0x00, 0x00, 0x00, 0x00 ; '"' - 0x22 + DB 0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a ; '#' - 0x23 + DB 0x04, 0x1e, 0x05, 0x0e, 0x14, 0x0f, 0x04 ; '$' - 0x24 + DB 0x03, 0x13, 0x08, 0x04, 0x02, 0x19, 0x18 ; '%' - 0x25 + DB 0x06, 0x09, 0x05, 0x02, 0x15, 0x09, 0x16 ; '&' - 0x26 + DB 0x06, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00 ; ' - 0x27 + DB 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08 ; '(' - 0x28 + DB 0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02 ; ')' - 0x29 + DB 0x00, 0x0a, 0x04, 0x1f, 0x04, 0x0a, 0x00 ; '*' - 0x2a + DB 0x00, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x00 ; '+' - 0x2b + DB 0x00, 0x00, 0x00, 0x00, 0x06, 0x04, 0x02 ; ',' - 0x2c + DB 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00 ; '-' - 0x2d + DB 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x06 ; '.' - 0x2e + DB 0x00, 0x10, 0x08, 0x04, 0x02, 0x01, 0x00 ; '/' - 0x2f + DB 0x0e, 0x11, 0x19, 0x15, 0x13, 0x11, 0x0e ; '0' - 0x30 + DB 0x04, 0x06, 0x04, 0x04, 0x04, 0x04, 0x0e ; '1' - 0x31 + DB 0x0e, 0x11, 0x10, 0x08, 0x04, 0x02, 0x1f ; '2' - 0x32 + DB 0x1f, 0x08, 0x04, 0x08, 0x10, 0x11, 0x0e ; '3' - 0x33 + DB 0x08, 0x0c, 0x0a, 0x09, 0x1f, 0x08, 0x08 ; '4' - 0x34 + DB 0x1f, 0x01, 0x0f, 0x10, 0x10, 0x11, 0x0e ; '5' - 0x35 + DB 0x0c, 0x02, 0x01, 0x0f, 0x11, 0x11, 0x0e ; '6' - 0x36 + DB 0x1f, 0x10, 0x08, 0x04, 0x02, 0x02, 0x02 ; '7' - 0x37 + DB 0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e ; '8' - 0x38 + DB 0x0e, 0x11, 0x11, 0x1e, 0x10, 0x08, 0x06 ; '9' - 0x39 + DB 0x00, 0x06, 0x06, 0x00, 0x06, 0x06, 0x00 ; ':' - 0x3a + DB 0x00, 0x06, 0x06, 0x00, 0x06, 0x04, 0x02 ; ';' - 0x3b + DB 0x08, 0x04, 0x02, 0x01, 0x02, 0x04, 0x08 ; '<' - 0x3c + DB 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00 ; '=' - 0x3d + DB 0x02, 0x04, 0x08, 0x10, 0x08, 0x04, 0x02 ; '>' - 0x3e + DB 0x0e, 0x11, 0x10, 0x08, 0x04, 0x00, 0x04 ; '?' - 0x3f + DB 0x0e, 0x11, 0x10, 0x16, 0x15, 0x15, 0x0e ; '@' - 0x40 + DB 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11 ; 'A' - 0x41 + DB 0x0f, 0x11, 0x11, 0x0f, 0x11, 0x11, 0x0f ; 'B' - 0x42 + DB 0x0e, 0x11, 0x01, 0x01, 0x01, 0x11, 0x0e ; 'C' - 0x43 + DB 0x07, 0x09, 0x11, 0x11, 0x11, 0x09, 0x07 ; 'D' - 0x44 + DB 0x1f, 0x01, 0x01, 0x0f, 0x01, 0x01, 0x1f ; 'E' - 0x45 + DB 0x1f, 0x01, 0x01, 0x0f, 0x01, 0x01, 0x01 ; 'F' - 0x46 + DB 0x0e, 0x11, 0x01, 0x1d, 0x11, 0x11, 0x1e ; 'G' - 0x47 + DB 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11 ; 'H' - 0x48 + DB 0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e ; 'I' - 0x49 + DB 0x1c, 0x08, 0x08, 0x08, 0x08, 0x09, 0x06 ; 'J' - 0x4a + DB 0x11, 0x09, 0x05, 0x03, 0x05, 0x09, 0x11 ; 'K' - 0x4b + DB 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x1f ; 'L' - 0x4c + DB 0x11, 0x1b, 0x15, 0x15, 0x11, 0x11, 0x11 ; 'M' - 0x4d + DB 0x11, 0x11, 0x13, 0x15, 0x19, 0x11, 0x11 ; 'N' - 0x4e + DB 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e ; 'O' - 0x4f + DB 0x0f, 0x11, 0x11, 0x0f, 0x01, 0x01, 0x01 ; 'P' - 0x50 + DB 0x0e, 0x11, 0x11, 0x11, 0x15, 0x09, 0x16 ; 'Q' - 0x51 + DB 0x0f, 0x11, 0x11, 0x0f, 0x05, 0x09, 0x11 ; 'R' - 0x52 + DB 0x1e, 0x01, 0x01, 0x0e, 0x10, 0x10, 0x0f ; 'S' - 0x53 + DB 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04 ; 'T' - 0x54 + DB 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e ; 'U' - 0x55 + DB 0x11, 0x11, 0x11, 0x11, 0x0a, 0x0a, 0x04 ; 'V' - 0x56 + DB 0x11, 0x11, 0x11, 0x15, 0x15, 0x15, 0x0a ; 'W' - 0x57 + DB 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11 ; 'X' - 0x58 + DB 0x11, 0x11, 0x11, 0x0a, 0x04, 0x04, 0x04 ; 'Y' - 0x59 + DB 0x1f, 0x10, 0x08, 0x04, 0x02, 0x01, 0x1f ; 'Z' - 0x5a + DB 0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e ; '[' - 0x5b + DB 0x00, 0x01, 0x02, 0x04, 0x08, 0x10, 0x00 ; '\' - 0x5c + DB 0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e ; ']' - 0x5d + DB 0x0e, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00 ; '^' - 0x5r + DB 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f ; '_' - 0x5f + DB 0x1c, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00 ; '`' - 0x60 + DB 0x00, 0x00, 0x0e, 0x10, 0x1e, 0x13, 0x1e ; 'a' - 0x61 + DB 0x01, 0x01, 0x0d, 0x13, 0x11, 0x11, 0x0f ; 'b' - 0x62 + DB 0x00, 0x00, 0x0e, 0x01, 0x01, 0x01, 0x0e ; 'c' - 0x63 + DB 0x10, 0x10, 0x16, 0x19, 0x11, 0x11, 0x1e ; 'd' - 0x64 + DB 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x01, 0x0e ; 'e' - 0x65 + DB 0x18, 0x04, 0x04, 0x0e, 0x04, 0x04, 0x04 ; 'f' - 0x66 + DB 0x00, 0x0e, 0x11, 0x11, 0x1e, 0x10, 0x0e ; 'g' - 0x67 + DB 0x01, 0x01, 0x0d, 0x13, 0x11, 0x11, 0x11 ; 'h' - 0x68 + DB 0x04, 0x00, 0x04, 0x04, 0x04, 0x04, 0x04 ; 'i' - 0x69 + DB 0x08, 0x00, 0x08, 0x08, 0x08, 0x08, 0x06 ; 'j' - 0x6a + DB 0x01, 0x01, 0x09, 0x05, 0x03, 0x05, 0x09 ; 'k' - 0x6b + DB 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x08 ; 'l' - 0x6c + DB 0x00, 0x00, 0x0f, 0x15, 0x15, 0x15, 0x15 ; 'm' - 0x6d + DB 0x00, 0x00, 0x09, 0x13, 0x11, 0x11, 0x11 ; 'n' - 0x6e + DB 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e ; 'o' - 0x6f + DB 0x00, 0x00, 0x0e, 0x11, 0x11, 0x0f, 0x01 ; 'p' - 0x70 + DB 0x00, 0x00, 0x0e, 0x11, 0x11, 0x1e, 0x10 ; 'q' - 0x71 + DB 0x00, 0x00, 0x0d, 0x13, 0x01, 0x01, 0x01 ; 'r' - 0x72 + DB 0x00, 0x00, 0x1e, 0x01, 0x0e, 0x10, 0x0f ; 's' - 0x73 + DB 0x04, 0x04, 0x0e, 0x04, 0x04, 0x04, 0x18 ; 't' - 0x74 + DB 0x00, 0x00, 0x11, 0x11, 0x11, 0x19, 0x16 ; 'u' - 0x75 + DB 0x00, 0x00, 0x11, 0x11, 0x0a, 0x0a, 0x04 ; 'v' - 0x76 + DB 0x00, 0x00, 0x11, 0x15, 0x15, 0x15, 0x0a ; 'w' - 0x77 + DB 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11 ; 'x' - 0x78 + DB 0x00, 0x00, 0x11, 0x11, 0x1e, 0x10, 0x0c ; 'y' - 0x79 + DB 0x00, 0x00, 0x1f, 0x08, 0x04, 0x02, 0x1f ; 'z' - 0x7a + DB 0x0c, 0x02, 0x02, 0x01, 0x02, 0x02, 0x0c ; '{' - 0x7b + DB 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04 ; '|' - 0x7c + DB 0x03, 0x04, 0x04, 0x08, 0x04, 0x04, 0x03 ; '}' - 0x7d + DB 0x00, 0x02, 0x15, 0x0a, 0x15, 0x08, 0x00 ; '~' - 0x7e + DB 0x15, 0x00, 0x15, 0x00, 0x15, 0x00, 0x15 ; [DEL] - 0x7f + +; 64 symbols 6x7, with codes 0x40..0x7f KOI-7 H1 +m_font_cp1: + DB 0x00, 0x00, 0x09, 0x15, 0x17, 0x15, 0x09 ; ю - 0x40 + DB 0x00, 0x00, 0x06, 0x08, 0x0e, 0x09, 0x16 ; а - 0x41 + DB 0x07, 0x02, 0x04, 0x0e, 0x09, 0x09, 0x06 ; б - 0x42 DIFF + DB 0x00, 0x00, 0x09, 0x09, 0x09, 0x1f, 0x10 ; ц - 0x43 + DB 0x03, 0x04, 0x08, 0x0e, 0x09, 0x09, 0x06 ; д - 0x44 DIFF + DB 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x01, 0x1e ; е - 0x45 + DB 0x00, 0x04, 0x0e, 0x15, 0x15, 0x0e, 0x04 ; ф - 0x46 + DB 0x00, 0x00, 0x0f, 0x09, 0x01, 0x01, 0x01 ; г - 0x47 + DB 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11 ; х - 0x48 + DB 0x00, 0x00, 0x11, 0x19, 0x15, 0x13, 0x11 ; и - 0x49 + DB 0x0a, 0x04, 0x11, 0x19, 0x15, 0x13, 0x11 ; й - 0x4a + DB 0x00, 0x00, 0x11, 0x09, 0x07, 0x09, 0x11 ; к - 0x4b + DB 0x00, 0x00, 0x1c, 0x12, 0x12, 0x12, 0x11 ; л - 0x4c + DB 0x00, 0x00, 0x11, 0x1b, 0x15, 0x11, 0x11 ; м - 0x4d + DB 0x00, 0x00, 0x11, 0x11, 0x1f, 0x11, 0x11 ; н - 0x4e + DB 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e ; о - 0x4f + DB 0x00, 0x00, 0x1f, 0x11, 0x11, 0x11, 0x11 ; п - 0x50 + DB 0x00, 0x00, 0x1e, 0x11, 0x1e, 0x14, 0x12 ; я - 0x51 + DB 0x00, 0x00, 0x07, 0x09, 0x07, 0x01, 0x01 ; р - 0x52 + DB 0x00, 0x00, 0x0e, 0x01, 0x01, 0x01, 0x0e ; с - 0x53 + DB 0x00, 0x00, 0x1f, 0x04, 0x04, 0x04, 0x04 ; т - 0x54 + DB 0x00, 0x00, 0x11, 0x11, 0x1e, 0x10, 0x0e ; у - 0x55 + DB 0x00, 0x00, 0x15, 0x15, 0x0e, 0x15, 0x15 ; ж - 0x56 + DB 0x00, 0x00, 0x03, 0x05, 0x07, 0x09, 0x07 ; в - 0x57 + DB 0x00, 0x00, 0x01, 0x01, 0x07, 0x09, 0x07 ; ь - 0x58 + DB 0x00, 0x00, 0x11, 0x11, 0x13, 0x15, 0x13 ; ы - 0x59 + DB 0x00, 0x00, 0x0e, 0x11, 0x0c, 0x11, 0x0e ; з - 0x5a + DB 0x00, 0x00, 0x15, 0x15, 0x15, 0x15, 0x1f ; ш - 0x5b + DB 0x00, 0x00, 0x07, 0x08, 0x0e, 0x08, 0x07 ; э - 0x5c + DB 0x00, 0x00, 0x15, 0x15, 0x15, 0x1f, 0x10 ; щ - 0x5d + DB 0x00, 0x00, 0x09, 0x09, 0x0e, 0x08, 0x08 ; ч - 0x5e + DB 0x00, 0x00, 0x06, 0x05, 0x0c, 0x14, 0x0c ; ъ - 0x5f + DB 0x09, 0x15, 0x15, 0x17, 0x15, 0x15, 0x09 ; Ю - 0x60 + DB 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11 ; А - 0x61 + DB 0x1f, 0x11, 0x01, 0x0f, 0x11, 0x11, 0x1f ; Б - 0x62 + DB 0x09, 0x09, 0x09, 0x09, 0x09, 0x1f, 0x10 ; С - 0x63 + DB 0x0c, 0x0a, 0x0a, 0x0a, 0x0a, 0x1f, 0x11 ; Д - 0x64 + DB 0x1f, 0x01, 0x01, 0x0f, 0x01, 0x01, 0x1f ; Е - 0x65 + DB 0x04, 0x0e, 0x15, 0x15, 0x15, 0x0e, 0x04 ; Ф - 0x66 + DB 0x1f, 0x11, 0x01, 0x01, 0x01, 0x01, 0x01 ; Г - 0x67 + DB 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11 ; Х - 0x68 + DB 0x11, 0x11, 0x19, 0x15, 0x13, 0x11, 0x11 ; И - 0x69 + DB 0x04, 0x15, 0x11, 0x19, 0x15, 0x13, 0x11 ; Й - 0x6a + DB 0x11, 0x09, 0x05, 0x03, 0x05, 0x09, 0x11 ; К - 0x6b + DB 0x1c, 0x12, 0x12, 0x12, 0x12, 0x12, 0x11 ; Л - 0x6c + DB 0x11, 0x1b, 0x15, 0x15, 0x11, 0x11, 0x11 ; М - 0x6d + DB 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11 ; Н - 0x6e + DB 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e ; О - 0x6f + DB 0x1f, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11 ; П - 0x70 + DB 0x1e, 0x11, 0x11, 0x11, 0x1e, 0x12, 0x11 ; Я - 0x71 + DB 0x0f, 0x11, 0x11, 0x11, 0x0f, 0x01, 0x01 ; Р - 0x72 + DB 0x0e, 0x11, 0x01, 0x01, 0x01, 0x11, 0x0e ; С - 0x73 + DB 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04 ; Т - 0x74 + DB 0x11, 0x11, 0x11, 0x11, 0x1e, 0x10, 0x0e ; У - 0x75 + DB 0x15, 0x15, 0x15, 0x0e, 0x15, 0x15, 0x15 ; Ж - 0x76 + DB 0x0f, 0x11, 0x11, 0x0f, 0x11, 0x11, 0x0f ; В - 0x77 + DB 0x01, 0x01, 0x01, 0x0f, 0x11, 0x11, 0x0f ; Ь - 0x78 + DB 0x11, 0x11, 0x11, 0x13, 0x15, 0x15, 0x13 ; Ы - 0x79 + DB 0x0e, 0x11, 0x10, 0x0c, 0x10, 0x11, 0x0e ; З - 0x7a + DB 0x15, 0x15, 0x15, 0x15, 0x15, 0x15, 0x1f ; Ш - 0x7b + DB 0x0e, 0x11, 0x10, 0x1c, 0x10, 0x11, 0x0e ; Э - 0x7c + DB 0x15, 0x15, 0x15, 0x15, 0x15, 0x1f, 0x10 ; Щ - 0x7d + DB 0x11, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x10 ; Ч - 0x7e + DB 0x1f, 0x15, 0x1f, 0x15, 0x1f, 0x15, 0x1f ; [DEL] - 0x7f diff --git a/Mon_r9/io.inc b/Mon_r9/io.inc new file mode 100644 index 0000000..dbc8d10 --- /dev/null +++ b/Mon_r9/io.inc @@ -0,0 +1,103 @@ +; ======================================================= +; Ocean-240.2 +; Computer with FDC variant. +; IO Ports definitions +; +; By Romych 2025-09-09 +; ======================================================= + + IFNDEF _IO_PORTS + DEFINE _IO_PORTS + +; ------------------------------------------------------- +; КР580ВВ55 DD79 +; ------------------------------------------------------- + +USR_DD79PA EQU 0x00 ; User port A +USR_DD79PB EQU 0x01 ; User port B +USR_DD79PC EQU 0x02 ; User port C + +; Config: [1][ma1,ma0][0-aO|1-aI],[0-chO,1-chI],[mb],[0-bO|1-bI],[0-clO,1-clI] +; Set bit: [0][xxx][bbb][0|1] +USR_DD79CTR EQU 0x03 + +; ------------------------------------------------------- +; КР1818ВГ93 +; ------------------------------------------------------- + +FDC_CMD EQU 0x20 ; FDC Command +FDC_TRACK EQU 0x21 ; FDC Track No +FDC_SECT EQU 0x22 ; FDC Sector +FDC_DATA EQU 0x23 ; FDC Data + +FDC_WAIT EQU 0x24 ; FDC Wait + +; Floppy Controller port +; WR: 5-SSEN, 4-#DDEN, 3-INIT, 2-DRSEL, 1-MOT1, 0-MOT0 +; RD: 7-MOTST, 6-SSEL, 5,4-x , 3-DRSEL, 2-MOT1, 1-MOT0, 0-INT +FLOPPY EQU 0x25 ; Floppy Controller port + +; ------------------------------------------------------- +; КР580ВВ55 DD78 +; ------------------------------------------------------- +KBD_DD78PA EQU 0x40 ; Port A - Keyboard Data +KBD_DD78PB EQU 0x41 ; Port B - JST3,SHFT,CTRL,ACK,TAPE5,TAPE4,GK,GC +KBD_DD78PC EQU 0x42 ; Port C - [PC7:5],[KBD_ACK],[PC3:0] + +; Сonfig: [1][ma1,ma0][0-aO|1-aI],[0-chO,1-chI],[mb],[0-bO|1-bI],[0-clO,1-clI] +; Set bit: [0][xxx][bbb][0|1]; +KBD_DD78CTR EQU 0x43 + + +; ------------------------------------------------------- +; КР580ВИ53 DD70 +; ------------------------------------------------------- + +TMR_DD70C1 EQU 0x60 ; Timer counter 1 +TMR_DD70C2 EQU 0x61 ; Timer counter 2 +TMR_DD70C3 EQU 0x62 ; Timer counter 3 + +; Timer config: [sc1,sc0][rl1,rl0][m2,m1,m0][bcd] +; sc - timer, rl=01-LSB, 10-MSB, 11-LSB+MSB +; mode 000 - int on fin, +; 001 - one shot, +; x10 - rate gen, +; x11-sq wave +TMR_DD70CTR EQU 0x63 + +; Programable Interrupt controller PIC KR580VV59 +PIC_DD75RS EQU 0x80 ; PIC RS +PIC_DD75RM EQU 0x81 ; PIC RM + +; ------------------------------------------------------- +; КР580ВВ51 DD72 +; ------------------------------------------------------- + +UART_DD72RD EQU 0xA0 ; Serial data +UART_DD72RR EQU 0xA1 ; Serial status [RST,RQ_RX,RST_ERR,PAUSE,RX_EN,RX_RDY,TX_RDY] + +; ------------------------------------------------------- +; КР580ВВ55 DD17 +; ------------------------------------------------------- + +SYS_DD17PA EQU 0xC0 ; Port A - VShift[8..1] +SYS_DD17PB EQU 0xC1 ; Port B - [ROM14,13][REST][ENROM-][A18,17,16][32k] +SYS_DD17PC EQU 0xC2 ; Port C - HShift[HS5..1,SB3..1] + +; Сonfig: [1][ma1,ma0][0-aO|1-aI],[0-chO,1-chI],[mb],[0-bO|1-bI],[0-clO,1-clI] +; Set bit: [0][xxx][bbb][0|1]; +SYS_DD17CTR EQU 0xC3 + +; ------------------------------------------------------- +; КР580ВВ55 DD67 +; ------------------------------------------------------- + +LPT_DD67PA EQU 0xE0 ; Port A - LPT Data +VID_DD67PB EQU 0xE1 ; Port B - [VSU,C/M,FL3..1,COL3..1] +DD67PC EQU 0xE2 ; Port C - [USER3..1,STB-LP,BELL,TAPE3..1] + +; Сonfig: [1][ma1,ma0][0-aO|1-aI],[0-chO,1-chI],[mb],[0-bO|1-bI],[0-clO,1-clI] +; Set bit: [0][xxx][bbb][0|1]; +DD67CTR EQU 0xE3 + + ENDIF \ No newline at end of file diff --git a/Mon_r9/m_vars.inc b/Mon_r9/m_vars.inc new file mode 100644 index 0000000..93617fa --- /dev/null +++ b/Mon_r9/m_vars.inc @@ -0,0 +1,105 @@ +; ======================================================= +; Ocean-240.2 +; Module M_VARS - Monitor variables +; RAM Range: 0xBA09-0xBFFF +; +; Disassembled by Romych 2025-02-05 +; ======================================================= + + IFNDEF _M_VARS + DEFINE _M_VARS + + MODULE M_VARS + ORG 0xbf00 + +stack_top EQU 0x100 +buffer DS 128 ; 0xbf00 search text or buffer to search? + DS 36 +paint_stack EQU $ ; 0xbfa4 + DS 32 +stack1: EQU $ ; 0xbfc4 + DS 1 +paint_var1 DS 1 ; 0xbfc5 +paint_var2 DS 1 ; 0xbfc6 +paint_var3 DS 1 ; 0xbfc7 +paint_var4 DS 1 ; 0xbfc8 +paint_var5 DS 1 ; 0xbfc9 +paint_y DS 1 ; 0xbfca +paint_var7 DS 1 ; 0xbfcb +cmp_color DS 1 ; 0xbfcc +paint_sp_save DS 2 + +; Right pixel mask ex: 11111000 +pixel_mask_r DS 1 ; 0xbfcf +tmp_color DS 1 ; 0xbfd0 +rect_var2 DS 1 ; 0xbfd1 +stack_0 EQU $ +rect_var3 DS 1 ; 0xbfd2 +esc_mode DS 1 ; 0xbfd3 +esc_cmd DS 1 ; 0xbfd4 + +esc_param_cnt DS 1 ; 0xbfd5 +esc_param DS 7 ; 0xbfd6 + +; Left inverse pixel mask ex: 00011111 +pixel_mask_l_i DS 1 +; Right inverse pixel mask ex: 00011111 +pixel_mask_r_i DS 1 +; Left pixel mask ex: 11100000 +pixel_mask_l DS 1 + +; Current screen mode, bit 3 - hide/show cursor, bit 4 - only 20 rows +screen_mode DS 1 ; 0xbfe0 +cursor_row DS 1 ; 0xbfe1 Cursor Y position +cursor_col DS 1 ; 0xbfe2 Cursor X position +curr_color DS 2 ; 0xbfe3 Current color low and hi bytes +esc_hex_cmd: +row_shift DS 1 ; 0xbfe5 +codepage DS 1 ; 0xbfe6 + +cur_palette DS 1 ; 0xbfe7 00bbbfff - background and foreground colors +beep_period DS 2 ; 0xbfe8 +beep_duration DS 2 ; 0xbfea +pix_shift DS 1 ; 0xbfec +strobe_state DS 1 ; 0xbfed +ul_var0 DS 1 ; 0xbfee +ul_A_var1 DS 1 ; 0xbfef +ul_B_var2 DS 1 ; 0xbff0 +ul_var3 DS 1 ; 0xbff1 +ul_A_var4 DS 1 ; 0xbff2 +ul_B_var5 DS 1 ; 0xbff3 +ul_var6 DS 1 ; 0xbff4 +esc_var0 DS 1 ; 0xbff5 +esc_var1 DS 1 ; 0xbff6 +esc_var2 DS 1 ; 0xbff7 +esc_var3 DS 1 ; 0xbff8 + DS 1 ; 0xbff9 + DS 1 ; 0xbffa + DS 1 ; 0xbffb + DS 1 ; 0xbffc + DS 1 ; 0xbffd + DS 1 ; 0xbffe + DS 1 ; 0xbfff + + IFDEF CHECK_INTEGRITY + + ASSERT stack1 = 0xbfc4 + ASSERT buffer = 0xbf00 + ASSERT paint_var1 = 0xbfc5 + ASSERT pixel_mask_r = 0xbfcf + ASSERT stack_0 = 0xbfd2 + ASSERT esc_mode = 0xbfd3 + ASSERT screen_mode = 0xbfe0 + ASSERT cur_palette = 0xbfe7 + ASSERT ul_var0 = 0xbfee + ASSERT paint_stack = 0xbfa4 + ASSERT esc_var3 = 0xbff8 + + ENDIF + + ;DISPLAY "screen_mode: ", /H, screen_mode + ;DISPLAY "fn48_var1: ", /H, fn48_var1 + + ENDMODULE + + ENDIF diff --git a/Mon_r9/monitor.asm b/Mon_r9/monitor.asm new file mode 100644 index 0000000..96b327c --- /dev/null +++ b/Mon_r9/monitor.asm @@ -0,0 +1,5613 @@ +; ====================================================== +; Ocean-240.2 +; Monitor V8 +; +; Modified by Romych 2026-02-22 +; ====================================================== + + DEVICE NOSLOT64K + + INCLUDE "config.inc" + INCLUDE "io.inc" + INCLUDE "equates.inc" + INCLUDE "ram.inc" + INCLUDE "bios_entries.inc" + + OUTPUT mon_E000.bin + + + MODULE MONITOR + + ORG 0xe000 + +; ------------------------------------------------------ +; Monitor Entry points +; ------------------------------------------------------ + +mon_start: JP m_start ; E000 +mon_hexb: JP m_hexb ; E003 +non_con_status: JP m_con_status ; E006 +mon_con_in: JP m_con_in ; E009 +mon_con_out: JP m_con_out ; E00C +mon_serial_in: JP m_serial_in ; E00F +mon_serial_out: JP m_serial_out ; E012 +mon_char_print: JP m_char_print ; E015 +mon_tape_read: JP m_tape_read ; E018 +mon_tape_write: JP m_tape_write ; E01B +mon_ram_disk_read: JP m_ramdisk_read ; E01E +mon_ram_disk_write: JP m_ramdisk_write ; E021 +mon_tape_read_ram: JP m_tape_read_ram2 ; E024 +mon_tape_write_ram: JP m_tape_write_ram2 ; E027 +mon_tape_wait: JP m_tape_wait ; E02A +mon_tape_detect: JP m_tape_blk_detect ; E02D +mon_read_floppy: JP m_read_floppy ; E030 +mon_write_floppy: JP m_write_floppy ; E033 +mon_out_str_z: JP m_out_strz ; E036 + JP m_fn_39 ; E039 + JP get_image_hdr ; E03C + JP esc_picture ; E03F + JP m_print_at_xy ; E042 + JP esc_draw_fill_rect ; E045 + JP esc_paint ; E048 + JP esc_draw_line ; E04B + JP esc_draw_circle ; E04E + + EXPORT mon_start + EXPORT mon_hexb + EXPORT non_con_status + EXPORT mon_con_in + EXPORT mon_con_out + EXPORT mon_serial_in + EXPORT mon_serial_out + EXPORT mon_char_print + EXPORT mon_tape_read + EXPORT mon_tape_write + EXPORT mon_ram_disk_read + EXPORT mon_ram_disk_write + EXPORT mon_tape_read_ram + EXPORT mon_tape_write_ram + EXPORT mon_tape_wait + EXPORT mon_tape_detect + EXPORT mon_read_floppy + EXPORT mon_write_floppy + EXPORT mon_out_str_z + +; ------------------------------------------------------ +; Init system devices +; ------------------------------------------------------ +m_start: + DI + LD A, 10000000b ; DD17 all ports to out + OUT (SYS_DD17CTR), A ; VV55 Sys CTR + OUT (DD67CTR), A ; VV55 Video CTR + + ; init_kbd_tape + LD A, 10010011b + OUT (KBD_DD78CTR), A + + ; init video + LD A, 01111111b ; VSU=0, C/M=1, FL=111, COL=111 + OUT (VID_DD67PB), A ; color mode + + LD A, 00000001b + OUT (SYS_DD17PB), A ; Access to VRAM + LD HL, 0x3f00 + LD B, L + LD A, H + ADD A, 0x41 ; A=128 0x80 + + ; Clear video memory from 0x3F00 to 0x7FFF +.fill_video: + LD (HL), B + INC HL + CP H + JP NZ, .fill_video + + XOR A + OUT (SYS_DD17PB), A ; Disable VRAM + LD A, 00000111b + OUT (SYS_DD17PC), A ; pix shift to 7 + LD (M_VARS.pix_shift), A + + XOR A + LD (M_VARS.screen_mode), A + LD (M_VARS.row_shift), A + + ; Set color mode and palette + LD (M_VARS.curr_color+1), A + CPL + LD (M_VARS.curr_color), A + LD A, 00000011b + LD (M_VARS.cur_palette), A + ; VSU=0, C/M=1, FL=000, COL=011 + ; color mode, black border + ; 00-black, 01-red, 10-purple, 11-white + LD A, 01000011b + OUT (VID_DD67PB), A + + ; Config LPT + LD A, 0x4 + OUT (DD67PC), A ; bell=1, strobe=0 + LD (M_VARS.strobe_state), A ; store strobe + LD HL, 1024 ; 683us + LD (M_VARS.beep_period), HL + LD HL, 320 ; 213us + LD (M_VARS.beep_duration), HL + + ; Config UART + LD A, 11001110b + OUT (UART_DD72RR), A + LD A, 00100101b + OUT (UART_DD72RR), A + + ; Config Timer#1 for UART clock + LD A, 01110110b ; tmr#1, load l+m bin, sq wave + OUT (TMR_DD70CTR), A + + ; 1.5M/20 = 75kHz + LD A, 20 + OUT (TMR_DD70C2), A + XOR A + OUT (TMR_DD70C2), A + + ; Config PIC + LD A,00010010b ; ICW1 edge trigger, interval 8, sin... + OUT (PIC_DD75RS), A + XOR A + OUT (PIC_DD75RM), A ; ICW2 + CPL + OUT (PIC_DD75RM), A ; ICW3 no slave + LD A,00100000b + OUT (PIC_DD75RS), A ; Non-specific EOI command, End of I... + LD A, PIC_POLL_MODE + OUT (PIC_DD75RS), A ; Poll mode, poll on next RD + + ; Send ACK to keyboard + LD A, KBD_ACK + OUT (KBD_DD78PC), A + NOP + NOP + XOR A + OUT (KBD_DD78PC), A + + ; Init cursor + LD SP, M_VARS.stack1 + CALL m_draw_cursor + + ; Beep + LD C, ASCII_BELL + CALL m_con_out + + LD A, (BIOS.boot_f) + CP JP_OPCODE + JP Z, BIOS.boot_f + LD HL, mgs_system_nf + CALL m_out_strz + JP m_sys_halt + +; -------------------------------------------------- +; Output ASCIIZ string +; Inp: HL -> string +; -------------------------------------------------- +m_out_strz: + LD C, (HL) + LD A, C + OR A + RET Z + CALL m_con_out + INC HL + JP m_out_strz + +mgs_system_nf: + DB "\r\nSYSTEM NOT FOUND\r\n", 0 + +m_sys_halt: + HALT + +; ------------------------------------------------------ +; Console status +; Out: A = 0 - not ready +; A = 0xFF - ready (key pressed) +; ------------------------------------------------------ +m_con_status: + IN A, (PIC_DD75RS) ; Read PIC status + NOP + AND KBD_IRQ ; Check keyboard request RST1 + LD A, 0 + RET Z ; no key pressed + CPL + RET ; key pressed + +; ------------------------------------------------------ +; Wait and read data from UART +; Out: A - 7 bit data +; ------------------------------------------------------ +m_serial_in: + IN A, (UART_DD72RR) + AND RX_READY + JP Z, m_serial_in ; wait for rx data ready + IN A, (UART_DD72RD) + AND 0x7f ; leave 7 bits + RET + +; ------------------------------------------------------ +; Read key +; Out: A +; ------------------------------------------------------ +m_con_in: + CALL m_con_status + OR A + JP Z, m_con_in ; wait key + IN A, (KBD_DD78PA) ; get key + ;AND 0x7f ; reset hi bit, leave 0..127 code +; NOP +; NOP + + ; Send ACK to keyboard + PUSH AF + LD A, KBD_ACK + OUT (KBD_DD78PC), A + NOP + NOP + XOR A + OUT (KBD_DD78PC), A + POP AF + + RET + +; ------------------------------------------------------ +; Send data by UART +; Inp: C - data to transmitt +; ------------------------------------------------------ +m_serial_out: + IN A, (UART_DD72RR) + AND TX_READY + JP Z, m_serial_out ; Wait for TX ready + LD A, C + OUT (UART_DD72RD), A + RET + +; ------------------------------------------------------ +; Send character to printer +; Inp: C - character +; ------------------------------------------------------ +m_char_print: + ; wait printer ready + IN A, (PIC_DD75RS) + AND PRINTER_IRQ + JP Z, m_char_print + + LD A, C + NOP + OUT (LPT_DD67PA), A + ; set LP strobe + LD A, 00010100b + OUT (DD67PC),A + +.wait_lp: + ; wait printer ack + IN A, (PIC_DD75RS) + AND PRINTER_IRQ + JP NZ, .wait_lp + ; remove LP strobe + LD A, 00000100b + OUT (DD67PC), A + RET + +; ------------------------------------------------------ +; Out char to console +; Inp: C - char +; ------------------------------------------------------ +m_con_out: + PUSH HL + PUSH DE + PUSH BC + CALL m_con_out_int + POP BC + POP DE + POP HL + RET + +; ------------------------------------------------------ +; Out char C to console +; ------------------------------------------------------ +m_con_out_int: + LD DE, M_VARS.esc_mode + LD A, (DE) + DEC A + OR A ; TODO: unused (save 1b 4t) + JP M, m_print_no_esc ; esc_mode=0 - standart print no ESC mode + JP NZ, m_print_at_xy ; esc_mode=2 (graphics) + + ; handle ESC param (esc_mode=1) + INC E ; INC DE + LD A, (DE) + OR A + JP P, get_esc_param + LD A, C + AND 0xf ; convert char to command code + LD (DE), A + INC E ; INC DE + XOR A + LD (DE), A + RET + +get_esc_param: + LD HL, M_VARS.esc_cmd + LD B, (HL) ; TODO: replace to INC L L=0xd4 save 2t + INC L ; HL -> param count + LD A, (HL) + INC A + LD (HL), A + ; store new param + LD E, A + LD D, 0x0 + ADD HL, DE ; HL -> parameter[param_count] + LD (HL), C ; store letter as esc parameter + ; get params count for esc command + LD HL, esc_params_tab + LD E, B ; d=0, b = cmd + ADD HL, DE ; DE - command offset + CP (HL) + ; return if enough + RET M + +;esc_set_mode: + LD HL, M_VARS.esc_cmd + LD A, (HL) + AND 0x0f ; mask (cmd=0..15) + LD E, A + DEC HL ; HL -> esc_mode + OR A + LD (HL), 2 ; mode=2 for cmd=0 + RET Z ; just return, no handler there + + LD D, 0 ; TODO: remove, D already 0 + LD (HL), D ; reset mode to 0 for other + DEC DE ; DE = cmd-1 + +;co_get_hdlr: + ; Calc ESC command handler offset + LD HL, esc_handler_tab + ADD HL, DE + ADD HL, DE + LD E, (HL) + INC HL + LD D, (HL) + ; HL = addr of handler func + EX DE, HL + ; It is 1..4 func DRAW_* func? + CP 0x4 + JP P, esc_no_draw_fn + LD A, (M_VARS.screen_mode) + AND 00000011b + ; If not in graphics mode - exit + JP NZ, esc_exit + +esc_no_draw_fn: + LD DE, esc_exit + PUSH DE + + ; Jump to ESC func handler + JP (HL) + +esc_exit: + XOR A + LD (M_VARS.esc_mode), A + RET + + ; Count of parameters for ESC commands + ; 0xe1cb +esc_params_tab: + DB 3, 5, 4, 3, 1, 2, 1, 1 + DB 1, 2, 1, 5, 5, 7, 6, 4 + +esc_handler_tab: + DW esc_draw_fill_rect ;5 1x1y1x2y2m + DW esc_draw_line ;4 2x1y1x2y2 + DW esc_draw_dot ;3 3xxyy + DW esc_set_color ;1 4N N=1..4 + DW esc_set_cursor ;2 5rc r-Row, c-Col + DW esc_set_vmode ;1 6m m-mode: + ; C 0 - 40x25 cursor on + ; M 1,2 - 64x25 cursor on + ; M 3 - 80x25 cursor on + ; C 4 - 40x25 cursor off + ; M 5,6 - 64x25 cursor off + ; M 7 - 80x25 cursor off + ; M 8 - 20rows mode + ; 9 - cursor off + ; 10 - cursor on + DW esc_set_charset ;1 7n where n is: + ; 0 - LAT Both cases + ; 1 - RUS Both cases + ; 2 - LAT+RUS Upper case + DW esc_set_palette ;1 8c c - Foreground+Backgound + DW esc_set_cursor2 ;2 9xy + DW esc_print_screen ;1 : + DW esc_draw_circle ;5 ;xyraxay X,Y, Radius, aspect ratio X, aspect ratio Y + DW esc_paint ;5 = + DW esc_picture ;6 > + DW esc_set_beep ;4 ?ppdd pp-period (word), dd - duration (word) + +esc_set_beep: + ; param byte 1+2 -> period + LD DE, M_VARS.esc_param + LD A, (DE) + LD H, A + INC DE + LD A, (DE) + LD L, A + LD (M_VARS.beep_period), HL + ; param byte 3+4 -> duration + INC DE + LD A, (DE) + LD H, A + INC DE + LD A, (DE) + LD L, A + LD (M_VARS.beep_duration), HL + RET + +esc_set_cursor2: + JP esc_set_cursor + +esc_print_screen: + LD A, (M_VARS.screen_mode) + AND 00000011b + RET NZ ; ret if not 0-3 mode + LD DE, 0x30ff + CALL m_print_hor_line + DEC E + LD D, 0xf0 + +.chk_keys: + CALL m_con_status + OR A + JP Z, .no_keys + CALL m_con_in + CP ASCII_ESC + RET Z + +.no_keys: + CALL m_print_hor_line + DEC E + JP NZ, .chk_keys + LD D, 0xe0 ; 224d + CALL m_print_hor_line + RET + +; ------------------------------------------------------ +; Print line to printer +; D - width +; ------------------------------------------------------ +m_print_hor_line: + LD HL, cmd_esc_set_X0 + + ; Set printer X coordinate = 0 + CALL m_print_cmd + LD HL, 4 + LD (M_VARS.ul_var0), HL ; Set start coord X = 4 + LD B, H ; LD B, 0x0 + +.print_next_col: + LD C, 0x0 + ; 1 + CALL m_get_7vpix + AND D + CALL NZ, m_print_vert_7pix + LD HL, (M_VARS.ul_var0) + INC HL + + ; inc X + LD (M_VARS.ul_var0), HL + LD C, 0x1 + ; 2 + CALL m_get_7vpix + AND D + CALL NZ, m_print_vert_7pix + LD HL, (M_VARS.ul_var0) + INC HL + ; inc X + LD (M_VARS.ul_var0), HL + INC B + LD A, B + CP 236 + JP C, .print_next_col + LD HL, cmd_esc_inc_Y2 + CALL m_print_cmd + RET + +; ------------------------------------------------------ +; Send command to printer +; Inp: HL -> command bytes array +; ------------------------------------------------------ +m_print_cmd: + PUSH BC +.print_nxt: + LD A, (HL) + CP ESC_CMD_END + JP Z, .cmd_end + LD C, A + CALL m_char_print + INC HL + JP .print_nxt +.cmd_end: + POP BC + RET + +; ------------------------------------------------------ +; Print 7 vertical pixels to printer +; Inp: A - value to print +; ------------------------------------------------------ +m_print_vert_7pix: + PUSH AF + ; Set coordinate X to 0 + LD HL, cmd_esc_set_X + CALL m_print_cmd + LD HL, (M_VARS.ul_var0) + LD C, H + CALL m_char_print + LD C, L + CALL m_char_print + ; Set column print mode + LD HL, cmd_esc_print_col + CALL m_print_cmd + POP AF + ; Print 7 vertical pixels + LD C, A + CALL m_char_print + RET + +; ------------------------------------------------------ +; Control codes for printer УВВПЧ-30-004 +; ------------------------------------------------------ +; Zn - Increment Y coordinate +; 0xe2a5 +cmd_esc_inc_Y2: + DB ASCII_ESC + DB 'Z' + DB 2h + DB ESC_CMD_END + +; Xnn - Set X coordinate +cmd_esc_set_X0: + DB ASCII_ESC + DB 'X' + DB 0h ; 0..479 + DB 0h + DB ESC_CMD_END + +; ------------------------------------------------------ +; X - Start on "Set X coordinate" command +; ------------------------------------------------------ +cmd_esc_set_X: + DB ASCII_ESC + DB 'X' + DB ESC_CMD_END + +; O - Column print (vertical 7 bit) +cmd_esc_print_col: + DB ASCII_ESC + DB 'O' + DB ESC_CMD_END + +; ------------------------------------------------------ +; Get 7 vertical pixels from screen +; Inp: C - sheet +; Out: A - byte +; ------------------------------------------------------ +m_get_7vpix: + LD A, (M_VARS.row_shift) + ADD A, B + ADD A, 19 ; skip first 20pix + LD L, A + PUSH DE + PUSH BC + LD A, E + +.calc_pix_no: + AND 0x7 + LD B, A + LD A, E + ; calc hi addr + RRA ; /8 + RRA + RRA + AND 0x1f + ADD A, A ; *2 + ADD A, 64 ; bytes per row + LD H, A + ; select sheet 0|1 + LD A, C + AND 0x1 + ADD A, H + LD H, A + ; HL = pix addr, turn on VRAM access + LD A, 0x1 + OUT (SYS_DD17PB), A + LD E, (HL) ; read pixel + INC H ; HL += 512 + INC H + LD D, (HL) ; read pixel row+1 + + ; turn off VRAM access + ;v8 XOR A + LD A, 0 + OUT (SYS_DD17PB), A +.for_all_pix: + DEC B + JP M, .all_shifted + ; shift pixels D >> [CF] >> E + LD A, D + RRA + LD D, A + LD A, E + RRA + LD E, A + JP .for_all_pix +.all_shifted: + LD A, E + LD D, 0 + RRA + JP NC, .not_1_1 + LD D, 00110000b +.not_1_1: + RRA + JP NC, .not_1_2 + LD A, D + OR 11000000b + LD D, A +.not_1_2: + LD A, D + POP BC + POP DE + RET + +esc_set_palette: + LD A, (M_VARS.esc_param) + AND 00111111b ; bgcol[2,1,0],pal[2,1,0] + LD (M_VARS.cur_palette), A + LD B, A + LD A, (M_VARS.screen_mode) + AND 00000011b + LD A, 0x0 + JP NZ, esp_no_colr + LD A, 0x40 + +esp_no_colr: + OR B + OUT (VID_DD67PB), A + RET + +esc_set_charset: + LD A, (M_VARS.esc_param) + AND 0x3 ; charset 0..3 + LD (M_VARS.codepage), A + RET + +; ------------------------------------------------------ +; Get address for draw symbol glyph +; Inp: A - ascii code +; Out: HL -> glyph offset +; ------------------------------------------------------ +m_get_glyph: + LD L, A ; L = ascii code + LD E, A ; E = ascii code + XOR A + LD D, A + LD H, A + ; HL = DE = ascii code + ADD HL, HL + ADD HL, DE + ADD HL, HL + ADD HL, DE + ; HL = A * 7 + LD A, E ; A = A at proc entry + CP '@' + ; First 64 symbols is same for all codepages + JP M, .cp_common + LD A, (M_VARS.codepage) + OR A + ; cp=0 - Latin letters + JP Z, .cp_common + DEC A + ; cp=1 - Russian letters + JP Z, .cp_rus + ; cp=2 - 0x40..0x5F - displayed as Lat + ; 0x60 - 0x7F - displayed as Rus + LD A, E + CP 0x60 + JP M, .cp_common +.cp_rus: + LD DE, 448 ; +448=64*7 Offset for cp1 + ADD HL, DE + +.cp_common: + LD DE, m_font_cp0-224 ; m_font_cp0-32*7 + ADD HL, DE ; add symbol glyph offset + RET + + +; -------------------------------------------------- +; Console output +; Inp: C - char +; -------------------------------------------------- +m_print_no_esc: + LD A, C + AND 0x7f ; C = 0..127 ASCII code + CP ASCII_SP ; C < ' '? + JP M, m_handle_esc_code ; jump if less + CALL m_get_glyph + EX DE, HL + LD A, (M_VARS.screen_mode) + AND 0x3 + JP NZ, mp_mode_64 ; jump to non color modes + + CALL calc_addr_40 + INC L + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + DEC H + DEC H + ; one or two bytes + LD A, B + OR B + JP Z, .l1 + DEC B + JP Z, .l2 + DEC B + JP Z, .l3 + JP .l4 +.l1: + INC H + INC H + LD BC, 0xffc0 + LD A, 0x0 + JP .l5 +.l2: + LD BC, 0xf03f + LD A, 0x6 + JP .l5 +.l3: + LD BC, 0xfc0f + LD A, 0x4 + JP .l5 +.l4: + LD BC, 0xff03 + LD A, 0x2 +.l5: + LD (M_VARS.esc_var1), A + EX DE, HL + +.sym_draw: + LD A, (M_VARS.esc_var1) + PUSH HL + LD L, (HL) + LD H, 0x0 + OR A + JP Z, .pne_l8 + +.pne_l7: + ADD HL, HL + DEC A + JP NZ, .pne_l7 + +.pne_l8: + EX DE, HL + LD A, (HL) + AND C + LD (HL), A + LD A, (M_VARS.curr_color) + AND E + OR (HL) + LD (HL), A + INC H + LD A, (HL) + AND C + LD (HL), A + LD A, (M_VARS.curr_color+1) + AND E + OR (HL) + LD (HL), A + INC H + LD A, (HL) + AND B + LD (HL), A + LD A, (M_VARS.curr_color) + AND D + OR (HL) + LD (HL), A + INC H + LD A, (HL) + AND B + LD (HL), A + LD A, (M_VARS.curr_color+1) + AND D + OR (HL) + LD (HL), A + INC L + DEC H + DEC H + DEC H + EX DE, HL + POP HL + INC HL + LD A, (M_VARS.esc_var0) + DEC A + LD (M_VARS.esc_var0), A + JP NZ, .sym_draw + + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + + ; draw cursor on return + LD HL, m_draw_cursor + PUSH HL + LD HL, M_VARS.cursor_row + +; -------------------------------------------------- +; Handle ASCII_CAN (cursor right) +; Inp: HL - cursor pos +; -------------------------------------------------- +m40_rt: + INC HL + LD A, (HL) ; a = col + ADD A, 1 ; col+1 + AND 0x3f ; screen column 0..63 + LD (HL), A ; save new col + CP 40 + DEC HL + RET M ; Return if no wrap + +m40_wrap_rt: + INC HL + XOR A + LD (HL), A + DEC HL + LD A, (M_VARS.screen_mode) + AND 0x08 ; screen_mode=8? + JP NZ, m2_lf + +; -------------------------------------------------- +; Handle ASCII_LF (cursor down) +; Inp: HL - cursor pos +; -------------------------------------------------- +m40_lf: + LD A, (HL) + ADD A, 10 + CP 248 + JP NC, scroll_up + LD (HL), A + RET + +; -------------------------------------------------- +; Handle ASCII_BS (cursor left) +; Inp: HL - cursor pos +; -------------------------------------------------- +m40_bksp: + INC HL + LD A, (HL) + DEC A + AND 0x3f ; A=0..63 + CP 0x3f + JP Z, .wrap + LD (HL), A + DEC HL + RET + +.wrap: + LD A, 39 + LD (HL), A + DEC HL + ; and cursor up + +; -------------------------------------------------- +; Handle ASCII_EM (cursor up) +; Inp: HL - cursor pos +; -------------------------------------------------- +m40_up: + LD A, (HL) + SUB 10 ; 10 rows per symbol + JP NC, .up_no_minus + LD A, 240 ; wrap to bottom +.up_no_minus: + LD (HL), A + RET + +; -------------------------------------------------- +; Handle ASCII_TAB (cursor right 8 pos) 20rows mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m20_tab: + INC HL + LD A, (HL) + ADD A, 8 + AND 0x3f ; wrap A=0..63 + LD (HL), A + CP 40 + DEC HL + RET M ; ret if column <40 + JP m40_wrap_rt ; or wrap to next line + +; -------------------------------------------------- +; Calculate VRAM address in 40 column mode +; -------------------------------------------------- +calc_addr_40: + LD HL, (M_VARS.cursor_row) + LD A, (M_VARS.row_shift) + ADD A, L + LD L, A + LD A, H + CP 4 + LD B, A + JP M, .l2 + AND 0x3 + LD B, A + LD A, H + OR A + RRA + OR A + RRA + LD C, A + LD H, 0x6 + XOR A + +.l1: + ADD A, H + DEC C + JP NZ, .l1 + ADD A, B + +.l2: + ADD A, B + ADD A, 66 + LD H, A + LD A, 0x7 + LD (M_VARS.esc_var0),A + RET + +m2_lf: + LD A, (HL) + ADD A, 10 + CP 15 + JP NC, .lf_nowr + LD (HL), A + RET + +.lf_nowr: + LD A, (M_VARS.row_shift) + LD L, A + ADD A, ASCII_LF + LD E, A + LD C, ASCII_BS + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + +.cas_l5: + LD B, 64 + LD H, B ; 0x40 + LD D, H + +.cas_l6: + LD A, (DE) + LD (HL), A + INC H + INC D + DEC B + JP NZ, .cas_l6 + INC L + INC E + DEC C + JP NZ, .cas_l5 + LD C, 10 + LD A, (M_VARS.row_shift) + ADD A, 8 + LD E, A + +.cas_l7: + LD B, 64 + LD D, B ; 0x40 + XOR A + +.cas_l8: + LD (DE),A + INC D + DEC B + JP NZ,.cas_l8 + INC E + DEC C + JP NZ,.cas_l7 + LD A,0x0 + OUT (SYS_DD17PB),A + RET + + +; --------------------------------------------------- +; Handle ASCII_BS (cursor left) in 20row mode +; --------------------------------------------------- +m20_bksp: + INC HL + LD A, (HL) + OR A + DEC HL + RET Z + + INC HL + DEC A + AND 0x3f + LD (HL), A + DEC HL + RET + +; --------------------------------------------------- +; Print symbol in 64x25 mode +; --------------------------------------------------- +mp_mode_64: + CP 3 ; + JP Z, mp_mode_80 ; jump for screen_mode=3 + ; calc symbol address in VRAM + LD HL, (M_VARS.cursor_row) + LD A, (M_VARS.row_shift) + ADD A, L + LD L, A + LD A, H + ADD A, 0x40 + LD H, A + ; + LD C, 7 ; symbol height + + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + EX DE, HL + XOR A + LD (DE), A + INC E + +.next_row: + LD A, (HL) + ADD A, A + LD (DE), A + INC HL + INC E + DEC C + JP NZ, .next_row + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + ; draw cursor at end + LD HL, m_draw_cursor + PUSH HL + LD HL, M_VARS.cursor_row + +; -------------------------------------------------- +; Handle ASCII_CAN (cursor right) in 64x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m64_rt: + INC HL + LD A, (HL) + ADD A, 1 + AND 0x3f ; wrap + LD (HL), A + DEC HL + RET NZ ; ret if no wrap + +; -------------------------------------------------- +; Handle ASCII_LF (cursor down) in 64x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m64_lf: + LD A, (HL) + ADD A, 10 + CP 248 + JP NC, scroll_up + LD (HL), A + RET + +; -------------------------------------------------- +; Scroll Up for 10 rows +; -------------------------------------------------- +scroll_up: + LD A, (M_VARS.row_shift) + ADD A, 10 + OUT (SYS_DD17PA), A ; Scroll via VShift register + LD (M_VARS.row_shift), A ; store new VShift value + ; calc bottom 16 rows address in VRAM + LD HL, 0x40f0 ; 240th VRAM byte + ADD A, L + LD L, A + LD C, H + + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + XOR A + LD DE, 0x1040 ; D=16 E=64 (512/8 bytes in row) + +.next_row: + LD H, C + LD B, E + + ; clear 64 bytes (512px in mono or 256px in color mode) +.next_col: + LD (HL), A + INC H ; next column + DEC B + JP NZ, .next_col + INC L ; next row address + DEC D ; row counter - 1 + JP NZ, .next_row + + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +; -------------------------------------------------- +; Handle ASCII_BS (cursor left) in 64x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m64_bs: + INC HL + LD A, (HL) + DEC A + AND 0x3f ; wrap column (0..63) + LD (HL), A + CP 63 + DEC HL + RET NZ + ; cursor up if wrapped + +; -------------------------------------------------- +; Handle ASCII_EM (cursor up) in 64x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m64_up: + LD A, (HL) + SUB 10 + JP NC, .no_wrap + LD A, 240 + +.no_wrap: + LD (HL), A + RET + +; -------------------------------------------------- +; Handle ASCII_TAB (cursor column + 8) in 64x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m64_tab: + INC HL + LD A, (HL) + ADD A, 8 + AND 0x38 + LD (HL), A + DEC HL + RET NZ ; return if no wrap + ; cursor down if wrap + JP m64_lf + +; -------------------------------------------------- +; Print symbols in 80x25 mode +; -------------------------------------------------- +mp_mode_80: + CALL calc_addr_80 + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + ; fix address + EX DE, HL + INC E + ; make bitmask + LD A, B + OR A + JP Z, .l1 + DEC A + JP Z, .l2 + DEC A + JP Z, .l3 + JP .l4 + +.l1: + LD B, (HL) + LD A, (DE) + AND 0xc0 + OR B + LD (DE), A + INC HL + INC E + DEC C + JP NZ, .l1 + JP .l6 +.l2: + LD A, (HL) + RRCA + RRCA + AND 0x7 + LD B, A + LD A, (DE) + AND 0xf0 + OR B + LD (DE), A + LD A, (HL) + RRCA + RRCA + AND 0xc0 + LD B, A + DEC D + LD A, (DE) + AND 0x1f + OR B + LD (DE), A + INC D + INC HL + INC E + DEC C + JP NZ, .l2 + JP .l6 +.l3: + LD A, (HL) + RRCA + RRCA + RRCA + RRCA + AND 0x1 + LD B, A + LD A, (DE) + AND 0xfc + OR B + LD (DE), A + LD A, (HL) + RRCA + RRCA + RRCA + RRCA + AND 0xf0 + LD B, A + DEC D + LD A, (DE) + AND 0x7 + OR B + LD (DE), A + INC D + INC HL + INC E + DEC C + JP NZ, .l3 + JP .l6 +.l4: + DEC D +.l5: + LD A, (HL) + RLCA + RLCA + LD B, A + LD A, (DE) + AND 0x1 + OR B + LD (DE), A + INC HL + INC E + DEC C + JP NZ, .l5 + INC D + +.l6: + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + ; Draw cursor after symbol + LD HL, m_draw_cursor + PUSH HL + LD HL, M_VARS.cursor_row + +; -------------------------------------------------- +; Handle ASCII_CAN (cursor right) in 80x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m80_rt: + INC HL + LD A, (HL) + ADD A, 1 ; inc column + AND 0x7f + LD (HL), A + CP 80 + DEC HL + RET M ; return if no wrap + +m80_col_wrap: + INC HL + XOR A + LD (HL), A + DEC HL + ; and move cursor to next row + +; -------------------------------------------------- +; Handle ASCII_LF (cursor down) in 80x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m80_lf: + LD A, (HL) + ADD A, 10 + CP 248 + JP NC, scroll_up + LD (HL), A + RET + +; -------------------------------------------------- +; Handle ASCII_BS (cursor left) in 80x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m80_bs: + INC HL + LD A, (HL) + DEC A + AND 0x7f ; mask [0..127] + CP 127 + JP Z, .wrap + LD (HL), A + DEC HL + RET + +.wrap: + LD A, 79 + LD (HL), A + DEC HL + ; and move cursor to previous line + +; -------------------------------------------------- +; Handle ASCII_EM (cursor up) in 80x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m80_up: + LD A, (HL) + SUB 10 + JP NC, .no_wrap + LD A, 240 + +.no_wrap: + LD (HL), A + RET + +; -------------------------------------------------- +; Handle ASCII_TAB (cursor column + 8) in 80x25 mode +; Inp: HL - cursor pos +; -------------------------------------------------- +m80_tab: + INC HL + LD A, (HL) + ADD A, 8 + AND 0x7f + LD (HL), A + CP 80 + DEC HL + RET M ; return if no cursor wrap + JP m80_col_wrap + +; -------------------------------------------------- +; Calculate address for cursor pos for 80x25 mode +; Out: HL -> VRAM +; B -> pixel pos in byte +; -------------------------------------------------- +calc_addr_80: + LD HL, (M_VARS.cursor_row) + LD A, (M_VARS.row_shift) + ADD A, L + LD L, A + LD A, H + CP 4 + LD B, A + JP M, mns_ep_fm_0 + AND 3 + LD B, A + LD A, H + OR A + RRA + OR A + RRA + LD C, A + LD H, 3 + XOR A + +mns_l1: + ADD A, H + DEC C + JP NZ, mns_l1 + ADD A, B + +mns_ep_fm_0: + ADD A, 0x42 + LD H, A + LD C, 0x7 + RET + +; -------------------------------------------------- +; Clear screen and set cursor to 0,0 +; Inp: HL -> cursor position +; -------------------------------------------------- +m_clear_screen: + LD A, (M_VARS.screen_mode) + AND 0x8 + JP NZ, m_clear_20_rows ; for bit 4 is set, clear only 20 rows + ; all in black + LD A, 01111111b + OUT (VID_DD67PB), A ; C/M=1 FL=111 CL=111 All black + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + LD DE, video_ram + EX DE, HL + LD A, H + ADD A, 0x40 ; A=0x80 + LD B, 0 + +.fill_scrn: + LD (HL), B + INC HL + CP H + JP NZ, .fill_scrn ; fill while HL<0x8000 + + EX DE, HL + LD A, (M_VARS.cur_palette) + LD B, A ; B = current palette + LD A, (M_VARS.screen_mode) + AND 0x3 ; color? + LD A, 0x0 + JP NZ, .mono_mode + LD A, 01000000b +.mono_mode: + OR B + ; Restore mode and palette + OUT (VID_DD67PB), A + + ; And set cursor to home position + +; -------------------------------------------------- +; Set cursor to 0,0 and close VRAM access +; Inp: HL -> cursor_row +; -------------------------------------------------- +m_cursor_home: + XOR A + NOP + NOP + LD (HL), A + INC HL + XOR A + LD (HL), A + DEC HL + ;XOR A + LD A, 0 + ; Disable VRAM access + OUT (SYS_DD17PB), A + RET + +; Clear only 20 rows +m_clear_20_rows: + ; take row shift in account + LD A, (M_VARS.row_shift) + LD L, A + LD C, 20 + + ; Access VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + +.next_row: + LD H, 0x40 ; HL = 0x4000 + shift_row + LD B, 64 ; 64 bytes at row + XOR A +.next_col: + LD (HL), A + INC H ; next column + DEC B + JP NZ, .next_col + INC L ; next row + DEC C + JP NZ, .next_row + ; Disabe VRAM access + LD A, 0 + OUT (SYS_DD17PB), A + JP m_cursor_home + +; -------------------------------------------------- +; Draw cursor at current cursor position +; if not hidden +; -------------------------------------------------- +m_draw_cursor: + LD A, (M_VARS.screen_mode) + AND 0x4 ; check hidden cursor bit + RET NZ ; return if hidden + LD A, (M_VARS.screen_mode) + AND 0x3 ; check color mode (40 column mode 6x7 font) + JP NZ, .dc_mode_64 + + EX DE, HL + LD HL, (M_VARS.cursor_row) + LD A, H ; cursor column + CP 40 ; > 40? + EX DE, HL + RET P ; ret if column out of screen + + PUSH HL + EX DE, HL + CALL calc_addr_40 + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + ; previous address + DEC H + DEC H + INC L + LD C, 7 ; cursor size + ; build masks + LD A, B + OR B + JP Z, .dc_rt2 + DEC B + JP Z, .dc_mid + DEC B + JP Z, .dc_lt + JP .dc_rt1 +.dc_rt2: + INC H + INC H + LD DE, 0x001f + JP .dc_put +.dc_mid: + LD DE, 0x07c0 + JP .dc_put +.dc_lt: + LD DE, 0x01f0 + JP .dc_put +.dc_rt1: + LD DE, 0x007c + +.dc_put: + ; xor cursor mask with VRAM[HL] value + ; left bytes + LD A, (HL) + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR E + LD (HL), A + ; right bytes + INC H + LD A, (HL) + XOR D + LD (HL), A + INC H + LD A, (HL) + XOR D + LD (HL), A + ; next cursor row address + INC L + DEC H + DEC H + DEC H + DEC C + JP NZ, .dc_put ; draw next cursor row if c>0 + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + POP HL + RET + + ; draw cursor in 64 column mode +.dc_mode_64: + CP 3 ; screen_mode = 3 - 80 rows + JP Z, .dc_mode_80 + EX DE, HL + LD HL, (M_VARS.cursor_row) ; H - col, L - row + ; take into account the vertical shift + LD A, (M_VARS.row_shift) + ADD A, L + LD L, A + ; + LD A, H + CP 64 ; check column + EX DE, HL + RET P ; return if column out of screen + EX DE, HL + ; calc VRAM address + ADD A, 0x40 + LD H, A + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + LD BC, 0x7f08 ; B=01111111b - mask, C=8 - cursor size +.cur_64_next: + ; xor with VRAM content + LD A, (HL) + XOR B + LD (HL), A + ; next row address + INC L + DEC C + JP NZ, .cur_64_next + EX DE, HL + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + + ; draw cursor in 80 column mode +.dc_mode_80 + EX DE, HL + LD HL, (M_VARS.cursor_row) + + LD A, H + CP 80 + EX DE, HL + RET P ; return if column > 80 + + PUSH HL + CALL calc_addr_80 + LD C, 7 ; cursor size + INC L + + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + ; mask + LD A, B + OR A + LD B, 0x1f + JP Z, .dc_1_byte + DEC A + LD DE, 0xc007 + JP Z, .dc_2_byte + DEC A + LD DE, 0xf001 + JP Z, .dc_2_byte + LD B, 0x7c + DEC H + ;JP .dc_1_byte ; TODO: unused + +.dc_1_byte: + ; xor with VRAM byte + LD A, (HL) + XOR B + LD (HL), A + INC L + DEC C + JP NZ, .dc_1_byte + JP .dc_80_end + +.dc_2_byte: + ; xor with previous byte + DEC H + LD A, (HL) + XOR D + LD (HL), A + ; xor with current byte + INC H + LD A, (HL) + XOR E + LD (HL), A + ; next cursor address + INC L + DEC C + JP NZ, .dc_2_byte + +.dc_80_end: + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + POP HL + RET + +; -------------------------------------------------- +; If ESC character, turn esc_mode ON +; Inp: A - ASCII symbol +; -------------------------------------------------- +m_handle_esc_code: + CP ASCII_ESC + JP NZ, m_handle_control_code + ; turn on ESC mode for next chars + LD HL, M_VARS.esc_mode + LD (HL), 0x1 ; turn on ESC mode + INC HL + LD (HL), 0xff ; esc_cmd = 0xff + RET + +; -------------------------------------------------- +; Handle one byte ASCII control code +; Inp: A - ASCII symbol +; -------------------------------------------------- +m_handle_control_code: + CP ASCII_BELL + JP Z, m_beep + LD HL, m_draw_cursor + PUSH HL + LD HL, M_VARS.cursor_row + PUSH AF + CALL m_draw_cursor + LD A, (M_VARS.screen_mode) + AND 0x08 ; 20-rows mode? + JP Z, handle_cc_common ; jump for normal screen modes + + ; for hidden cursor modes + POP AF + CP ASCII_TAB ; TAB + JP Z, m20_tab + CP ASCII_BS ; BKSP + JP Z, m20_bksp + CP ASCII_CAN ; Cancel + JP Z, m40_rt + CP ASCII_US ; ASCII Unit separator + JP Z, m_clear_20_rows + CP ASCII_LF ; LF + JP Z, m2_lf + CP ASCII_CR ; CR + RET NZ ; ret on unknown + INC HL + LD (HL), 0x0 + DEC HL + RET + +; -------------------------------------------------- +; Handle cursor for 40x25, 64x25, 80x25 modes +; -------------------------------------------------- +handle_cc_common: + POP AF + CP ASCII_US + JP Z, m_clear_screen + CP ASCII_FF + JP Z, m_cursor_home + PUSH AF + LD A, (M_VARS.screen_mode) + AND 3 ; check for color modes + JP NZ, .handle_cc_mono + ; 32x25 text mode + POP AF + CP ASCII_TAB ; cursor right +8 + JP Z, m20_tab + CP ASCII_BS ; cursor left + JP Z, m40_bksp + CP ASCII_CAN ; cursor right + JP Z, m40_rt + CP ASCII_EM ; cursor up + JP Z, m40_up + CP ASCII_SUB + JP Z, m40_lf ; cursor down + CP ASCII_LF + JP Z, m40_lf + CP ASCII_CR + RET NZ + INC HL + LD (HL), 0x0 ; move cursor to first column for CR + DEC HL + RET + +; -------------------------------------------------- +; Handle control chars for 64x25 or 80x25 modes +; -------------------------------------------------- +.handle_cc_mono: + LD A, (M_VARS.screen_mode) + CP 3 + JP Z, handle_cc_80x25 + CP 7 + JP Z, handle_cc_80x25 + ; 64x25 screen mode + POP AF + CP ASCII_TAB + JP Z, m64_tab + CP ASCII_BS + JP Z, m64_bs + CP ASCII_CAN + JP Z, m64_rt + CP ASCII_EM + JP Z, m64_up + CP ASCII_SUB + JP Z, m64_lf + CP ASCII_LF + JP Z, m64_lf + CP ASCII_CR + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +; -------------------------------------------------- +; Handle control chars for 80x25 modes +; -------------------------------------------------- +handle_cc_80x25: + POP AF + CP ASCII_TAB + JP Z, m80_tab + CP ASCII_BS + JP Z, m80_bs + CP ASCII_CAN + JP Z, m80_rt + CP ASCII_EM + JP Z, m80_up + CP ASCII_SUB + JP Z, m80_lf + CP ASCII_LF + JP Z, m80_lf + CP ASCII_CR + RET NZ + INC HL + LD (HL), 0x0 + DEC HL + RET + +; -------------------------------------------------- +; +; -------------------------------------------------- +m_beep: + LD HL, (M_VARS.beep_duration) + EX DE, HL + LD HL, (M_VARS.beep_period) + LD A, 00110110b ; TMR#0 LSB+MSB Square Wave Generator + OUT (TMR_DD70CTR), A + LD A, L ; LSB + OUT (TMR_DD70C1), A + LD A, H ; MSB + OUT (TMR_DD70C1), A + LD A, (M_VARS.strobe_state) + LD B, A +m_bell_cont: + LD A, D ; DE=duration + OR E + RET Z ; ret if enough + DEC DE + LD A, B + XOR BELL_PIN + LD B, A + OUT (DD67PC), A ; Invert bell pin +m_bell_wait_tmr1: + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; 0x10 + JP NZ, m_bell_wait_tmr1 + LD A, B + XOR BELL_PIN ; Flip pin again + LD B, A + OUT (DD67PC), A +m_bell_wait_tmr2: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP Z,m_bell_wait_tmr2 + JP m_bell_cont + + +; ------------------------------------------------------ +; 5 Set cursor position +; ------------------------------------------------------ +esc_set_cursor: + CALL m_draw_cursor + LD DE, M_VARS.esc_param + LD HL, M_VARS.cursor_col + INC DE + LD A, (DE) ; column + SUB 32 + LD B, A + LD A, (M_VARS.screen_mode) + CP 3 + JP Z, .mode_80 + CP 7 + JP Z, .mode_80 + OR A + JP Z, .mode_40 + CP 4 + JP Z, .mode_40 + ; mode 64x25 + LD A, B + CP 64 + JP M, .common + LD A, 64 + JP .common + ; mode 40x25 +.mode_40: + LD A, B + CP 40 + JP M, .common + LD A, 40 + JP .common + ; mode 80x25 +.mode_80: + LD A, B + CP 80 + JP M, .common + LD A, 80 +.common: + LD (HL), A + DEC DE + DEC HL + LD A, (DE) + SUB 32 + CP 24 + JP C, esc_le_24 + LD A, 24 +esc_le_24: + LD B, A + ADD A, A + ADD A, A + ADD A, B + ADD A, A + LD (HL), A + CALL m_draw_cursor ; TODO change call+ret to jp + RET ; + +; ------------------------------------------------------ +; 6n Set video mode or cursor visibility +; Inp: n is +; 0 - C 32x25 with cursor; 0000 +; 1 - M 64x25 with cursor; 0001 +; 2 - M 64x25 with cursor; 0010 +; 3 - M 80x25 with cursor; 0011 +; 4 - C 32x25 no cursor; 0100 +; 5 - M 64x25 no cursor; 0101 +; 6 - M 64x25 no cursor; 0110 +; 7 - M 80x25 no cursor; 0111 +; 8 - M 20rows mode 1000 +; 9 - hide cursor 1001 +; 10 - show cursor 1010 +; ------------------------------------------------------ +esc_set_vmode: + LD HL, M_VARS.screen_mode + LD A, (M_VARS.cur_palette) + LD B, A + LD A, (M_VARS.esc_param) ; first parameter - video mode + AND 0xf + CP 11 + RET NC ; return if not valid input parameter + CP 9 + JP Z, .cursor_hide + CP 10 + JP Z, .cursor_show + LD (HL), A ; store new mode + CP 4 + JP Z, .set_color_mode + AND 0x3 ; monochrome (80x25, 64x25) mode? + LD A, 0 ; mode 512x254 mono + JP NZ, .skip_for_mono_mode + ; mode=0 or 4 -> 256x256px color +.set_color_mode: + LD A, 0x40 ; color mode +.skip_for_mono_mode: + OR B ; color mode with palette + OUT (VID_DD67PB), A ; configure screen mode + + LD HL, M_VARS.cursor_row + CALL m_clear_screen + +.draw_cursor: + CALL m_draw_cursor ; TODO change call+ret to jp + RET + +.cursor_hide: + LD A, (HL) ; screen_mode + OR 00000100b ; cursor hide + LD (HL), A + LD HL, M_VARS.cursor_row + JP .draw_cursor + +.cursor_show: + LD A, (HL) ; screen_mode + AND 11111011b ; cursor show + LD (HL), A + JP .draw_cursor + + +; ------------------------------------------------------ +; 4n n=1..4 Set drawing color +; ------------------------------------------------------ +esc_set_color: + LD A, (M_VARS.esc_param) +m_set_color: + AND 0x3 + RRA + LD B, A + LD A, 0x0 ; TODO: unused + SBC A, A + LD (M_VARS.curr_color), A + LD A, B + DEC A + CPL + LD (M_VARS.curr_color+1), A + RET + +;--------------------------------------------------- +; Print symbol or print sprite at X,Y coordinates +; Inp: param x,y +; C - character or sprite_no to draw +;--------------------------------------------------- +m_print_at_xy: + ; check video mode + LD A, (M_VARS.screen_mode) + AND 0x3 ; color? + JP NZ, esc_exit ; exit for mono modes + + LD A, C + AND 0x7f + LD C, A ; C = C with 7th bit reset + CP 0x1 + JP Z, .sprites_en ; enable sprite mode + + CP ASCII_SP + JP M, mode2_exit ; codes 0..31 - turm off game_mode + + ; check X, Y range to prevent drawing symbols out of screen + LD HL, M_VARS.esc_param + LD A, (HL) + LD E, A + ADD A, 8 + JP C, mode2_exit ; exit if esc_param[0]>247 + LD (HL), A + INC HL ; HL -> esc_param[1] + LD A, 247 + CP (HL) + JP C, mode2_exit ; exit if esc_param[1]>247 + ; calculate X,Y pixel address in VRAN + LD D, (HL) + CALL calc_px_addr + ; HL - address, B - pixel pos in byte + LD A, L + SUB 8 + LD L, A + PUSH HL ; save address + + LD A, (M_VARS.esc_var2) + OR A + JP NZ, .mode_sp + + ; font + LD A, C + CALL m_get_glyph + LD C, 7 + POP DE + INC E + JP .out_sp + + ; sprite mode +.mode_sp: + LD A, C + SUB 32 + CP 35 + JP NC, co_ex_l08 + + ; Calc sprite address + LD L, A ; HL=A - sprite_no + XOR A + LD H, A + ADD HL, HL + ADD HL, HL + ADD HL, HL ; HL=HL*8 + LD DE, game_sprite_tab + ADD HL, DE ; HL -> sprite + LD C, 8 ; bytes count + POP DE + + ; Out sprite + ; DE -> VRAM address + ; C - height +.out_sp: + LD A, (M_VARS.esc_param+2) + DEC A + JP Z, out_no_xor + +.next_line: + PUSH HL + ; Access Video RAM + LD A, 0x1 + OUT (SYS_DD17PB), A + LD L, (HL) ; load from table + LD H, 0x0 + LD A, B + OR A + JP Z, .l05 +.l04: + ADD HL, HL + DEC A + JP NZ, .l04 +.l05: + EX DE, HL + LD A, (M_VARS.curr_color) + AND E + XOR (HL) + LD (HL), A + INC H + INC H + LD A, (M_VARS.curr_color) + AND D + XOR (HL) + LD (HL), A + DEC H + LD A, (M_VARS.curr_color+1) + AND E + XOR (HL) + LD (HL), A + INC H + INC H + LD A, (M_VARS.curr_color+1) + AND D + XOR (HL) + LD (HL), A + DEC H + DEC H + DEC H + INC L + EX DE, HL + ; Disable VRAM + LD A, 0x0 + OUT (SYS_DD17PB), A + POP HL + INC HL + DEC C + JP NZ, .next_line + RET + +.sprites_en: + LD (M_VARS.esc_var2), A + RET + +mode2_exit: + XOR A + LD (M_VARS.esc_var2), A + JP esc_exit + +co_ex_l08: + POP DE + JP mode2_exit + +out_no_xor: + PUSH HL + ; Acess to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + LD L, (HL) + LD H, 0x0 + LD A, B + OR A + JP Z, .l11 +.l10: + ADD HL, HL + DEC A + JP NZ, .l10 +.l11: + EX DE, HL + PUSH BC + LD A, (M_VARS.curr_color) + CPL + LD B, A + LD A, (HL) + XOR B + OR E + XOR B + LD (HL), A + INC H + INC H + LD A, (HL) + XOR B + OR D + XOR B + LD (HL), A + DEC H + LD A, (M_VARS.curr_color+1) + CPL + LD B, A + LD A, (HL) + XOR B + OR E + XOR B + LD (HL), A + INC H + INC H + LD A, (HL) + XOR B + OR D + XOR B + LD (HL), A + DEC H + DEC H + DEC H + INC L + EX DE, HL + POP BC + + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + + POP HL + INC HL + DEC C + JP NZ, out_no_xor + RET + + ; Binary data to draw sprites + ; game_sprite_tab: + INCLUDE "sprites.inc" + +; -------------------------------------------------- +; Calculate address of pixel in Video RAM +; Inp: DE - Y, X +; Out: HL - address +; B - offset in byte +; -------------------------------------------------- +calc_px_addr: + ; take into account the vertical displacement + LD A, (M_VARS.row_shift) + SUB D + DEC A + LD L, A + + LD A, E + AND 0x07 ; X mod 8 - offset in byte + LD B, A + + LD A, E + RRA + RRA + AND 00111110b + ADD A, 0x40 ; VRAM at 0x4000 + LD H, A + RET + + +;--------------------------------------------------- +; Draw filled rectanger +; Inp: esc param X1,Y2,X2,Y2 +; -------------------------------------------------- +esc_draw_fill_rect: + LD HL, M_VARS.esc_param + LD E, (HL) ; E=X1 + INC HL + LD C, (HL) ; C=Y1 + INC HL + INC HL + LD D, (HL) ; D=Y2 + LD A, D + SUB C ; delta Y + JP NZ, .non_zero_h + INC A ; 1 as minimum +.non_zero_h: + LD C, A ; C = height + ; DE = Y2, X1 + CALL calc_px_addr + ; HL -> videomem offset, b - pixel offset + + ; build pixel mask + XOR A +.shift_mask_l: + SCF + RLA + DEC B + JP P, .shift_mask_l + RRA + LD (M_VARS.pixel_mask_l), A + CPL ; invert + LD (M_VARS.pixel_mask_l_i), A + LD A, (M_VARS.esc_param+2) ; X2 + AND 0x7 ; 0..7 + LD B, A + XOR A +.shift_mask_r: + SCF + RLA + DEC B + JP P, .shift_mask_r + LD (M_VARS.pixel_mask_r_i), A + LD B, C + ; calc end address + LD A, (M_VARS.esc_param+2) ; X2 + RRA + RRA + AND 00111110b + ADD A, 0x40 + SUB H + RRCA + LD C, A ; C - width + INC B + LD A, (M_VARS.esc_param+4) + DEC A + JP NZ, .rectangle_xor + LD A, (M_VARS.pixel_mask_r_i) + CPL + LD (M_VARS.pixel_mask_r), A + LD D, A + LD A, (M_VARS.pixel_mask_l) + LD E, A + ; draw B horisontal lines +.next_line: + PUSH DE + PUSH HL + PUSH BC + CALL draw_line_h + POP BC + POP HL + POP DE + INC L + DEC B + JP NZ, .next_line + RET + + ; draw B horisontal lines (xor) +.rectangle_xor: + LD A, (M_VARS.pixel_mask_r_i) + LD (M_VARS.pixel_mask_r), A + LD D, A + LD A, (M_VARS.pixel_mask_l_i) + LD E, A + ; Access to VideoRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + +.edf_l6: + PUSH DE + PUSH HL + PUSH BC + LD A, C + OR A + JP NZ, .w_ne_0 ; jump if width != 0 + LD A, E ; merge masks E=E or D + OR D +.next_8px: + LD E, A +.w_ne_0: + LD B, E ; B - mask + EX DE, HL + LD HL, (M_VARS.curr_color) ; color + EX DE, HL + ; Set pixels - VideoRAM[HL] = color xor VideoRAM[HL] + LD A, E + AND B + XOR (HL) + LD (HL), A + ; And next byte + INC H + LD A, D + AND B + XOR (HL) + LD (HL), A + ; ---------- + INC H + LD A, C + OR A + JP Z, .complete + DEC C + ; right tail of line, use right mask +.r_mask: + LD A, (M_VARS.pixel_mask_r) + JP Z, .next_8px + ; full 8 bits without mask at middle of line +.next_full: + LD A, (HL) + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + LD (HL), A + INC H + DEC C + JP NZ, .next_full + JP .r_mask +.complete: + POP BC + POP HL + POP DE + INC L + DEC B + JP NZ, .edf_l6 + ; Disable VideoRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +;--------------------------------------------------- +; Paint screen +; Inp: params X,Y,Color,repColor +;--------------------------------------------------- +esc_paint: + ; Save stack + LD HL, 0x0 + ADD HL, SP + LD (M_VARS.paint_sp_save), HL + + ; Set our own stack + ;LD HL, M_VARS.paint_stack ; TODO: Z80 LD SP,var i800 - LXI SP,nn + ;LD SP, HL + LD SP, M_VARS.paint_stack + + ; save current color + LD HL, (M_VARS.curr_color) + LD (M_VARS.tmp_color), HL + + ; set color from param 3 + LD A, (M_VARS.esc_param+2) + DEC A + CALL m_set_color + + ; color to replace, from param 4 + LD A, (M_VARS.esc_param+3) + DEC A + LD (M_VARS.cmp_color), A + + ; HL - Y,X + LD A, (M_VARS.esc_param) + LD L, A + LD A, (M_VARS.esc_param+1) + LD H, A + LD (M_VARS.paint_y), A + + LD A, (M_VARS.esc_param+4) ; 0 - full fill, 1 - fast fill + DEC A + LD (M_VARS.esc_param), A + + LD A, 0x2 + LD (M_VARS.paint_var5), A ; task_no=2 + + EX DE, HL + CALL calc_px_addr + LD (M_VARS.esc_param+1), HL ; temporary ctore address of start fill point + ; make mask + LD A, 10000000b +.l1: + RLCA + DEC B + JP P, .l1 + + LD B, A + LD (M_VARS.esc_param+3), A ; store mask + + ; find left border + LD A, (M_VARS.cmp_color) + LD C, A + LD D, E ; D = X + CALL paint_find_left + ; find right border + LD HL, (M_VARS.esc_param+1) ; restore HL + LD A, (M_VARS.esc_param+3) ; restore mask + LD B, A + CALL paint_find_right + ; + LD HL, 0x0 + PUSH HL + PUSH HL + ; + LD A, (M_VARS.esc_param) ; A = fill mode + OR A + JP Z, ep_fm_0 + ; push fill task parameters + LD A, (M_VARS.paint_var5) + DEC A ; task_no-1 + LD H, A + LD L, E + PUSH HL + LD A, (M_VARS.paint_y) + LD H, A + LD L, D + PUSH HL + +ep_fm_0: + ; push fill task parameters + LD A, (M_VARS.paint_var5) ; task_no + LD H, A + LD L, E + PUSH HL + LD A, (M_VARS.paint_y) + LD H, A + LD L, D + PUSH HL + JP paint_task ; exec task + +ep_task_end: + LD A, (M_VARS.cmp_color) + LD C, A ; color to compare + + LD A, (M_VARS.esc_param) ; fill mode 0 - full, 1 - fast + OR A + JP NZ, ep_f_fast + + LD A, 0x2 + LD (M_VARS.paint_var7), A + LD A, (M_VARS.paint_var2) + CP 2 + JP Z, ep_l4 + JP ep_l5 ; TODO: change to one JP NZ + +ep_l4: + LD A, 1 + LD (M_VARS.paint_var5), A ; task_no? + JP ep_l8 + +ep_l5: + LD A, 2 + LD (M_VARS.paint_var5), A + JP ep_l11 + +ep_l6: + LD A, (M_VARS.paint_var7) + OR A + JP Z, paint_task + LD A, (M_VARS.paint_var2) + CP 2 + JP Z, ep_l5 ; TODO: change to one JP NZ + JP ep_l4 + +ep_f_fast: + LD A, (M_VARS.paint_var2) + LD (M_VARS.paint_var5), A + CP 1 ; TODO: DEC A - save 1b 3t + JP Z, ep_l8 ; TODO: change to one JP NZ + JP ep_l11 + +ep_l8: + LD A, (M_VARS.paint_var3) + LD D, A + LD A, (M_VARS.paint_var1) + LD E, A + LD HL, (M_VARS.esc_param+1) + LD A, (M_VARS.esc_param+3) + LD B, A + LD A, (M_VARS.paint_var4) + DEC A + JP Z, ep_l10 + LD (M_VARS.paint_y), A + INC L + CALL paint_find_next_right + JP Z, ep_l10 + LD HL, (M_VARS.esc_param+4) + LD A, (M_VARS.esc_param+6) + LD B, A + INC L + CALL paint_find_next_left + JP Z, ep_l10 + LD A, (M_VARS.esc_param) + OR A + JP NZ, ep_l9 + JP ep_l12 + +ep_l9: + LD A, (M_VARS.paint_var5) + LD H, A + LD L, E + PUSH HL + LD A, (M_VARS.paint_y) + LD H, A + LD L, D + PUSH HL + JP paint_task + +ep_l10: + LD A, (M_VARS.esc_param) + OR A + JP NZ, paint_task + LD A, (M_VARS.paint_var7) + DEC A + LD (M_VARS.paint_var7), A + JP ep_l6 + +ep_l11: + LD A, (M_VARS.paint_var3) + LD D, A + LD A, (M_VARS.paint_var1) + LD E, A + LD HL, (M_VARS.esc_param+1) + LD A, (M_VARS.esc_param+3) + LD B, A + LD A, (M_VARS.paint_var4) + INC A + CP 0xff + JP Z, ep_l10 + LD (M_VARS.paint_y), A + DEC L + CALL paint_find_next_right + JP Z, ep_l10 + LD HL, (M_VARS.esc_param+4) + LD A, (M_VARS.esc_param+6) + LD B, A + DEC L + CALL paint_find_next_left + JP Z, ep_l10 + LD A, (M_VARS.esc_param) + OR A + JP NZ, ep_l9 + JP ep_l12 + +; --------------------------------------------------- +; +; --------------------------------------------------- +paint_find_next_right: + CALL get_pixel + JP NZ, .l1 + CALL paint_find_left + LD A, 0xff + OR A + RET + +.l1: + LD A, D + CP E + RET Z + INC D + LD A, B + RLCA + LD B, A + JP NC, .l2 + INC H + INC H + +.l2: + CALL get_pixel + JP NZ, .l1 + LD A, 0xff + OR A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +paint_find_next_left: + CALL get_pixel + JP NZ, .l1 + CALL paint_find_right + LD A, 0xff + OR A + RET +.l1: + LD A, E + CP D + RET Z + DEC E + LD A, B + RRCA + LD B, A + JP NC, .l2 + DEC H + DEC H +.l2: + CALL get_pixel + JP NZ, .l1 + LD A, 0xff + OR A + RET + +ep_l12: + LD A, D + LD (M_VARS.pixel_mask_r), A + LD A, (M_VARS.paint_var5) + LD D, A + PUSH DE + LD A, (M_VARS.pixel_mask_r) + CP E + JP NZ, ep_l13 + LD L, A + LD A, (M_VARS.paint_y) + LD H, A + PUSH HL + JP ep_l16 +ep_l13: + LD D, E + CALL paint_find_left + LD E, D + LD A, (M_VARS.paint_y) + LD D, A + PUSH DE + LD A, (M_VARS.pixel_mask_r) + LD D, A + CP E + JP Z, ep_l16 +ep_l14: + DEC E + LD A, B + RRCA + LD B, A + JP NC, ep_l15 + DEC H + DEC H +ep_l15: + CALL get_pixel + JP NZ, ep_l14 + JP ep_l12 +ep_l16: + JP ep_l10 + +; --------------------------------------------------- +; Find rightmost pixel to fill +; In/Out: E = x_right +; HL - current pixel address +; B - pixel mask +; --------------------------------------------------- +paint_find_right: + LD A, E + CP 0xff + RET Z ; return if X=right border + INC E ; x=x+1 + ; rotate pixel mask right + LD A, B + RLCA + LD B, A + JP NC, .in_byte + ; inc addr+2 (2 byte per 8 pixels) + INC H + INC H + +.in_byte: + CALL get_pixel + JP Z, paint_find_right ; find until same color + ; border found, x-1 + DEC E + ; rotate mask back 1 px + LD A, B + RRCA + LD B, A + RET NC + ; addr-2 if previous byte + DEC H + DEC H + RET + +; --------------------------------------------------- +; Find leftmost pixel to fill +; In/Out: D = x_left +; HL - current pixel address +; B - pixel mask +; --------------------------------------------------- +paint_find_left: + LD A, D + OR A + RET Z ; return if x=0 + + DEC D ; x-1 + LD A, B + RRCA ; rotate mask to right + LD B, A + JP NC, .in_byte + DEC H ; addr-2 (2 byte for 8px) + DEC H + +.in_byte: + CALL get_pixel + JP Z, paint_find_left ; repeat until same color + + INC D ; border found, x+1 + ; mask rotate right + LD A, B + RLCA + LD B, A + RET NC + ; if CF, inc address+2 + INC H + INC H + RET + +; --------------------------------------------------- +; Inp: HL - address +; B - pixel mask +; C - color to compare +; Out: A - 0,1,2 +; ZF - set if color match +; --------------------------------------------------- +get_pixel: + ; Access to VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + ; get pixel and mask + LD A, (HL) + AND B + JP NZ, .bit1_set + INC H + LD A, (HL) + DEC H + AND B + JP NZ, .bit2_set + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + CP C + RET + +.bit1_set: + INC H + LD A, (HL) + DEC H + AND B + JP NZ, .bit12_set + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + LD A, 0x1 + CP C + RET + +.bit2_set: + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + LD A, 0x2 + CP C + RET + +.bit12_set: + LD A, 0x0 + OUT (SYS_DD17PB), A + LD A, 3 + CP C + RET + +paint_task: + POP HL ; L=x0, H=Y + LD (M_VARS.paint_var3), HL + EX DE, HL + + POP HL ; L=x1, H=mode + LD A, H + OR A + JP Z, paint_exit ; jump for mode=0 + + ; calc leftmost pixel address, mask for draw horisontal line + LD (M_VARS.paint_var1), HL + CALL calc_px_addr + LD (M_VARS.esc_param+1), HL + LD C, B + LD A, 0x80 + +.lmp_mask: + RLCA + DEC B + JP P, .lmp_mask + LD (M_VARS.esc_param+3), A + ; calc rightmos pixel address and mask + LD A, (M_VARS.paint_var1) + LD E, A + LD A, (M_VARS.paint_var4) + LD D, A + CALL calc_px_addr + LD (M_VARS.esc_param+4), HL + LD D, B + LD A, 0x80 + +.rmp_mask: + RLCA + DEC B + JP P, .rmp_mask + LD (M_VARS.esc_param+6), A + ;LD A, (M_VARS.esc_param+3) ; TODO: unused code + + XOR A +.lmi_mask: + SCF + RLA + DEC C + JP P, .lmi_mask + RRA + LD E, A ; E - left inv mask + + XOR A +.rmi_mask: + SCF + RLA + DEC D + JP P, .rmi_mask + CPL + LD D, A ; D - right inv mask + + LD (M_VARS.pixel_mask_r), A + LD HL, (M_VARS.esc_param+1) ; HL -> lext pix address + LD A, (M_VARS.esc_param+5) ; right pix address (low byte) + SUB H ; delta x + RRCA ; 2 byte for 8 pix + LD C, A ; C - line width + CALL draw_line_h + JP ep_task_end + +paint_exit: + LD HL, (M_VARS.tmp_color) ; restore previous current color + LD (M_VARS.curr_color), HL + LD HL, (M_VARS.paint_sp_save) ; restore previous stack + LD SP, HL + RET + +;--------------------------------------------------- +; Draw horizontal line +; Inp: C - width +; DE - left & right pixel mask +; HL - address of first byte of line +;--------------------------------------------------- +draw_line_h: + ; Access to VideoRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, C + OR A + JP NZ, .width_ne0 + LD A, E ; join left and right masks + OR D +.next_byte: + LD E, A +.width_ne0: + LD B, E + EX DE, HL + LD HL, (M_VARS.curr_color) + EX DE, HL + ; Get pixels, apply colors + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A ; store first + ; Same for second byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; move to next byte + INC H + LD A, C + OR A + JP Z, .complete + DEC C + +.r_mask: + ; use right mask for last right byte + LD A, (M_VARS.pixel_mask_r) + JP Z, .next_byte + +.full_8: + LD (HL), E + INC H + LD (HL), D + INC H + DEC C + JP NZ, .full_8 + JP .r_mask + +.complete: ; TODO: duplicate close_vram_ret + ; Disable VideoRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +;--------------------------------------------------- +; 2x1y1x2y2 Draw Line +;--------------------------------------------------- +esc_draw_line: + LD HL, M_VARS.esc_param + LD E, (HL) ; E=X1 + INC HL + LD D, (HL) ; D=Y1 + INC HL + LD A, (HL) + INC HL + LD H, (HL) ; H=Y2 + LD L, A ; L=X2 + CP E + JP C, .x1_le_x2 + EX DE, HL ; exchange if X1>X2 +.x1_le_x2: + LD (M_VARS.esc_param), HL ; store x1,y1 back + LD A, E + SUB L + LD L, A ; L - width + LD A, D + SUB H + LD H, A ; H - height + PUSH AF + JP NC, .pos_height + ; change sign + CPL + INC A + LD H, A +.pos_height: + EX DE, HL + LD HL, (M_VARS.esc_param) + EX DE, HL + JP Z, height0 + LD A, L + OR A + JP Z, .width0 + LD B, A + POP AF + LD A, 0x0 + ADC A, A + LD (M_VARS.esc_param+4), A + ; HL = E/B height/width + LD E, H + LD C, 16 + LD D, 0 +.next_16: + ADD HL, HL + EX DE, HL + ADD HL, HL + EX DE, HL + LD A, D + JP C, .edl_l4 + CP B + JP C, .edl_l5 +.edl_l4: + SUB B + LD D, A + INC HL +.edl_l5: + DEC C + JP NZ, .next_16 + LD DE, 0x0 + PUSH DE + ; save result at stack + PUSH HL + + LD HL, (M_VARS.esc_param) ; x1,y1 + EX DE, HL + LD C, B + CALL calc_px_addr + ; HL - address, B - offset in byte + ; make mask + LD A, 10000000b +.roll_l: + RLCA + DEC B + JP P, .roll_l + CPL + LD B, A ; b - inv mask + +.edl_l7 + POP DE + EX (SP), HL ; save HL on top of stack + LD A, H + ADD HL, DE + SUB H + CPL + INC A + EX (SP), HL + PUSH DE + PUSH BC + LD C, A + EX DE, HL + + LD HL, (M_VARS.curr_color) + EX DE, HL + ; Access VideoRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + + LD A, (M_VARS.esc_param+4) ; sign of delta Y + OR A + JP NZ, .next_down +.next_up: + ; firs byte + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; second byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + DEC H + LD A, C + OR A + JP Z, .is_last + DEC C + ; draw up + DEC L + JP .next_up +.next_down: + ; first byte + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; second byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; + DEC H + LD A, C + OR A + JP Z, .is_last + DEC C + ; draw down + INC L + JP .next_down +.is_last: + ; Disable VideoRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + POP BC + LD A, B + ; <<1px + SCF + RLA + JP C, .edl_l11 + RLA + INC H + INC H +.edl_l11 + LD B, A + DEC C + JP NZ, .edl_l7 + POP HL + POP HL + RET + +; -------------------------------------------------- +; draw vertical line +; Inp: DE - YX +; L - length +; -------------------------------------------------- +.width0 + LD C, H + CALL calc_px_addr + + ; make pixel mask + LD A, 10000000b +.edl_l13: + RLCA + DEC B + JP P, .edl_l13 + CPL + LD B, A + + EX DE, HL + LD HL, (M_VARS.curr_color) + EX DE, HL + POP AF + + ; Enable VRAM + LD A, 0x1 + OUT (SYS_DD17PB), A + JP C, .next_row_down + +.next_row_up: + ; first byte + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; second byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; next Y + DEC H + LD A, C + OR A + JP Z, close_vram_ret + DEC C + ; dec row + DEC L + JP .next_row_up + +.next_row_down: + ; first byte + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; second byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; next address + DEC H + LD A, C + OR A + JP Z, close_vram_ret + DEC C + ; inc row + INC L + JP .next_row_down + +close_vram_ret: + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +; -------------------------------------------------- +; draw horizontal line +; Inp: DE - YX +; L - length +; -------------------------------------------------- +height0: + POP AF + LD C, L + LD A, L + OR A + JP NZ, .len_ne0 + INC C ; length 1 at least +.len_ne0: + CALL calc_px_addr + ; make pixel mask + LD A, 10000000b +.edl_l19 + RLCA + DEC B + JP P, .edl_l19 + CPL + LD B, A + + EX DE, HL + LD HL, (M_VARS.curr_color) + EX DE, HL + + ; Enable VRAM access + LD A, 0x1 + OUT (SYS_DD17PB), A + +.next_col: + ; set 1st byte + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; set 2nd byte + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; next byte + DEC H + ; next (right) horizontal pixel + LD A, B + SCF + RLA + JP C, .edl_l21 + RLA + INC H + INC H + +.edl_l21: + LD B, A + DEC C + JP NZ, .next_col + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +; -------------------------------------------------- +; ESC Draw Dot +; -------------------------------------------------- +esc_draw_dot: + LD HL, (M_VARS.esc_param) + EX DE, HL + CALL calc_px_addr + LD A, 0x80 + +edd_l1: + RLCA + DEC B + JP P, edd_l1 + LD B, A + LD A, (M_VARS.esc_param+2) + CP 0x3 + JP Z, edd_ep_task_end + LD A, B + CPL + LD B, A + LD A, (M_VARS.esc_param+2) + CP 0x2 + JP Z, edd_ep_fm_0 + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (HL) + AND B + LD (HL), A + INC H + LD A, (HL) + AND B + LD (HL), A + LD A, 0x0 + OUT (SYS_DD17PB), A + RET +edd_ep_fm_0: + EX DE, HL + LD HL, (M_VARS.curr_color) + EX DE, HL + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +edd_ep_task_end: + CALL get_pixel + LD (M_VARS.esc_var3), A + RET + +; -------------------------------------------------- +; +; -------------------------------------------------- +esc_picture: + LD HL, (M_VARS.esc_param+3) + LD A, (HL) + CP ':' + RET NZ + INC HL + LD E, (HL) + INC HL + LD D, (HL) + INC HL + LD A, (HL) + LD (M_VARS.esc_var0), A + INC HL + LD A, (HL) + LD (M_VARS.esc_var1), A + INC HL + PUSH HL + LD C, (HL) + INC HL + LD B, (HL) + INC HL + INC HL + EX DE, HL + PUSH DE + + ; Enable VRAM access + LD A, 0x1 + OUT (SYS_DD17PB), A + CALL pict_sub1 + ; Disable VRAM access + LD A, 0x0 + OUT (SYS_DD17PB), A + + POP DE + POP HL + LD (HL), C + INC HL + LD (HL), B + CALL pict_sub2 ; TODO: replace call+ret to jp; + RET + +pict_sub1: + LD A, (M_VARS.esc_param) + CP ASCII_EM + JP Z, gih_up + CP ASCII_CAN + JP Z, gih_rt + CP ASCII_SUB + JP Z, gih_ctrl_z + CP ASCII_BS + JP Z, gih_bs + CP ASCII_US + JP Z, pict_clr + RET + +pict_clr: + LD L, C + LD H, B + LD A, (M_VARS.esc_var0) + LD C, A + LD A, (M_VARS.esc_var1) + LD B, A + CALL put_image + POP HL + POP HL + POP HL + RET + +ehd_l1: + CP 0x2 + JP Z, get_image_hdr + CP 0x3 + JP Z, m_fn_39 + RET + +; -------------------------------------------------- +; Function 39 +; -------------------------------------------------- +m_fn_39: + LD HL, (M_VARS.esc_param+2) ; pr 3,4 + INC L + LD C, L + LD B, H + LD E, L + CALL dc_mul_e_h + ADD HL, HL + EX DE, HL + LD HL, (M_VARS.esc_param) ; par 1,2 + PUSH BC + PUSH DE + LD BC, 10 + LD E, L + LD D, H + ADD HL, BC + EX DE, HL + LD (HL), E + INC HL + LD (HL), D + INC HL + POP BC + LD A, 4 +.l1: + PUSH AF ; TODO: remove AF not changed + EX DE, HL + ADD HL, BC + EX DE, HL + LD (HL), E + INC HL + LD (HL), D + INC HL + POP AF ; TODO: remove AF not changed + DEC A + JP NZ, .l1 + EX DE, HL + LD HL, 0x0 + ADD HL, BC ; HL=BC + ADD HL, BC ; HL=2*BC + ADD HL, HL ; HL=4*BC + ADD HL, BC ; HL=5*BC + ADD HL, HL ; HL=10*BC + EX DE, HL ; DE=10*BC + LD A, 0x0 + LD B, A ; B=A=0 + ; fill DE bytes at [HL] with 0 +.l2: + LD (HL), B + INC HL + DEC DE + CP E + JP NZ, .l2 + CP D + JP NZ, .l2 + + XOR A + LD (M_VARS.esc_var0), A + POP BC + LD HL, (M_VARS.esc_param) + LD DE, 10 + ADD HL, DE +.l3: + EX DE, HL + LD HL, (M_VARS.esc_param+4) + EX DE, HL + PUSH BC + CALL fn39_sub2 + POP BC + LD A, (M_VARS.esc_var0) + ADD A, 0x2 + LD (M_VARS.esc_var0), A + CP 10 + RET Z + JP .l3 + +; --------------------------------------------------- +; Function 3C +; --------------------------------------------------- +get_image_hdr: + LD HL, (M_VARS.esc_param+4) + LD (HL), 58 ; ':' + INC HL + PUSH HL + LD HL, (M_VARS.esc_param+2) + INC L + LD C, L + LD A, H + ADD A, 0x4 + LD B, A + LD H, B + LD E, C + CALL dc_mul_e_h + ADD HL, HL + EX DE, HL + POP HL + LD (HL), E + INC HL + LD (HL), D + INC HL + LD (HL), C + INC HL + LD (HL), B + INC HL + EX DE, HL + LD HL, (M_VARS.esc_param) + ADD HL, HL + EX DE, HL + PUSH BC + PUSH HL + CALL calc_px_addr + POP DE + LD A, L + LD (DE), A + INC DE + LD A, H + LD (DE), A + INC DE + LD A, B + LD (DE), A + INC DE + POP BC + LD A, 0x1 + OUT (SYS_DD17PB), A + CALL get_image ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; = +; --------------------------------------------------- +esc_get_put_image: + LD A, (M_VARS.esc_param+6) + CP 0x2 + JP NC, ehd_l1 + LD HL, M_VARS.esc_param + LD E, (HL) + INC HL + LD D, (HL) + INC HL + LD C, (HL) + INC HL ; TODO: next call to calc_px_addr + LD B, (HL) ; destroy value of B and HL + CALL calc_px_addr + EX DE, HL + LD HL, (M_VARS.esc_param+4) + LD A, H + CP 128 + RET C + + CP 184 + RET NC + + EX DE, HL + + ; Enable VRAM access + LD A, 0x1 + OUT (SYS_DD17PB), A + LD A, (M_VARS.esc_param+6) + OR A + JP NZ, put_image + +; --------------------------------------------------- +; Get image from VRAM to user buffer +; Inp: HL -> VRAM[x,y] +; DE -> buffer +; BC - width, height +; --------------------------------------------------- +get_image: + PUSH HL + PUSH BC +.next_row: + ; byte 1 + LD A, (HL) + LD (DE), A + INC H ; next Y (row) + INC DE + ; byte 2 ; next dst addr + LD A, (HL) + LD (DE), A + INC H + LD A, H + CP 128 ; last row? + JP NZ, .l2 + LD H, 0x40 ; reset Y +.l2: + INC DE + DEC C + JP NZ, .next_row + POP BC + POP HL + INC L + DEC B ; dec width + JP NZ, get_image + JP img_task_end + +; --------------------------------------------------- +; Put image from buffer to VRAM +; Inp: HL -> VRAM[x,y] +; DE -> buffer +; BC - width, height +; --------------------------------------------------- +put_image: + PUSH HL + PUSH BC +.next_row: + ; two bytes for 8 pixels + ; byte 1 + LD A, (DE) ; get from buffer + LD (HL), A ; put to screen + INC H ; next Y (row) + INC DE ; next src addr + ; byte 2 + LD A, (DE) + LD (HL), A + INC DE + INC H + LD A, H + CP 128 ; last row? + JP NZ, .l2 + LD H, 0x40 ; reset +.l2: + DEC C + JP NZ, .next_row + POP BC + POP HL + ; next column + INC L + DEC B + JP NZ, put_image + +img_task_end: + LD A, 0x0 + OUT (SYS_DD17PB), A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +fn39_sub2: + DEC C +.l1: + PUSH BC +.l2: + EX DE, HL + PUSH BC + PUSH HL + LD L, (HL) + LD H, 0x0 + LD A, (M_VARS.esc_var0) + LD B, A + OR A + JP Z, .l4 +.l3: + ADD HL, HL + DEC A + JP NZ, .l3 +.l4: + LD A, B + LD C, L + LD B, H + POP HL + INC HL + PUSH HL + LD L, (HL) + LD H, 0x0 + OR A + JP Z, .l6 +.l5: + ADD HL, HL + DEC A + JP NZ, .l5 +.l6: + EX DE, HL + LD A, (HL) + OR C + LD (HL), A + INC HL + LD A, (HL) + OR E + LD (HL), A + INC HL + LD (HL), B + INC HL + LD (HL), D + DEC HL + POP DE + INC DE + POP BC + DEC C + JP NZ, .l2 + POP BC + INC HL + INC HL + DEC B + JP NZ, .l1 + RET + +; -------------------------------------------------- +; Handle ASCII_CAN symbol (cursor right) +; -------------------------------------------------- +gih_rt: + DEC DE + LD A, (DE) + ADD A, 0x2 + LD (DE), A + CP 9 + RET C + LD A, 0x2 + LD (DE), A + INC DE + PUSH BC + LD H, D + LD L, E + INC HL + INC HL + LD A, (M_VARS.esc_var0) + PUSH AF + DEC A + LD (M_VARS.esc_var0), A + INC A + ADD A, A + ADD A, B + CP 128 + JP C, .l1 + SUB 0x40 +.l1: + LD B, A + LD A, (M_VARS.esc_var1) +.l2: + PUSH AF + LD A, (M_VARS.esc_var0) +.l3: + PUSH AF + LD A, (HL) + LD (DE), A + INC HL + INC DE + LD A, (HL) + LD (DE), A + INC HL + INC DE + POP AF + DEC A + JP NZ, .l3 + LD A, (BC) + LD (DE), A + INC DE + INC HL + INC B + LD A, (BC) + LD (DE), A + INC HL + INC DE + DEC B + INC C + POP AF + DEC A + JP NZ, .l2 + POP AF + LD (M_VARS.esc_var0), A + POP BC + INC B + INC B + LD A, B + CP 0x80 + RET NZ + LD B, 0x40 + RET + +; -------------------------------------------------- +; Handle ASCII_BS (BackSpace) symbol +; -------------------------------------------------- +gih_bs: + DEC DE + LD A, (DE) + SUB 0x2 + LD (DE), A + RET NC + + LD A, 6 + LD (DE), A + INC DE + PUSH BC + ADD HL, DE + DEC HL + LD D, H + LD E, L + DEC HL + DEC HL + LD A, (M_VARS.esc_var1) + ADD A, C + DEC A + LD C, A + LD A, B + DEC A + CP 0x3f + JP NZ, .l1 + LD A, 0x7f ; [DEL]? +.l1: + LD B, A + LD A, (M_VARS.esc_var0) + PUSH AF + DEC A + LD (M_VARS.esc_var0), A + LD A, (M_VARS.esc_var1) +.l2: + PUSH AF + LD A, (M_VARS.esc_var0) +.l3: + PUSH AF + LD A, (HL) + LD (DE), A + DEC HL + DEC DE + LD A, (HL) + LD (DE), A + DEC HL + DEC DE + POP AF + DEC A + JP NZ, .l3 + LD A, (BC) + LD (DE), A + DEC HL + DEC DE + DEC B + LD A, (BC) + LD (DE), A + DEC HL + DEC DE + INC B + DEC C + POP AF + DEC A + JP NZ, .l2 + POP AF + LD (M_VARS.esc_var0), A + POP BC + DEC B + DEC B + LD A, B + CP 0x3e + RET NZ + LD B, 0x7e + RET + +; -------------------------------------------------- +; Handle ASCII_SUB symbol +; -------------------------------------------------- +gih_ctrl_z: + PUSH BC + LD A, (M_VARS.esc_var0) + ADD A, A + ADD A, A + ADD A, E + LD L, A + LD H, D + LD A, (M_VARS.esc_var1) + ADD A, C + LD C, A + PUSH BC + LD A, (M_VARS.esc_var1) + DEC A + DEC A + LD C, A +.l1: + LD A, (M_VARS.esc_var0) + LD B, A +.l2: + LD A, (HL) + LD (DE), A + INC HL + INC DE + LD A, (HL) + LD (DE), A + INC HL + INC DE + DEC B + JP NZ, .l2 + DEC C + JP NZ, .l1 + POP BC + LD L, 0x2 +.l3: + LD A, (M_VARS.esc_var0) + LD H, A + PUSH BC +.l4: + LD A, (BC) + LD (DE), A + INC DE + INC B + LD A, (BC) + LD (DE), A + INC DE + INC B + LD A, B + CP 0x80 + JP NZ, .l5 + LD B, 0x40 +.l5: + DEC H + JP NZ, .l4 + POP BC + INC C + DEC L + JP NZ, .l3 + POP BC + INC C + INC C + RET + +; -------------------------------------------------- +; Handle ASCII_EM symbol +; -------------------------------------------------- +gih_up: + PUSH BC + LD A, (M_VARS.esc_var0) + ADD A, A + ADD A, B + CP 128 + JP Z, .l1 + JP C, .l1 + SUB 64 +.l1: + DEC A + LD B, A + DEC C + PUSH BC + ADD HL, DE + LD A, (M_VARS.esc_var0) + ADD A, A + ADD A, A + LD E, A + LD A, L + SUB E + LD E, A + LD D, H + DEC DE + DEC HL + EX DE, HL + LD A, (M_VARS.esc_var1) + DEC A + DEC A + LD C, A +.l2: + LD A, (M_VARS.esc_var0) + LD B, A +.l3: + LD A, (HL) + LD (DE), A + DEC HL + DEC DE + LD A, (HL) + LD (DE), A + DEC HL + DEC DE + DEC B + JP NZ, .l3 + DEC C + JP NZ, .l2 + POP BC + LD L, 0x2 + +.l4: + LD A, (M_VARS.esc_var0) + LD H, A + PUSH BC + +.l5: + LD A, (BC) + LD (DE), A + DEC DE + DEC B + LD A, (BC) + LD (DE), A + DEC DE + DEC B + LD A, B + CP 0x3f + JP NZ, .l6 + LD B, 0x7f + +.l6: + DEC H + JP NZ, .l5 + POP BC + DEC C + DEC L + JP NZ, .l4 + POP BC + DEC C + DEC C + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +pict_sub2: + PUSH DE + DEC DE + LD A, (DE) + LD E, A + LD D, 0x0 + LD HL, (M_VARS.esc_param+1) + ADD HL, DE + LD E, (HL) + INC HL + LD D, (HL) + POP HL + PUSH BC + PUSH HL + PUSH HL + LD HL, (M_VARS.esc_param+3) + INC HL + LD C, (HL) + INC HL + LD B, (HL) + POP HL + ADD HL, BC + LD C, L + LD B, H + POP HL + CALL mov_hl_bc + LD A, (M_VARS.esc_param+5) + OR A + JP Z, .l1 + EX DE, HL +.l1: + LD A, (M_VARS.esc_var1) + SUB 0x4 +.l2: + PUSH AF + LD A, (M_VARS.esc_var0) +.l3: + PUSH AF + LD A, (DE) + INC DE + PUSH DE + PUSH AF + LD A, (DE) + LD E, A + POP AF + LD D, A + OR E + CPL + PUSH AF + AND (HL) + OR D + LD (BC), A + INC BC + INC HL + POP AF + AND (HL) + OR E + LD (BC), A + INC BC + INC HL + POP DE + INC DE + POP AF + DEC A + JP NZ, .l3 + POP AF + DEC A + JP NZ, .l2 + LD A, (M_VARS.esc_param+5) + OR A + JP Z, .l4 + EX DE, HL +.l4: + CALL mov_hl_bc + POP DE + EX DE, HL + LD A, (M_VARS.esc_var0) + LD C, A + LD A, (M_VARS.esc_var1) + LD B, A + LD A, 0x1 + OUT (SYS_DD17PB), A + CALL put_image ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; Move form [HL] to [BC] count of bytes +; Inp: HL -> src +; BC -> dst +; esc_var0*4 - count +; --------------------------------------------------- +mov_hl_bc: + PUSH DE + LD A, (M_VARS.esc_var0) + ADD A, A + ADD A, A + LD E, A ; E = param * 4 + ; move [HL] -> [BC] E bytes +.next: + LD A, (HL) + LD (BC), A + INC HL + INC BC + DEC E + JP NZ, .next + POP DE + RET + +; --------------------------------------------------- +; Draw circle +; Inp: param x,y,radius, aspect_x, aspect_y +; --------------------------------------------------- +esc_draw_circle: + LD A, (M_VARS.esc_param+2) ; radius + LD B, A + OR A + RET Z ; exit ir radius 0 + LD A, 0x7f + CP B + RET M ; exit if radius>127 + + XOR A + LD D, A ; 0 + LD E, B ; r + CALL dc_draw_8px + + LD A, 1 + LD H, A + SUB B + LD C, A + LD A, B + RLCA + LD B, A + LD A, 0x1 + SUB B + LD L, A + CCF ; TODO: unused +.l1: + INC D + LD A, E + CP D + JP Z, dc_draw_8px + CALL dc_draw_8px + LD A, H + ADD A, 0x2 + LD H, A + LD A, L + ADD A, 0x2 + LD L, A + LD A, C + ADD A, H + LD C, A + JP NC, .l1 +.l2: + CCF ; TODO: unused + INC D + DEC E + LD A, D + CP E + JP Z, dc_draw_8px + SUB E + CP 0x1 + RET Z + LD A, E + SUB D + CP 0x1 + JP Z, dc_draw_8px + CALL dc_draw_8px + LD A, H + ADD A, 0x2 + LD H, A + LD A, L + ADD A, 0x4 + LD L, A + JP NC, .l3 + CCF ; TODO: unused +.l3: + LD A, C + ADD A, L + LD C, A + JP NC, .l1 + JP .l2 + +; --------------------------------------------------- +; +; --------------------------------------------------- +dc_draw_8px: + PUSH HL + PUSH DE + PUSH BC + PUSH DE + CALL dc_aspect_ratio_1 + LD HL, (M_VARS.esc_param) ; HL=Y,X + CALL dc_draw_4px_bc + POP DE + CALL dc_aspect_ratio2 + LD HL, (M_VARS.esc_param) ; HL=Y,X + CALL dc_draw_4px_cb + POP BC + POP DE + POP HL + XOR A + RET + +; --------------------------------------------------- +; Scale circle axis dy specified aspect ratio +; if aspect_x = 0 C = D else C = D * aspect_x / 256 +; if aspect_y = 0 B = E else B = E * aspect_y / 256 +; --------------------------------------------------- +dc_aspect_ratio_1: + LD HL, (M_VARS.esc_param+3) ; aspect_x -> L, aspect_y -> H + LD A, L + OR A + LD C, D + LD B, E + JP NZ, .dc_ax_ne0 + LD A, H + OR A + JP NZ, .dc_ay_ne0 + RET +.dc_ax_ne0: + LD A, H + LD H, L + LD E, C + CALL dc_mul_e_h + LD C, E + OR A + RET Z +.dc_ay_ne0: + LD H, A + LD E, B + CALL dc_mul_e_h + LD B, E + RET + +; --------------------------------------------------- +; if aspect_x = 0 B = E else B = E * aspect_x / 256 +; if aspect_y = 0 C = D else C = D * aspect_y / 256 +; --------------------------------------------------- +dc_aspect_ratio2: + LD HL, (M_VARS.esc_param+3) ; aspect_x -> L, aspect_y -> H + LD A, L + OR A + LD C, D + LD B, E + JP NZ, .dc_ax_ne0 + LD A, H + OR A + JP NZ, .dc_ay_ne0 + RET +.dc_ax_ne0: + LD A, H + LD H, L + LD E, B + CALL dc_mul_e_h + LD B, E + OR A + RET Z + +.dc_ay_ne0: + LD H, A + LD E, C + CALL dc_mul_e_h + LD C, E + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +dc_mul_e_h: + LD D, 0x0 + LD L, D + ADD HL, HL + JP NC, .l1 + ADD HL, DE +.l1: + ADD HL, HL + JP NC, .l2 + ADD HL, DE +.l2: + ADD HL, HL + JP NC, .l3 + ADD HL, DE +.l3: + ADD HL, HL + JP NC, .l4 + ADD HL, DE +.l4: + ADD HL, HL + JP NC, .l5 + ADD HL, DE +.l5: + ADD HL, HL + JP NC, .l6 + ADD HL, DE +.l6: + ADD HL, HL + JP NC, .l7 + ADD HL, DE +.l7: + ADD HL, HL + JP NC, .l8 + ADD HL, DE +.l8: + LD E, H + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +dc_draw_4px_bc: + ; draw pixel(H+B, L+C) if in screen + LD A, H + ADD A, B + JP C, .l1 + LD D, A + LD A, L + ADD A, C + LD E, A + CALL dc_put_pixel +.l1: + ; draw pixel(H+B, L-C) if in screen + LD A, H + ADD A, B + JP C, .l2 + LD D, A + LD A, L + SUB C + LD E, A + CALL dc_put_pixel +.l2: + ; draw pixel(H-B, L-C) if in screen + LD A, H + SUB B + JP C, .l3 + LD D, A + LD A, L + SUB C + LD E, A + CALL dc_put_pixel +.l3: + ; draw pixel(H-B, L+C) if in screen + LD A, H + SUB B + RET C + LD D, A + LD A, L + ADD A, C + LD E, A + CALL dc_put_pixel ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +dc_draw_4px_cb: + ; draw pixel(H+C, L+B) if in screen + LD A, H + ADD A, C + JP C, .l1 + LD D, A + LD A, L + ADD A, B + LD E, A + CALL dc_put_pixel +.l1: + ; draw pixel(H+C, L-B) if in screen + LD A, H + ADD A, C + JP C, .l2 + LD D, A + LD A, L + SUB B + LD E, A + CALL dc_put_pixel +.l2: + ; draw pixel(H-C, L-B) if in screen + LD A, H + SUB C + JP C, l3 + LD D, A + LD A, L + SUB B + LD E, A + CALL dc_put_pixel +l3: + ; draw pixel(H-C, L+B) if in screen + LD A, H + SUB C + RET C + LD D, A + LD A, L + ADD A, B + LD E, A + CALL dc_put_pixel ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; Draw pixel on screen +; Inp: DE - X, Y +; --------------------------------------------------- +dc_put_pixel: + RET C ; return if CF set (out of screen) + PUSH HL + PUSH BC + CALL calc_px_addr + ; calculate B = pixel mask + LD A, 10000000b +.roll: + RLCA ; [07654321] <- [76547210], [7] -> CF + DEC B + JP P, .roll + CPL + LD B, A + ; DE = foreground color low and hi bytes + EX DE, HL + LD HL, (M_VARS.curr_color) + EX DE, HL + ; Turn on Video RAM + LD A, 0x1 + OUT (SYS_DD17PB), A + ; Load VRAM[HL] byte (low byte), mask and set + LD A, (HL) + XOR E + AND B + XOR E + LD (HL), A + ; Load VRAM[HL+1] byte (low byte), mask and set + INC H + LD A, (HL) + XOR D + AND B + XOR D + LD (HL), A + ; Turn off Video RAM + LD A, 0x0 + OUT (SYS_DD17PB), A + POP BC + POP HL + RET + + ; Full charset, Common + Latin letters (112*8=890) + INCLUDE "font-6x7.inc" + +; --------------------------------------------------- +; Convert 0h..Fh decimal value to symbol '0'..'F' +; --------------------------------------------------- +conv_nibble: + AND 0xf + ADD A, 0x90 + DAA + ADC A, 0x40 + DAA + LD C, A + RET + +; --------------------------------------------------- +; Print byte in HEX +; Inp: A - byte to print +; --------------------------------------------------- +m_hexb: + PUSH AF + RRCA + RRCA + RRCA + RRCA + CALL out_hex + POP AF + +out_hex: + CALL conv_nibble + CALL m_con_out ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; Wtite RAM-Disk 64K to TAPE +; --------------------------------------------------- +m_tape_write_ram2: + LD HL, M_VARS.buffer + LD C, 128 +.cl_stack: + LD (HL), 0x0 + INC HL + DEC C + JP NZ, .cl_stack + LD HL, M_VARS.buffer + LD DE, 0xffff + ; write empty block + ; DE - block ID + ; HL -> block + CALL m_tape_write + CALL twr2_delay + LD DE, 0x0 + CALL m_tape_write + CALL twr2_delay + LD BC, 512 + LD DE, 0x0 +.nxt_blk: + PUSH BC + LD HL, M_VARS.buffer + CALL m_ramdisk_read + INC DE + CALL m_tape_write + CALL twr2_delay + POP BC + DEC BC + LD A, B + OR C + JP NZ, .nxt_blk + RET + +; --------------------------------------------------- +; Pause between blocks on tape +; --------------------------------------------------- +twr2_delay: + LD BC, 250 +.delay: + DEC BC + LD A, B + OR C + JP NZ, .delay + RET + +; --------------------------------------------------- +; Read RAM-Disk 64K from TAPE +; --------------------------------------------------- +m_tape_read_ram2: + LD A, 100 + CALL m_tape_wait + OR A + JP NZ, .end + LD E, 6 + +.srch_first: + DEC E + JP Z, .not_found + ; read block + LD HL, M_VARS.buffer + CALL m_tape_read + CP 4 + JP Z, .end + OR A + JP NZ, .srch_first + LD A, B + OR C + JP NZ, .srch_first + + LD BC, 512 + LD DE, 0x0 + +.rd_next: + PUSH BC + ; Read block from tape + CALL m_tape_read + OR A + JP NZ, .rd_error + DEC BC + LD A, B + CP D + JP NZ, .inv_id + LD A, C + CP E + JP NZ, .inv_id + ; Ok, write block to RAM disk + CALL m_ramdisk_write + INC DE + POP BC + DEC BC + LD A, B + OR C + JP NZ, .rd_next + RET +.not_found: + LD HL, msg_no_start_rec + CALL me_out_strz ; TODO: replace call+ret to jp + RET +.rd_error: + CP 2 + JP Z, .err_ubi + CP 4 + JP Z, .err_ibu + LD HL, msg_checksum + CALL me_out_strz + CALL out_hexw + POP BC + RET + + ; Illegal sequence of blocks +.inv_id: + LD HL, msg_sequence + CALL me_out_strz + INC BC + CALL out_hexw + POP BC + RET + +.err_ubi: + LD HL, msg_ibg + CALL me_out_strz + POP BC + RET + + ; Interrupted by user +.err_ibu: + POP BC +.end: + LD HL, msg_break + CALL me_out_strz ; TODO: replace call+ret to jp + RET + +; -------------------------------------------------- +; Output hex word +; Inp: BC - word to output +; -------------------------------------------------- +out_hexw: + PUSH BC + LD A, B + CALL m_hexb + POP BC + LD A, C + CALL m_hexb ; TODO: replace call+ret to jp + RET + +msg_no_start_rec: + DB "NO START RECORD", 0 +msg_checksum: + DB "CHECKSUM ", 0 +msg_sequence: + DB "SEQUENCE ", 0 +msg_ibg: + DB "IBG", 0 +msg_break: + DB "BREAK", 0 + +; --------------------------------------------------- +; Out ASCIIZ message +; Inp: HL -> zero ended string +; --------------------------------------------------- +me_out_strz: + LD A, (HL) + OR A + RET Z + PUSH BC + LD C, A + CALL m_con_out + INC HL + POP BC + JP me_out_strz + + + +; --------------------------------------------------- +; Read from RAM-disk to RAM +; Inp: DE - source sector 0..511/1535 +; HL -> destination buffer +; --------------------------------------------------- +m_ramdisk_read: + PUSH HL + PUSH DE + LD A, D + ; Build value to access ext RAM (A17, A16, 32k bits) + ; A17, A16, Low 32K bits of memory mapper + IFDEF RAM_DISK_192K + ; Calc A18, A17, A16, 32k address lines + AND 00000111b ; limit to 2047 sectors - 512k + ADD 0x2 + ELSE + ; Default for 64k RAM disk + AND 00000001b ; limit to 511 sectors - 64k + OR 0x2 ; Set A16 address line + ENDIF + ;OR 0x0 ; TODO: nothing, remove + LD B, A ; B - value to turn on access to Ext RAM + ; Calculate DE = address from sector number + XOR A + LD A, E ; E - low address + RRA ; [CF] -> [7:0] -> [CF] + LD D, A ; D = E/2 + LD A, 0x0 + RRA ; [CF] -> E + LD E, A +.read: + ; Access to ExtRAM + LD A, B + OUT (SYS_DD17PB), A + ; Get Byte + LD A, (DE) + LD C, A + ; Access to RAM + LD A, 0x0 + OUT (SYS_DD17PB), A + ; Set Byte + LD (HL), C + ; HL++, DE++ + INC HL + INC DE + LD A, E + ADD A, A + JP NZ, .read ; jump if has more bytes + + ; Access to RAM + LD A, 0x0 + OUT (SYS_DD17PB), A + + POP DE + POP HL + RET + +; --------------------------------------------------- +; Write sector to RAM disk +; Inp: HL -> source buffer +; DE - destination sector 0..511/1535 +; --------------------------------------------------- +m_ramdisk_write: + PUSH HL + PUSH DE + LD A, D + ; Build value to access ext RAM (A17, A16, 32k bits) + ; Calc A16, A17 address lines + IFDEF RAM_DISK_192K + AND 00000111b ; 2048 sectors = 256k + ADD 0x2 + ELSE + ; Default for 64k RAM disk + AND 00000001b ; 512 sectors = 64k + OR 0x2 ; Set A16 address line + ENDIF + ;OR 0x0 ; TODO: remove unused + LD B, A + XOR A + LD A, E + RRA + LD D, A + LD A, 0x0 + RRA + LD E, A +.wr_byte: + LD A, 0x0 + OUT (SYS_DD17PB), A + LD C, (HL) + LD A, B + OUT (SYS_DD17PB), A + LD A, C + LD (DE), A + INC HL + INC DE + LD A, E + ADD A, A + JP NZ, .wr_byte + LD A, 0x0 + OUT (SYS_DD17PB), A + POP DE + POP HL + RET + +; -------------------------------------------------- +; Write block to Tape +; In: DE - block ID, +; HL -> block of data. +; -------------------------------------------------- +m_tape_write: + PUSH HL + PUSH DE + PUSH DE + LD BC, 2550 + LD A, PIC_POLL_MODE ; pool mode + OUT (PIC_DD75RS), A + LD A, TMR0_SQWAVE ; tmr0, load lsb+msb, sq wave, bin + OUT (TMR_DD70CTR), A + LD A, C + OUT (TMR_DD70C1), A + LD A, B + OUT (TMR_DD70C1), A + ; Write Hi+Lo, Hi+Lo + LD DE, 4 ; repeat next 4 times +.l1: + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; check rst4 from timer#0 + JP NZ, .l1 + LD A, D + CPL + LD D, A + OR A + LD A, TL_HIGH ; tape level hi + JP NZ, .set_lvl + LD A, TL_LOW ; tape level low +.set_lvl: + OUT (DD67PC), A ; set tape level + LD A, TMR0_SQWAVE ; tmr0, load lsb+msb, swq, bin + ; timer on + OUT (TMR_DD70CTR), A + LD A, C + OUT (TMR_DD70C1), A + LD A, B + OUT (TMR_DD70C1), A + DEC E + JP NZ, .l1 + +.l2: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ, .l2 + + ; Write 00 at start + LD A, 0x0 + CALL m_tape_wr_byte + ; Write 0xF5 marker + LD A, 0xf5 + CALL m_tape_wr_byte + LD E, 0x0 ; checksum=0 + ; Write block ID + POP BC + LD A, C + CALL m_tape_wr_byte + LD A, B + CALL m_tape_wr_byte + ; Write 128 data bytes + LD B, 128 +.next_byte: + LD A, (HL) + CALL m_tape_wr_byte + INC HL + DEC B + JP NZ, .next_byte + ; Write checksum + LD A, E + CALL m_tape_wr_byte + ; Write final zero byte + LD A, 0x0 + CALL m_tape_wr_byte +.wait_end: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ, .wait_end + LD A, TL_MID ; tape level middle + OUT (DD67PC), A + POP DE + POP HL + RET + + +; ------------------------------------------------------ +; Write byte to tape +; Inp: A - byte top write +; D - current level +; E - current checksum +; ------------------------------------------------------ +m_tape_wr_byte: + PUSH BC + ; calc checksum + LD B, A + LD A, E + SUB B + LD E, A + LD C, 8 ; 8 bit in byte +.get_bit: + LD A, B + RRA + LD B, A + JP C, .bit_hi +.wait_t: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ, .wait_t + LD A, TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; program for 360 cycles + LD A, 0x68 + OUT (TMR_DD70C1), A + LD A, 0x1 + OUT (TMR_DD70C1), A + ; change amplitude + LD A, D + CPL + LD D, A + OR A + LD A, TL_HIGH + JP NZ, .out_bit + LD A, TL_LOW +.out_bit: + OUT (DD67PC), A + DEC C + JP NZ,.get_bit + POP BC + RET +.bit_hi: + IN A, (PIC_DD75RS) + AND TIMER_IRQ + JP NZ, .bit_hi + ; program for 660 cycles + LD A, TMR0_SQWAVE + OUT (TMR_DD70CTR), A + LD A, 0x94 + OUT (TMR_DD70C1), A + LD A, 0x2 + OUT (TMR_DD70C1), A + ; change amplitude + LD A, D + CPL + LD D, A + OR A + LD A, TL_HIGH + JP NZ, .out_bit_hi + LD A, TL_LOW +.out_bit_hi: + OUT (DD67PC), A + DEC C + JP NZ, .get_bit + POP BC + RET + +; ------------------------------------------------------ +; Load block from Tape +; In: HL -> buffer to receive bytes from Tape +; Out: A = 0 - ok, +; 1 - CRC error, +; 2 - unexpected block Id +; 4 - key pressed +; ------------------------------------------------------ +m_tape_read: + PUSH HL + PUSH DE + LD A, PIC_POLL_MODE ; pool mode + OUT (PIC_DD75RS), A + LD A, TMR0_SQWAVE + OUT (TMR_DD70CTR), A ; tmr0, load lsb+msb, sq wave + LD A, 0x0 + ; tmr0 load 0x0000 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + LD C, 3 +.wait_3_changes: + CALL read_tape_bit_kbd + INC A + JP Z, .key_pressed + LD A, B + ADD A, 4 + JP P, .wait_3_changes + DEC C + JP NZ, .wait_3_changes +.wait_4th_change: + CALL read_tape_bit_kbd + INC A + JP Z, .key_pressed + LD A, B + ADD A, 4 + JP M, .wait_4th_change + LD C, 0x0 +.wait_f5_marker: + CALL read_tape_bit_kbd + INC A + JP Z, .key_pressed + DEC A + RRA + LD A, C + RRA + LD C, A + CP 0xf5 + JP NZ, .wait_f5_marker + LD E, 0x0 ; checksum = 0 + ; Read blk ID + CALL m_tape_read_byte + JP NC, .err_read_id + LD C, D + CALL m_tape_read_byte + JP NC, .err_read_id + LD B, D + PUSH BC + ; Read block, 128 bytes + LD C, 128 +.read_next_b: + CALL m_tape_read_byte + JP NC, .err_read_blk + LD (HL), D + INC HL + DEC C + JP NZ, .read_next_b + + ; Read checksum + CALL m_tape_read_byte + JP NC, .err_read_blk + LD A, E + OR A + JP Z, .checksum_ok + LD A, 0x1 ; bad checksum +.checksum_ok: + POP BC +.return: + POP DE + POP HL + RET + +.err_read_blk: + POP BC + LD BC, 0x0 +.err_read_id: + LD A, 0x2 ; read error + JP .return +.key_pressed: + CALL m_con_in + LD C, A ; store key code in C + LD B, 0x0 + LD A, 0x4 + JP .return + +; ------------------------------------------------------ +; Read byte from Tape +; Out: D - byte +; CF is set if ok, cleared if error +; ------------------------------------------------------ +m_tape_read_byte: + PUSH BC + LD C, 8 +.next_bit: + CALL m_read_tape_bit + ; push bit from lo to hi in D + RRA + LD A, D + RRA + LD D, A + LD A, 4 + ADD A, B + JP NC, .ret_err + DEC C + JP NZ, .next_bit + ; calc checksum + LD A, D + ADD A, E + LD E, A + SCF +.ret_err: + POP BC + RET + +; ------------------------------------------------------ +; Read bit from tape +; Out: A - bit from tape +; B - time from last bit +; ------------------------------------------------------ +m_read_tape_bit: + IN A, (KBD_DD78PB) ; Read Tape bit 5 (data) + AND TAPE_P + LD B, A +.wait_change: + IN A, (KBD_DD78PB) + AND TAPE_P + CP B + JP Z, .wait_change + LD A, TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; [360...480...660] 0x220=544d + IN A, (TMR_DD70C1) ; get tmer#0 lsb + ADD A, 0x20 + IN A, (TMR_DD70C1) ; get tmer#0 msb + LD B, A + ADC A, 0x2 + ; reset timer to 0 + LD A, 0x0 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + ; For 0 - 65535-360+544 -> overflow P/V=1 + ; For 1 - 65535-660+544 -> no overflow P/V=0 + RET P + INC A + RET + +; ------------------------------------------------------ +; Read bit from tape with keyboard interruption +; Out: A - bit from tape +; B - time from last bit +; ------------------------------------------------------ +read_tape_bit_kbd: + IN A, (KBD_DD78PB) + AND TAPE_P + LD B, A ; save tape bit state + ; wait change with keyboard check +.wait_change: + IN A, (PIC_DD75RS) + AND KBD_IRQ + JP NZ, .key_pressed + IN A, (KBD_DD78PB) + AND TAPE_P + CP B + JP Z, .wait_change + ; measure time + LD A, TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; read lsb+msb + IN A, (TMR_DD70C1) + ADD A, 0x20 + IN A, (TMR_DD70C1) + LD B, A + ADC A, 0x2 + ; reset timer#0 + LD A, 0x0 + OUT (TMR_DD70C1), A + OUT (TMR_DD70C1), A + ; flag P/V is set for 0 + RET P + INC A + RET +.key_pressed: + LD A, 0xff + RET + +; ------------------------------------------------------ +; Wait tape block +; Inp: A - periods to wait +; Out: A=4 - interrupded by keyboard, C=key +; ------------------------------------------------------ +m_tape_wait: + OR A + RET Z + PUSH DE + LD B, A +.wait_t4: + LD C,B + IN A, (KBD_DD78PB) + AND TAPE_P ; Get TAPE4 (Wait det) and save + LD E, A ; store T4 state to E +.wait_next_2ms: + LD A,TMR0_SQWAVE + OUT (TMR_DD70CTR), A + ; load 3072 = 2ms + XOR A + OUT (TMR_DD70C1), A + LD A, 0xc + OUT (TMR_DD70C1), A +.wait_tmr_key: + IN A, (PIC_DD75RS) + AND KBD_IRQ ; RST1 flag (keyboard) + JP NZ, .key_pressed + IN A, (PIC_DD75RS) + AND TIMER_IRQ ; RST4 flag (timer out) + JP Z, .wait_no_rst4 + IN A, (KBD_DD78PB) + AND TAPE_P ; TAPE4 not changed? + CP E + JP NZ, .wait_t4 ; continue wait + JP .wait_tmr_key +.wait_no_rst4: + DEC C + JP NZ, .wait_next_2ms + XOR A + POP DE + RET + +.key_pressed: + CALL m_con_in + LD C, A ; C = key pressed + LD A, 0x4 ; a=4 interrupted by key + POP DE + RET + +; ------------------------------------------------------ +; Check block marker from Tape +; Out: A=0 - not detected, 0xff - detected +; ------------------------------------------------------ +m_tape_blk_detect: + IN A, (KBD_DD78PB) + AND TAPE_D ; TAPE5 - Pause detector + LD A, 0x0 + RET Z + CPL + RET + +; ====================================================== +; FDC DRIVER +; ====================================================== + + +fdc_unload_head: + LD A, 0x0 + OUT (FDC_DATA), A + LD A, FDC_RESTORE_UH_NV + OUT (FDC_CMD), A + NOP + NOP + +.wait_no_busy: + IN A, (FDC_CMD) + AND 00000101b ; Track0 , Busy + CP 00000100b + JP Z, .tr0_ok + + IN A, (FLOPPY) + RLCA ; MOTST -> CF + JP NC, .wait_no_busy + LD A, 0x20 + RET +.tr0_ok: + LD A, B + DEC A + LD A, 0x1 + JP Z, .b1 + LD (M_VARS.ul_A_var1), A + XOR A + LD (M_VARS.ul_A_var4), A + RET + +.b1: + LD (M_VARS.ul_B_var2), A + XOR A + LD (M_VARS.ul_B_var5), A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_select_drive: + PUSH AF + CALL delay_1.4mS + DEC A ; CP 0x1 + LD B, 0x5 + JP Z, .sel_A + LD B, 0x2 + ;JP .sel_B +.sel_A: + ;LD A, 0x5 +;.sel_B + ;LD B, A ; 010b or 101b + IN A, (FLOPPY) ; read Floppy controller reg + AND 0x40 ; SSEL + RRA ; SSEL for out + OR B ; 0x22 or 0x25 if WP + OUT (FLOPPY), A ; Select drive A or B + LD B, A + POP AF + DEC A + JP Z, .dpar_a + LD A, (bios_var2) + JP .dpar_b +.dpar_a: + LD A, (BIOS.bios_var04) +.dpar_b: + PUSH BC + LD B, A ; B = dpar_A or B + LD A, D ; compare with D? + CP B + JP C, .l_le ; D < B + SUB B + LD D, A + POP BC + LD A, C + OR 0x8 + LD C, A + LD A, B + AND 0x20 + OR A + RET NZ + LD A, B + OR 0x20 ; set SSEL to 1 + OUT (FLOPPY), A + CALL delay_136uS + RET +.l_le: + POP BC + LD A, B + AND 0x20 + OR A + RET Z + LD A, B + AND 0x7 + OUT (FLOPPY), A + CALL delay_136uS + RET + +; --------------------------------------------------- +; Delay for 136uS +; --------------------------------------------------- +delay_136uS: + LD B, 16 ; 7 + +; --------------------------------------------------- +; Delay for B*8uS +; --------------------------------------------------- +delay_b: + DEC B ; 4 + JP NZ, delay_b ; 10 + RET ; 10 + +; --------------------------------------------------- +; Delay for 1.4mS +; --------------------------------------------------- +delay_1.4mS: + LD B, 175 ; 7 + JP delay_b ; 10 + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_read_floppy: + PUSH AF + CALL m_select_drive + POP AF + CALL m_start_seek_track + JP C, fdc_ret + CALL m_fdc_read_c_bytes + JP C, fdc_ret + XOR A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_write_floppy: + PUSH AF + CALL m_select_drive + POP AF + CALL m_start_seek_track + JP C, fdc_ret + CALL m_fdc_write_bytes + JP C, fdc_ret + XOR A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_start_seek_track: + CALL m_start_floppy + RET C + CALL m_fdc_seek_trk + RET C ; TODO: remove + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_start_floppy: + LD B, A + LD A, (M_VARS.ul_var3) + CP B + JP Z, .need_m_start + CALL .wait_motor ; TODO: replace call+ret to jp + RET + +.need_m_start: + IN A, (FLOPPY) + RLCA ; check MOTST + JP C, .wait_motor + IN A, (FDC_CMD) + AND FDC_NOT_READY ; not ready flag + RET Z + +; --------------------------------------------------- +; +; --------------------------------------------------- +.wait_motor: + PUSH BC + LD BC, 65535 + CALL fdc_init +.wait_rdy1: + IN A, (FDC_CMD) + AND FDC_NOT_READY + JP Z, .long_delay + IN A, (FLOPPY) + RLCA ; CF<-A[7] MOTST flag + JP NC, .wait_rdy1 + LD A, 0x20 + JP .mst_exi +.long_delay: + DEC BC + LD A, B + OR A + JP NZ, .long_delay +.mst_exi: + POP BC + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +fdc_init: + IN A, (FLOPPY) + AND 01001110b ; Get SSEL, DRSEL, MOT1, MOT0 + RRA + OUT (FLOPPY), A + OR 0x08 ; Set INIT bit + OUT (FLOPPY), A + RET + +; --------------------------------------------------- +; Seek track on floppy +; Inp: DE - track/sector +; --------------------------------------------------- +m_fdc_seek_trk: + LD A, B + DEC A + JP Z, .drv_b + LD A, (M_VARS.ul_A_var1) + OR A + CALL Z, fdc_unload_head + RET C + LD A, (M_VARS.ul_A_var4) + OUT (FDC_TRACK), A + LD A, D + LD (M_VARS.ul_A_var4), A + JP .cmn +.drv_b: + LD A, (M_VARS.ul_B_var2) + OR A + CALL Z, fdc_unload_head + RET C + LD A, (M_VARS.ul_B_var5) + OUT (FDC_TRACK), A + LD A, D + LD (M_VARS.ul_B_var5), A +.cmn: + LD A, (M_VARS.ul_var3) + CP B + LD A, B + LD (M_VARS.ul_var3), A + JP NZ, .l2 + IN A, (FDC_TRACK) + CP D + JP Z, .l2 + JP C, .l1 + LD A, (M_VARS.ul_var6) + OR A + JP NZ, .l2 + LD B, 0xff + CALL delay_b + LD A, 0x1 + LD (M_VARS.ul_var6), A + JP .l2 +.l1: + LD A, (M_VARS.ul_var6) + OR A + JP Z, .l2 + LD B, 0xff + CALL delay_b + LD A, 0x0 + LD (M_VARS.ul_var6), A +.l2: + LD A, D + OUT (FDC_DATA), A + LD A, 0x1f + OUT (FDC_CMD), A + NOP + NOP + IN A, (FDC_WAIT) + IN A, (FDC_CMD) + AND 0x19 + CP 0x0 + JP NZ, .l3 + JP .l4 +.l3: + SCF + LD A, 0x40 +.l4: + PUSH AF + LD A, E + OUT (FDC_SECT), A + POP AF + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_fdc_write_bytes: + LD A, C + OUT (FDC_CMD), A +.w_next: + IN A, (FDC_WAIT) + RRCA + LD A, (HL) + OUT (FDC_DATA), A + INC HL + JP C, .w_next + CALL fdc_check_status ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +m_fdc_read_c_bytes: + LD A, C + OUT (FDC_CMD), A + JP .l2 +.l1: + LD (HL), A + INC HL +.l2: + IN A, (FDC_WAIT) + RRCA + IN A, (FDC_DATA) + JP C, .l1 + CALL fdc_check_status ; TODO: replace call+ret to jp + RET + +; --------------------------------------------------- +; Check fdc status for errors +; Out: CF set if errors +; --------------------------------------------------- +fdc_check_status: + IN A, (FDC_CMD) + AND 11011111b + CP 0x0 + JP Z, fdc_ret + SCF +fdc_ret: + RET + +;filler1: +; DB 20h + + +; ------------------------------------------------------ + +LAST EQU $ +CODE_SIZE EQU LAST-0xE000 +FILL_SIZE EQU ROM_CHIP_SIZE-CODE_SIZE + + + IFDEF CHECK_INTEGRITY + ASSERT m_start = 0xe051 + ASSERT m_out_strz = 0xe0f1 + ASSERT m_con_out_int = 0xe16d + ASSERT get_esc_param = 0xe187 + ASSERT esc_params_tab = 0xe1cb + ASSERT esc_handler_tab = 0xe1db + ASSERT esc_set_beep = 0xe1f9 + ASSERT m_print_hor_line = 0xe23a + ASSERT m_get_7vpix = 0xe2b4 + ASSERT esc_set_palette = 0xe2fe + ASSERT m_get_glyph = 0xe320 + ASSERT m_print_no_esc = 0xe349 + ASSERT calc_addr_40 = 0xe439 + ASSERT mp_mode_64 = 0xe4b8 + ASSERT calc_addr_80 = 0xe612 + ASSERT m_clear_screen = 0xe639 + ASSERT m_cursor_home = 0xe66c + ASSERT m_draw_cursor = 0xe69a + ASSERT m_handle_esc_code = 0xe77c + ASSERT handle_cc_common = 0xe7c4 + ASSERT handle_cc_80x25 = 0xe833 + ASSERT m_beep = 0xe85a + ASSERT esc_set_cursor = 0xe890 + ASSERT esc_set_vmode = 0xe8e9 + ASSERT esc_set_color = 0xe92f + ASSERT m_print_at_xy = 0xe943 + ASSERT game_sprite_tab = 0xea39 + ASSERT esc_draw_fill_rect = 0xeb64 + ASSERT draw_line_h = 0xeed1 + ASSERT esc_draw_line = 0xef0b + ASSERT esc_draw_dot = 0xf052 + ASSERT esc_picture = 0xf0a4 + ASSERT m_fn_39 = 0xf10f + ASSERT get_image_hdr = 0xf177 + ASSERT esc_get_put_image = 0xf1b5 + ASSERT pict_sub2 = 0xf3ca + ASSERT m_font_cp0 = 0xf5bc + ASSERT me_out_strz = 0xfb36 + ASSERT m_ramdisk_write = 0xfb6d + ASSERT m_tape_write = 0xfb97 + ASSERT m_tape_wr_byte = 0xfc0e + ASSERT m_tape_read_byte = 0xfcee + ASSERT m_read_tape_bit = 0xfd08 + ASSERT m_tape_wait = 0xfd58 + ENDIF + + ; DISPLAY "Code size is: ", /A, CODE_SIZE + + +FILLER + DS FILL_SIZE, 0xFF + DISPLAY "Free size is: ", /A, FILL_SIZE + + ENDMODULE + + OUTEND + + OUTPUT m_vars.bin + ; put in separate waste file + INCLUDE "m_vars.inc" + OUTEND diff --git a/Mon_r9/monitor.inc b/Mon_r9/monitor.inc new file mode 100644 index 0000000..a142cfc --- /dev/null +++ b/Mon_r9/monitor.inc @@ -0,0 +1,19 @@ +mon_start: EQU 0x0000E000 +mon_hexb: EQU 0x0000E003 +non_con_status: EQU 0x0000E006 +mon_con_in: EQU 0x0000E009 +mon_con_out: EQU 0x0000E00C +mon_serial_in: EQU 0x0000E00F +mon_serial_out: EQU 0x0000E012 +mon_char_print: EQU 0x0000E015 +mon_tape_read: EQU 0x0000E018 +mon_tape_write: EQU 0x0000E01B +mon_ram_disk_read: EQU 0x0000E01E +mon_ram_disk_write: EQU 0x0000E021 +mon_tape_read_ram: EQU 0x0000E024 +mon_tape_write_ram: EQU 0x0000E027 +mon_tape_wait: EQU 0x0000E02A +mon_tape_detect: EQU 0x0000E02D +mon_read_floppy: EQU 0x0000E030 +mon_write_floppy: EQU 0x0000E033 +mon_out_str_z: EQU 0x0000E036 diff --git a/Mon_r9/ram.inc b/Mon_r9/ram.inc new file mode 100644 index 0000000..8c6c08e --- /dev/null +++ b/Mon_r9/ram.inc @@ -0,0 +1,49 @@ +; ======================================================= +; Ocean-240.2 +; +; RAM area at address: 0x0000 - 0x0100, used by CP/M and +; HW-Monitor +; By Romych 2026-02-03 +; ======================================================= + + IFNDEF _RAM + DEFINE _RAM + + MODULE RAM + +@warm_boot EQU 0x0000 ; Jump warm_boot (Restart) +@warm_boot_addr EQU 0x0001 ; address of warm boot entry point +@iobyte EQU 0x0003 ; Input/Output mapping +@cur_user_drv EQU 0x0004 ; [7:4] - curent user, [3:0] - current drive +@jp_bdos_enter EQU 0x0005 ; Jump bdos (CALL 5 to make CP/M requests) +@bdos_ent_addr EQU 0x0006 ; addres of BDOS entry point +@RST1 EQU 0x0008 +@RST1_handler_addr EQU 0x0009 +;RST2 EQU 0x0010 +;RST3 EQU 0x0018 +;RST4 EQU 0x0020 +;RST5 EQU 0x0028 +;RST6 EQU 0x0030 +;RST7 EQU 0x0038 +;reserve1 EQU 0x003b +@bios_var0 EQU 0x0040 ; 0xaa - bios init r8 +@bios_var1 EQU 0x0041 ; 0xaa - bios init r8 +@bios_var2 EQU 0x0042 ; 0x00 - bios init r8 +@bios_var3 EQU 0x0043 ; 0xff - bios init r8 +@interleave_0 EQU 0x0044 +;reserve2 EQU 0x0050 +@fcb1 EQU 0x005c ; Default FCB, 16 bytes +@fcb2 EQU 0x006c +;NMI_ISR EQU 0x0066 + +@dma_buffer EQU 0x0080 ; Default "DMA" 128 bytes buffer +@p_cmd_line_len EQU 0x0080 ; command line character count +@p_cmd_line EQU 0x0081 ; command line buffer +@fcb_ra_record_num EQU 0x00a1 +@bios_stack EQU 0x0100 +@tpa_start EQU 0x0100 ; start of program +@video_ram EQU 0x4000 + + ENDMODULE + + ENDIF \ No newline at end of file diff --git a/Mon_r9/sprites.inc b/Mon_r9/sprites.inc new file mode 100644 index 0000000..345a321 --- /dev/null +++ b/Mon_r9/sprites.inc @@ -0,0 +1,48 @@ +; -------------------------------------------------- +; Ocean-240.2 +; Monitor V8 - Sprites for games +; +; Disassembled by Romych 2026-02-22 +; -------------------------------------------------- + + IFNDEF _SPRITES + DEFINE _SPRITES + +game_sprite_tab: + DB 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 ; 0x00 + DB 0x7E, 0x81, 0xA5, 0x81, 0xBD, 0x99, 0x81, 0x7E ; 0x01 + DB 0x7E, 0xFF, 0xDB, 0xFF, 0xC3, 0xE7, 0xFF, 0x7E ; 0x02 + DB 0x00, 0x08, 0x08, 0x14, 0x63, 0x14, 0x08, 0x08 ; 0x03 + DB 0x36, 0x7F, 0x7F, 0x7F, 0x3E, 0x1C, 0x08, 0x00 ; 0x04 + DB 0x08, 0x1C, 0x3E, 0x7F, 0x3E, 0x1C, 0x08, 0x00 ; 0x05 + DB 0x1C, 0x3E, 0x1C, 0x7F, 0x7F, 0x6B, 0x08, 0x1C ; 0x06 + DB 0x08, 0x08, 0x1C, 0x3E, 0x7F, 0x3E, 0x08, 0x1C ; 0x07 + DB 0x3C, 0x66, 0x66, 0x66, 0x3C, 0x18, 0x7E, 0x18 ; 0x08 + DB 0x18, 0xDB, 0x3C, 0xE7, 0xE7, 0x3C, 0xDB, 0x18 ; 0x09 + DB 0xE7, 0xE7, 0x00, 0x7E, 0x7E, 0x00, 0xE7, 0xE7 ; 0x0a + DB 0x7E, 0x81, 0x81, 0xFF, 0xFF, 0x81, 0x81, 0x7E ; 0x0b + DB 0x00, 0x18, 0x3C, 0x7E, 0x18, 0x18, 0x18, 0x18 ; 0x0c + DB 0x18, 0x18, 0x18, 0x18, 0x7E, 0x3C, 0x18, 0x00 ; 0x0d + DB 0x00, 0x10, 0x30, 0x7F, 0x7F, 0x30, 0x10, 0x00 ; 0x0e + DB 0x00, 0x08, 0x0C, 0xFE, 0xFE, 0x0C, 0x08, 0x00 ; 0x0f + DB 0x88, 0x44, 0x22, 0x11, 0x88, 0x44, 0x22, 0x11 ; 0x10 + DB 0x11, 0x22, 0x44, 0x88, 0x11, 0x22, 0x44, 0x88 ; 0x11 + DB 0x0F, 0x0F, 0x0F, 0x0F, 0xF0, 0xF0, 0xF0, 0xF0 ; 0x12 + DB 0xF0, 0xF0, 0xF0, 0xF0, 0x0F, 0x0F, 0x0F, 0x0F ; 0x13 + DB 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF ; 0x14 + DB 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF ; 0x15 + DB 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F ; 0x16 + DB 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0 ; 0x17 + DB 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00 ; 0x18 + DB 0xCC, 0xCC, 0x33, 0x33, 0xCC, 0xCC, 0x33, 0x33 ; 0x19 + DB 0x70, 0x08, 0x76, 0xFF, 0xFF, 0xFF, 0x7E, 0x18 ; 0x1a + DB 0xC3, 0xDB, 0xDB, 0x18, 0x18, 0xDB, 0xDB, 0xC3 ; 0x1b + DB 0xFC, 0xCC, 0xFC, 0x0C, 0x0C, 0x0E, 0x0F, 0x07 ; 0x1c + DB 0xFE, 0xC6, 0xFE, 0xC6, 0xC6, 0xE6, 0x67, 0x03 ; 0x1d + DB 0x18, 0x3C, 0x3C, 0x18, 0x7E, 0x18, 0x24, 0x66 ; 0x1e + DB 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80 ; 0x1f + DB 0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01 ; 0x20 + DB 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01 ; 0x21 + DB 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFF ; 0x22 + + ENDIF \ No newline at end of file diff --git a/Type/.vscode/extensions.json b/Type/.vscode/extensions.json new file mode 100644 index 0000000..1fdc4e8 --- /dev/null +++ b/Type/.vscode/extensions.json @@ -0,0 +1,9 @@ +{ + "recommendations": [ + "maziac.asm-code-lens", + "maziac.dezog", + "maziac.hex-hover-converter", + "maziac.z80-instruction-set", + "maziac.sna-fileviewer" + ] +} diff --git a/Type/.vscode/launch.json b/Type/.vscode/launch.json new file mode 100644 index 0000000..99a521e --- /dev/null +++ b/Type/.vscode/launch.json @@ -0,0 +1,42 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "type": "dezog", + "request": "launch", + "name": "Simulator - ZX48K Spectrum", + "remoteType": "zsim", + "zsim": { + "visualMemory": true, + "memoryModel": "ZX48K", + "ulaScreen": "spectrum", + "zxKeyboard": "spectrum", + "zxBeeper": true + }, + "sjasmplus": [ + { + "path": "monitor.sld" + } + ], + "commandsAfterLaunch": [], + "history": { + "reverseDebugInstructionCount": 1000000, + "spotCount": 10, + "codeCoverageEnabled": true + }, + "startAutomatically": false, + "rootFolder": "${workspaceFolder}", + + "topOfStack": "stack_top", + + "loadObjs": [ + { "path": "mon_E000.bin", "start": "0xe000" } + ], + "execAddress": "0xe021" + + } + ] +} \ No newline at end of file diff --git a/Type/.vscode/tasks.json b/Type/.vscode/tasks.json new file mode 100644 index 0000000..4af112c --- /dev/null +++ b/Type/.vscode/tasks.json @@ -0,0 +1,31 @@ +{ + "version": "2.0.0", + "tasks": [ + { + "label": "make TYPE (sjasmplus)", + "type": "shell", + "command": "sjasmplus", + "args": [ + "--fullpath", + "--nofakes", + "--i8080", + "type.asm" + ], + "problemMatcher": { + "owner": "sjasmplus", + "fileLocation": "autoDetect", + "pattern": { + "regexp": "^(.*)\\((\\d+)\\):\\s+(warning|error):\\s+(.*)$", + "file": 1, + "line": 2, + "severity": 3, + "message": 4 + } + }, + "group": { + "kind": "build", + "isDefault": true + } + } + ] +} \ No newline at end of file diff --git a/Type/TYPE.COM b/Type/TYPE.COM new file mode 100644 index 0000000..9af4a5f Binary files /dev/null and b/Type/TYPE.COM differ diff --git a/Type/equates.inc b/Type/equates.inc new file mode 100644 index 0000000..0484f42 --- /dev/null +++ b/Type/equates.inc @@ -0,0 +1,72 @@ +; ================================================== +; Equates for TYPE.COM +; +; By Romych, 2026-03-01 +; ================================================== + + IFNDEF _EQUATES + DEFINE _EQUATES + +; -------------------------------------------------- +; ASCII CODES +; -------------------------------------------------- + +ASCII_BELL EQU 0x07 ; Make Beep +ASCII_BS EQU 0x08 ; Move cursor left (Back Space) +ASCII_TAB EQU 0x09 ; Move cursor right +8 pos +ASCII_LF EQU 0x0A ; Move cursor down (Line Feed) +ASCII_FF EQU 0x0C ; Move cursor to home (Form Feed) +ASCII_CR EQU 0x0D ; Move gursor to 1st pos (Cariage Return) +ASCII_SO EQU 0x0E ; ^N Shift Out +ASCII_SI EQU 0x0F ; ^O Shift In +ASCII_CAN EQU 0x18 ; Move cursor right +ASCII_EM EQU 0x19 ; Move cursor up +ASCII_SUB EQU 0x1A ; CTRL-Z - end of text file marker +ASCII_ESC EQU 0x1B ; +ASCII_US EQU 0x1F ; Clear screen +ASCII_SP EQU 0x20 +ASCII_DEL EQU 0x7F + +; -------------------------------------------------- +; KEYBOARD Ctrl+Key CODES +; -------------------------------------------------- + +CTRL_A EQU 0x01 +CTRL_B EQU 0x02 +CTRL_C EQU 0x03 ; Warm boot +CTRL_D EQU 0x04 +CTRL_E EQU 0x05 ; Move to beginning of new line (Physical EOL) +CTRL_F EQU 0x06 +CTRL_G EQU 0x07 +CTRL_H EQU 0x08 ; Backspace +CTRL_I EQU 0x09 +CTRL_J EQU 0x0A ; LF - Line Feed +CTRL_K EQU 0x0B +CTRL_L EQU 0x0C +CTRL_M EQU 0x0D ; CR - Carriage Return +CTRL_N EQU 0x0E +CTRL_O EQU 0x0F +CTRL_P EQU 0x10 ; turn on/off printer +CTRL_Q EQU 0x11 +CTRL_R EQU 0x12 ; Repeat current cmd line +CTRL_S EQU 0x13 ; Temporary stop display data to console (aka DC3) +CTRL_T EQU 0x14 +CTRL_U EQU 0x15 ; Cancel (erase) current cmd line +CTRL_V EQU 0x16 +CTRL_W EQU 0x17 +CTRL_X EQU 0x18 ; Cancel (erase) current cmd line +CTRL_Y EQU 0x19 +CTRL_Z EQU 0x1A ; CTRL-Z - end of text file marker + +; -------------------------------------------------- +; BIOS RAM Entries +; -------------------------------------------------- + +jp_bdos_enter EQU 0x0005 ; Jump bdos (CALL 5 to make CP/M requests) +fcb1 EQU 0x005c ; Default FCB, 16 bytes +dma_buffer EQU 0x0080 ; Default "DMA" 128 bytes buffer +p_cmd_line_len EQU 0x0080 ; command line character count +p_cmd_line EQU 0x0081 ; command line buffer +tpa EQU 0x0100 ; Program area + + ENDIF \ No newline at end of file diff --git a/Type/type.asm b/Type/type.asm new file mode 100644 index 0000000..b509453 --- /dev/null +++ b/Type/type.asm @@ -0,0 +1,497 @@ +; ================================================== +; TYPE.COM +; +; Disassembled by Romych, 2026-03-01 +; ================================================== + + DEVICE NOSLOT64K + + INCLUDE "equates.inc" + + OUTPUT TYPE.COM + + MODULE TYPE + + ORG 0x0100 + +; --------------------------------------------------- +; Entry point +; --------------------------------------------------- +start: + LD HL, t_start + LD SP, HL + LD DE, 0x0 + PUSH DE + JP (HL) + + DB "roDOS TYPE FILE Utility(C) IRIMS, Moscow 1985" + +t_start: + CALL t_check_version + ; unsupported bdos call + LD C, 49 + LD DE, t_scb_1 + CALL jp_bdos_enter + DEC A + DEC A + LD (t_scb_mm), A + + ; At start command line params here + LD HL, p_cmd_line_len + LD (t_buff_addr), HL + LD A, (HL) + LD (cmd_par_len), A + + ; skip spaces before first parameter +.skip_sp_0: + CALL t_get_cmdl_char + JP C, t_handle_error + CP ASCII_SP + JP Z, .skip_sp_0 + + ; get filename +.get_next_ch: + CALL t_get_cmdl_char + JP C, t_open_file + CP ASCII_SP + JP NZ, .get_next_ch + + ; get +.skip_sp_1: + CALL t_get_cmdl_char + JP C, t_open_file + CP ASCII_SP + JP Z, .skip_sp_1 + CP 'P' + JP Z, t_param_P + CP 'D' + JP NZ, t_param_no_PD + LD A, 1 + JP t_param_cmn + +t_param_no_PD: + CP 'C' + JP NZ, t_param_no_D + LD A, 2 + JP t_param_cmn + +t_param_no_D: + CP 'F' + JP NZ, t_param_unknown + LD A, 3 + +t_param_cmn: + LD (cmd_switch), A + +.skip_sp_2: + CALL t_get_cmdl_char + JP C, t_open_file + CP ASCII_SP + JP Z, .skip_sp_2 + +t_param_P: + CP 'P' + JP NZ, t_param_unknown + LD A, 0xff + LD (flag1), A + CALL get_numbr + JP C, t_open_file + LD A, L + OR A + JP Z, t_open_file + LD (t_scb_mm), A + +t_open_file: + LD C, 15 + LD DE, fcb1 + CALL jp_bdos_enter + CP 0xff + JP Z, t_handle_error + LD HL, tpa + LD (t_buff_addr), HL + +t_dump_part: + LD A, (t_scb_mm) + LD (cmd_par_len), A + +print_next_byte: + ; get next byte, return if error + CALL t_get_nxt_byte + RET C + ; return if end of text marker + CP ASCII_SUB + RET Z + + ; print character + LD (t_cut_byte), A + LD E, A + CALL t_print + + LD A, (t_cut_byte) + CP ASCII_LF + JP NZ, print_next_byte + ; LF + LD A, (flag0) + OR A + JP Z, lo_ctr_0 + + ; wait until keyboard key pressed +wait_for_key: + CALL t_get_key_wo_echo + OR A + JP Z, wait_for_key + + ; check for Ctrl+C - interrupt + CP CTRL_C + JP Z, t_is_ctrl_c + + ; Space - fro continue + CP ASCII_SP + JP Z, print_next_byte + + CP CTRL_P + JP NZ, is_no_ctrl_p + + ; Access the System Control Block (Unsupported!) + ; get value at offset + LD C, 49 + LD DE, t_scb_2 + CALL jp_bdos_enter + XOR 0xff + LD (t_scb_3+2), A + ; set new value an offset + LD C, 49 + LD DE, t_scb_3 + CALL jp_bdos_enter + ; and wait for next key + JP wait_for_key + +is_no_ctrl_p: + ; Return key + CP ASCII_CR + JP NZ, t_is_no_cr + ; update hi counter + LD A, 0xff + LD (flag1), A + ; zero to low counter + XOR A + LD (flag0), A + ; and dump next part + JP t_dump_part + +t_is_no_cr: + ; other key - zero counters + XOR A + LD (flag0), A + LD (flag1), A + JP print_next_byte + +lo_ctr_0: + CALL t_get_key_wo_echo + OR A + JP Z, no_key_pressd + +lo_ctr_set_ff: + LD A, 0xff + LD (flag0), A + JP wait_for_key + +no_key_pressd: + LD A, (flag1) + OR A + JP Z, print_next_byte + + LD A, (cmd_par_len) + DEC A + LD (cmd_par_len), A + JP NZ, print_next_byte + JP lo_ctr_set_ff + +; --------------------------------------------------- +; +; --------------------------------------------------- +t_check_version + LD C, 12 + CALL jp_bdos_enter + CP 0x26 + JP C, t_ver_unsupported + CP 0x30 + JP NC, t_ver_unsupported + RET + +t_param_unknown: + LD E, 0x0 + JP t_calc_msg_offset + +t_handle_error: + LD E, 0x1 + JP t_calc_msg_offset + +t_is_ctrl_c: + LD E, 0x2 + +t_calc_msg_offset: + LD HL, t_message_tab + LD D, 0x0 + ADD HL, DE + ADD HL, DE + LD E, (HL) + INC HL + LD D, (HL) + ; C_WRITESTR - Output string + LD C, 9 + JP jp_bdos_enter + +; --------------------------------------------------- +; Print character +; Inp: E - charater to print +; --------------------------------------------------- +t_print: + LD A, (cmd_switch) + OR A + JP Z, t_con_output ; D + CP 1 + JP Z, t_get_key_echo ; C + + LD A, E + AND 0x7f ; limit to 0..127 codes + ; check for printable + CP ASCII_SP + JP NC, t_con_output + CP ASCII_CR + JP Z, t_con_output + CP ASCII_LF + JP Z, t_con_output + CP ASCII_TAB + JP Z, t_con_output + CP ASCII_SO ; ^N 0xe + JP Z, t_con_output + CP ASCII_SI ; ^O 0xf + JP Z, t_con_output + LD A, (cmd_switch) + ; if param='F', and unprintable char, do not print + CP 3 + RET Z + + ; replace unprintable with '^' + PUSH DE + LD E, '^' + CALL t_con_output + POP DE + + ; + LD A, E + OR 0x40 + LD E, A + JP t_con_output + +; -------------------------------------------------- +; Return keyboard key if pressed +; Out: A - key code, 0 - no key +; -------------------------------------------------- +t_get_key_wo_echo: + LD E, 0xff + +t_get_key_echo: + LD C, 6 + JP jp_bdos_enter + +t_con_output: + LD C, 2 + JP jp_bdos_enter + +t_ver_unsupported: + HALT + +; --------------------------------------------------- +; Get next character from command line +; Out: A - character +; CF is set if EOL +; ZF is set if A=0 +; --------------------------------------------------- +t_get_cmdl_char: + ; there are still characters in the cmd line? + LD A, (cmd_par_len) + OR A + JP NZ, t_get_next_cmdc ; jump if not eol + CCF + RET + +t_get_next_cmdc: + ; decrement characters count + DEC A + LD (cmd_par_len), A + ; get next character to A + LD HL, (t_buff_addr) + INC HL + LD A, (HL) + ; update pointer + LD (t_buff_addr), HL + OR A + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +get_numbr: + LD C, 10 + CALL t_get_cmdl_char + LD HL, 0x0 + +t_do_nxt_lettr: + JP NC, t_has_a_lettr + OR A + RET + +t_has_a_lettr: + CP ASCII_SP + RET Z + CALL t_is_digits + RET C + CP C + CCF + RET C + LD D, H + LD E, L + LD L, A + LD H, 0 + LD A, C + CALL t_next_hl_de + PUSH HL + CALL t_get_cmdl_char + POP HL + JP t_do_nxt_lettr + +; --------------------------------------------------- +; +; --------------------------------------------------- +t_is_digits: + SBC A, '0' + RET C + CP 10 + JP C, .digit + SBC A, 7 + CP 10 + RET C +.digit: + CP 16 + CCF + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +t_next_hl_de: + OR A + RET Z + RRA + JP NC, .a0_is_0 + ADD HL, DE +.a0_is_0: + EX DE, HL + ADD HL, HL + EX DE, HL + JP t_next_hl_de + +; --------------------------------------------------- +; +; --------------------------------------------------- +t_get_nxt_byte: + LD HL, (t_buff_addr) + LD DE, 0xff00 + ADD HL, DE + LD A, H + OR L + CALL Z, t_read_next_128 + RET C + LD HL, (t_buff_addr) + LD A, (HL) + INC HL + LD (t_buff_addr), HL + RET + +; --------------------------------------------------- +; +; --------------------------------------------------- +t_read_next_128: + LD DE, dma_buffer + ;(F_DMAOFF) - Set DMA address + LD C, 26 + CALL jp_bdos_enter + LD DE, fcb1 + ;(F_READ) - read next record + LD C, 20 + CALL jp_bdos_enter + RRA + LD HL, dma_buffer + LD (t_buff_addr), HL + RET + +; --------------------------------------------------- +; Variables +; --------------------------------------------------- + +flag0: + db 0x00 +flag1: + db 0x00 + +; Cmd line switch D-1, C-2, F-3 +cmd_switch: + db 0x00 + +t_scb_mm: + db 0x00 + +t_cut_byte: + db 0x00 + +cmd_par_len: + db 0x00 + +t_buff_addr: + dw 0x0000 + +t_scb_1: + db 0x1c ; offset + db 0 ; read byte at offset onto a, and word into hl + db 0, 0 + +t_scb_2: + db 0x38 ; offset + db 0, ; read byte at offset onto a, and word into hl + db 0 ,0 + +t_scb_3: + db 0x38 ; offset + db 0xff ; save next byte to SCB+offset + db 0 , 0 + +;t_val_scb1 +; dw 0x0000 + +t_message_tab: + dw msg_err_cmdline + dw msg_no_file + dw msg_interrupted + +msg_err_cmdline: + db "o{ibka komandnoj stroki. ispolxzujte\r\n" + db "TYPE UFN SWITCH \t ili\r\n" + db "TYPE UFN SWITCH P \t ili\r\n" + db "TYPE UFN SWITCH P#\r\n\t" + db "s perekl`~atelem SWITCH:\tNO D C F\r\n" + db "$" + +msg_no_file: + db "net fajla$" + + +msg_interrupted: + db "\r\nTYPE prerwana$" + +filler1: + ds 88, 0x1A +filler2: + ds 1024+start-filler2, 0xe5 + ENDMODULE \ No newline at end of file diff --git a/Type/type.com b/Type/type.com new file mode 100644 index 0000000..9af4a5f Binary files /dev/null and b/Type/type.com differ