[A83] Re: SDCC port


[Prev][Next][Index][Thread]

[A83] Re: SDCC port



> Van: Patai Gergely <patai_gergely@fastmail.fm>
>
>>> And what about the system interrupt? You should disable that too,
>>> shouldn't you?
>>>
>> Do you mean so it won't try to change the system flags using a
>> meaningless IY?
>> Smart. A wrapper might be a better idea, however.
>
>
> How would you realise that?

<sigh>

[Sorry for the HTML mail, just did it to stop line breaking]

This one does a bit too much for what you would want to let it do under
SDCC. But the z88dk also uses the shadow registers here and there.

{z88dk}/lib/intwrap83.asm

; Ti83 interrupt 'wrapper' - by Henk Poley
;-----------------------------------------------------------------------------
; The z88dk makes extensively use of the shadow registers (EXX and EX AF,AF)
; The Ti83 system interrupt doesn't preserve (any of) these regs and
;  could thus crash your program. The workaround is to use this interrupt
;  all the time, it saves and restores the (shadow-)registers for the
;  system interrupt.
; We need the system interrupt when scanning keys (in an easy way), also
;  some (other) ROM calls make use of the system interrupt. if the interrupt
;  is then not running, the calculator would crash.
;-----------------------------------------------------------------------------
; Do work:
; ticalc\smile.c
; ticalc\dstar.c
; ticalc\spritest.c
; ticalc\world.c
; ticalc2\fib.c
;
; Don't work:
; ticalc\smallgfx.c (83 lib uses dcircle.asm instead of dcircle2.asm)
;  - Displays circles, but doesn't return to prompt...
;    (Runs correctly now we safe IY and restore it at the end of the program)
; ticalc2\enigma.c
;  - Just crashes...
; ticalc2\rpn.c
;  - Displays text, but crashes before you can press a key, doesn't respond
;     to anything
;-----------------------------------------------------------------------------

defc intcount    = $878A ; 1 byte needed

INCLUDE "#int83.asm" ; Put interrupt loader here
; HL = $8789
inc hl ; We need to intialize variables
ld (hl),0 ;  by ourself.
;
jr jump_over ; Jump over the interrupt code

;-----------------
; Actual interrupt
;-----------------
.IntProcStart
push af ;
ld a,(intcount) ; Check if own interrupt has quited
bit 7,a ;  correctly, then bit 7 is zero
jr nz,int_fix ; If not zero, fix stack...
push hl ;
push de ;
push bc ;
push iy ;
ld iy,_IY_TABLE ;
ld hl,intcount ; If a 'direct interrupt' occures    
set 7,(hl) ;  right after the TIOS-int, then
;  we want bit 7 to be set...
.exit_interrupt ;
exx ; Swap to shadow registers.
ex af,af ; So the TIOS swaps back to the
;  normal ones... (the ones we saved
;  with push/pops)
rst $38 ;
di ; 'BIG' HOLE HERE... (TIOS does ei...)
ex af,af ;
exx ;
;
ld hl,intcount ; Interrupt returned correctly, so
res 7,(hl) ;  we reset our error-condition...
;
pop iy ;
pop bc ;
pop de ;
pop hl ;
pop af ;
ei ;
ret ;
.int_fix ;
pop af ; Pop AF back
ex af,af ; Fix shadowregs back
exx ;
pop bc ; Pop the returnpoint of RST $38
;  from the stack
jr exit_interrupt ; Continue with interrupt
.IntProcEnd
.jump_over

; Memory usage in statvars:
; -------------------------------------------
; $858F / $85FF - 113 bytes - free
; $8600 / $8700 - 256 bytes - IV table
; $8701 / $8786 - 134 bytes - free
; $8787 / $8789 -   3 bytes - JP IntProcStart
; $878A         -   1 byte  - intcount        <--
; $878B / $87A2 -  24 bytes - free
; -------------------------------------------


The loader, not really needed to get the picture though.

{z88dk}/lib/int83.asm

; Ti83 interrupt loader - by Henk Poley
; Based upon several sources, uses statvars to put the IV-table and JP
;-----------------------------------------------------------------------------
; You only need to have an interrupt marked with IntProcStart
;  at the beginning, since the on the Ti83 programs stay where
;  they are untill you quit. (you need to enable IM2 yourself)
;-----------------------------------------------------------------------------

im 1 ;
res 6,(iy+9) ; stats not valid
ld a,$86 ; locate vector table at $8600-$8700
ld i,a ;
ld bc,$0100 ; vector table is 256 bytes
ld h,a ;
ld l,c ; HL = $8600
ld d,a ;
ld e,b ; DE = $8601
inc a ; A  = $87
ld (hl),a ; interrupt "program" located at 8787h
ldir ;
;
ld l,a ; HL = $8787
ld (hl),$C3 ; Put a JP IntProcStart at $8787
inc hl ;
ld (hl),IntProcStart&$FF ;
inc hl ;
ld (hl),IntProcStart/256 ;


; Registers by now:
; -------------------------------------------
; A  = $87
; HL = $8789
; DE = $8701
; BC = $0000
; F  = carry flag is preserved
; -------------------------------------------
; Memory usage in statvars:
; -------------------------------------------
; $858F / $85FF - 113 bytes - free
; $8600 / $8700 - 256 bytes - IV table
; $8701 / $8786 - 134 bytes - free
; $8787 / $8789 -   3 bytes - JP IntProcStart
; $878A / $87A2 -  25 bytes - free
; -------------------------------------------
; See the interrupt routines themselves for
;  further info of memory useage.