Hi George,
Yes, using CALL is the way to perform relative jumps in your ML
program. The idea is this:
Poke a helper function into a hidey hole (on M100 there is a nice 52
byte location you can use for this that I will explain). So the way to
do a relative jump is to add your jump distance as a data byte after the
CALL:
CALL myRelJump ; Relative jump the distance in the next two
bytes (or one if you want)
DW 0xFFE5 ; Jump -27 (signed jump)
Then at myRelJump you would do something like (not tested, you will have
to play with it):
PUSH H ; Save HL. Also modifies SP
PUSH D ; Save DE.
PUSH B
LXI H,FFFAH ; Load HL with -8
DAD SP ; HL now has the Stack location of the return address
(i.e. points to your relative jump distance)
MOV E,L ; Save stack location in DE
MOV D,H
LHLX ; Undocumented opcode to load HL from (DE) ... HL now
points to your ML program
MOV C,M ; Get LSB of the relative jump distance
INX H ; Point to MSB
MOV B,M ; Get MSB of relative jump distance
DAD B ; Add the offset to the PC location (in HL) of the
program
SHLX ; Undocumentd opcode to save HL at (DE) ... save new
return address to stack
POP B
POP D
POP H
RET ; This now returns to the new location you just
calculated
Note that is will be SLOWER ... you are executing 17 opcodes for each
jump instead of one!!
The hidey hole I was talking about is an array used only by the TEXT
application. It saves 26 2-byte pointers (one for each line of the LCD
/ DVI, plus an extra containing 0xFFFF) to indicate the location in the
edited .DO file of the start of that line. I call it the "line starts
array". When runing BASIC, this memory region is unused and can be
poked with any ML you want. On M100, this is at address F6EBH.
Hope this helps. Again, this is UNTESTED code, but should give you the
idea.
Ken
On 3/7/23 4:44 AM, grima...@gmail.com wrote:
Hi all,
One of the things I struggled with in trying to build 8085 subroutines
for BASIC program was the lack of a relative jump command.
So far, the approach I have taken to embed ML programs into BASIC has
been to poke them into arrays, thus allowing BASIC to manage the
routines within memory. However, I then have to use BASIC to get
VARPTR of the array and update all JMP locations before calling the
subroutine, just in case BASIC has moved the array.
The other thought I had was, can I have the ML program modify itself
when it runs? I was racking my brain reading the Inten 8085
documentation, and as far as I can tell there is no easy way to read
the program counter into any of the register pairs, which I would want
to do in order to calculate offsets and update JMP locations.
However I had one thought. It seems that both CALL and RST
instructions push the program counter onto the stack. Is it possible
to leverage either of these and then RET to return to my program, and
then immediately decrement the stack pointer and to retrieve the
previous value.
Then I can use that value to calculate all the offsets and update the
JMP locations.
Does anyone have any constructive input here?
-George