added Ibuffs $xx00 fix

added a fix when the input buffer starts at the beginning of a page
added a pre-patched versiion
This commit is contained in:
Klaus2m5 2017-07-13 16:00:32 +02:00
parent 640fcdab2f
commit 1dd25eb8a3
3 changed files with 8904 additions and 0 deletions

View File

@ -17,6 +17,10 @@ is very limited. In a 2MHz system more than 100 interrupts per second or
interrupts requiring less than 10ms service time should be handled in machine
language. The numbers are worse if the interrupt handler gets more complex.
Of course, a hybrid solution is always possible. You could service the interrupt
in machine language and flag an interrupt to basic only after a buffer is
filled/emptied or a count is reached.
2. String handling when the string is in the input buffer.
@ -128,3 +132,46 @@ LAB_HEXS
JSR LAB_A2HX ; convert A to ASCII hex byte and output
; *** disable decimal mode patch - comment next line ***
; CLD ; back to binary
5. Ibuffs located at $xx00
If the input buffer is located at the beginning of a page then any direct
statement (RUN, LIST, ...) is read from Ibuffs-$100 resulting in unexpected
behavior of EhBASIC.
A patch is available from Daryl Rictor. I took the freedom to add conditional
assembly.
LAB_142A
INY ; increment pointer
INY ; increment pointer (makes it next line pointer high byte)
STA Ibuffs,Y ; save [EOL] (marks [EOT] in immediate mode)
INY ; adjust for line copy
INY ; adjust for line copy
INY ; adjust for line copy
; *** begin patch for when Ibuffs is $xx00 - Daryl Rictor ***
; *** insert
.IF Ibuffs&$FF==0
LDA Bpntrl ; test for $00
BNE LAB_142P ; not $00
DEC Bpntrh ; allow for increment when $xx00
LAB_142P
.ENDIF
; *** end patch for when Ibuffs is $xx00 - Daryl Rictor ***
; end of patch
DEC Bpntrl ; allow for increment
RTS
The conditional in the patch abover requires Ibuffs to be known at path 1 during
assembly. The standard definition of Ibuffs does not satisfy this requirement.
We need to replace it like below:
; Ibuffs can now be anywhere in RAM, ensure that the max length is < $80,
; the input buffer must not cross a page boundary and must not overlap with
; program RAM pages!
;Ibuffs = IRQ_vec+$14
Ibuffs = VEC_SV+$16
; start of input buffer after IRQ/NMI code
Ibuffe = Ibuffs+$47; end of input buffer

8724
patched/basic.asm Normal file

File diff suppressed because it is too large Load Diff

133
patched/min_mon.asm Normal file
View File

@ -0,0 +1,133 @@
; minimal monitor for EhBASIC and 6502 simulator V1.05
; tabs converted to space, tabwidth=6
; To run EhBASIC on the simulator load and assemble [F7] this file, start the simulator
; running [F6] then start the code with the RESET [CTRL][SHIFT]R. Just selecting RUN
; will do nothing, you'll still have to do a reset to run the code.
.include "basic.asm"
; put the IRQ and MNI code in RAM so that it can be changed
IRQ_vec = VEC_SV+2 ; IRQ code vector
NMI_vec = IRQ_vec+$0A ; NMI code vector
; setup for the 6502 simulator environment
IO_AREA = $F000 ; set I/O area for this monitor
ACIAsimwr = IO_AREA+$01 ; simulated ACIA write port
ACIAsimrd = IO_AREA+$04 ; simulated ACIA read port
; now the code. all this does is set up the vectors and interrupt code
; and wait for the user to select [C]old or [W]arm start. nothing else
; fits in less than 128 bytes
*= $FF80 ; pretend this is in a 1/8K ROM
; reset vector points here
RES_vec
CLD ; clear decimal mode
LDX #$FF ; empty stack
TXS ; set the stack
; set up vectors and interrupt code, copy them to page 2
LDY #END_CODE-LAB_vec ; set index/count
LAB_stlp
LDA LAB_vec-1,Y ; get byte from interrupt code
STA VEC_IN-1,Y ; save to RAM
DEY ; decrement index/count
BNE LAB_stlp ; loop if more to do
; now do the signon message, Y = $00 here
LAB_signon
LDA LAB_mess,Y ; get byte from sign on message
BEQ LAB_nokey ; exit loop if done
JSR V_OUTP ; output character
INY ; increment index
BNE LAB_signon ; loop, branch always
LAB_nokey
JSR V_INPT ; call scan input device
BCC LAB_nokey ; loop if no key
AND #$DF ; mask xx0x xxxx, ensure upper case
CMP #'W' ; compare with [W]arm start
BEQ LAB_dowarm ; branch if [W]arm start
CMP #'C' ; compare with [C]old start
BNE RES_vec ; loop if not [C]old start
JMP LAB_COLD ; do EhBASIC cold start
LAB_dowarm
JMP LAB_WARM ; do EhBASIC warm start
; byte out to simulated ACIA
ACIAout
STA ACIAsimwr ; save byte to simulated ACIA
RTS
; byte in from simulated ACIA
ACIAin
LDA ACIAsimrd ; get byte from simulated ACIA
BEQ LAB_nobyw ; branch if no byte waiting
SEC ; flag byte received
RTS
LAB_nobyw
CLC ; flag no byte received
no_load ; empty load vector for EhBASIC
no_save ; empty save vector for EhBASIC
RTS
; vector tables
LAB_vec
.word ACIAin ; byte in from simulated ACIA
.word ACIAout ; byte out to simulated ACIA
.word no_load ; null load vector for EhBASIC
.word no_save ; null save vector for EhBASIC
; EhBASIC IRQ support
IRQ_CODE
PHA ; save A
LDA IrqBase ; get the IRQ flag byte
LSR ; shift the set b7 to b6, and on down ...
ORA IrqBase ; OR the original back in
STA IrqBase ; save the new IRQ flag byte
PLA ; restore A
RTI
; EhBASIC NMI support
NMI_CODE
PHA ; save A
LDA NmiBase ; get the NMI flag byte
LSR ; shift the set b7 to b6, and on down ...
ORA NmiBase ; OR the original back in
STA NmiBase ; save the new NMI flag byte
PLA ; restore A
RTI
END_CODE
LAB_mess
.byte $0D,$0A,"6502 EhBASIC [C]old/[W]arm ?",$00
; sign on string
; system vectors
*= $FFFA
.word NMI_vec ; NMI vector
.word RES_vec ; RESET vector
.word IRQ_vec ; IRQ vector