Welcome to Schneider / Amstrad CPC Forum. Please login or sign up.

20. April 2024, 01:38:12

Login with username, password and session length

Shoutbox

TFM

2024-04-08, 20:42:44
Happy Sonnenfinsternis!  :)

TFM

2024-01-15, 17:06:57
Momentan billige Farbbänder auf Ebay für PCW

Devilmarkus

2023-07-09, 10:37:40
Zweiter 👋😂🤣

TFM

2023-06-13, 14:21:49
Sommerloch!

TFM

2023-05-30, 17:00:20
Erster ;-)

Recent

Members
Stats
  • Total Posts: 11,695
  • Total Topics: 1,336
  • Online today: 185
  • Online ever: 1,724
  • (16. January 2020, 00:18:45)
Users Online
Users: 1
Guests: 213
Total: 214

213 Guests, 1 User
Dobbertin

Wie programmiert man einen Interrupt in Z80

Started by oobdoo, 15. February 2015, 14:25:19

Previous topic - Next topic

0 Members and 1 Guest are viewing this topic.

oobdoo

Ich bin auf der Suche nach einer Möglichkeit, einen Interrupt zu programmieren, steige aber bei der Firmware nicht durch.  :(
Wie stellt man es da, das eine Aktion einmal oder öfter pro Sekunde gestartet wird?
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

almasys

Hier hilft z.B. das Schneider CPC Systembuch: http://k1.spdns.de/Vintage/Schneider%20CPC/Das%20Schneider%20CPC%20Systembuch/z138.htm

Ansonsten gab es auch im Schneider Magazin bzw. Computer Partner eine gute Serie dazu, müsste ich mal raussuchen.

Viel Erfolg,
AMSi

TFM

Du könntest natürlich auch einfach den Interrupt an Adresse &0038 abfangen und in dein Programm umleiten. In dem Fall gibt es sechs Interrupts pro Bild (also pro 1/50 Sekunde). Und jedes 6te mal kannst Du testen ob der Elektronenstrahl zurück läuft, um den Bildaufbau zu synchronisieren.

Das funktioniert aber nur solange du das untere RAM eingeblendet hast, dann im ROM würde ja noch die alte Interrupt Routine stehen.
TFM of FutureSoft
http://www.futureos.de --> Das Betriebssystem FutureOS (Update: 20.12.2023)
http://futureos.cpc-live.com/files/LambdaSpeak_RSX_by_TFM.zip --> RSX ROM für LambdaSpeak (Update: 26.12.2021)

oobdoo

Ich hatte eigentlich auf einen kleinen Codeschnipsel gehofft. So muß ich ja doch wieder selber denken. Ich weiß nur das ich vor 30 Jahren mal was versucht hatte und das ging nach hinten los.   :(
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

almasys

'n Abend!

Oh, Z80, geht es überhaupt um den CPC?

Was soll die aufzurufende Routine tun? Von asynchronen Events aus lassen sich die wenigsten Firmwareroutinen nutzen. Muss sie synchron zum Strahlrücklauf aufgerufen werden?

Gute Nacht,
AlMaSys

oobdoo

Ööööhh...  :gruebel:
Da soll einfach nur was regelmäßig aufgerufen werden. Strahlrücklauf ist nicht so wichtig, nur die Regelmäßgkeit vom Aufruf würde ich gerne steuern können. 1x pro Sekunde oder 5x oder nur alle 2 Sekunden. Irgendwie sowas.
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

oobdoo

Mein erster Interrupt.  :00008351: :00008351: :00008351: :00008351: :00008351:

Gibt (fast) im Sekundentakt den Buchstaben A aus. Heute mal voll stolz auf mich bin.  :jubelaola:

org &4000

InterruptInit:
LD HL,BlocEvent
LD DE,InterruptHandle
LD BC,#8100
call #BCD7
ret

InterruptDone:
LD HL,BlocEvent
call #BCDD
ret
InterruptHandle:
DI
ld a,(counter)
dec a
ld (counter),a
cp 0
jr nz,nixmachen

;; was soll ich hier machen?
ld a,65
call &bb5a
          ld a,50
          ld (counter),a


.nixmachen

          ei
          ret


BlocEvent:
DS 16

.counter
defb 50
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

oobdoo

Wenn ich keine Fehler beim Abtippen gemacht habe, hier das erste Listing aus https://cpcwiki.de/forum/index.php/topic,282.msg2022.html#msg2022

org &a000
ld hl,free4
ld bc,tab1
call &bcd1
ret

.free4
defs 4
.tab1
defw ntab

jp init2
jp aus
.ntab
defb "O","N"+&80
defb "O","F","F"+&80
defb 0

.init2
ld a,0
call &bd1c
call &bd19
ld hl,block
call &bce3
di
ld a,6
ld (auf),a
call &bd19
ei
ret

.aus
ld hl,block
call &bce6
ld a,2
call &bd1c
ret

.block
defw 0
defw 0
defb 0
defb &81
defw routi
defb 0
defw 0

.routi
ld a,(auf)
dec a
ld (auf),a
cp 0
jr z,mod0
cp 2
ret nz
ld a,2
jp &bd1c
.mod0
ld a,6
ld (auf),a
ld a,0
jp &bd1c

.auf
defb 6

CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

Devilmarkus

Wer keinen Assembler zur Hand hat:

10 AD=&A000:L=&006A
20 READ a:POKE AD+P,a
30 P=P+1:IF P=L THEN CALL &A000:END
40 GOTO 20
50 DATA &21,&0A,&A0,&01,&0E,&A0,&CD,&D1,&BC,&C9,&00,&00,&00,&00,&16,&A0
60 DATA &C3,&1C,&A0,&C3,&35,&A0,&4F,&CE,&4F,&46,&C6,&00,&3E,&00,&CD,&1C
70 DATA &BD,&CD,&19,&BD,&21,&41,&A0,&CD,&E3,&BC,&F3,&3E,&06,&32,&69,&A0
80 DATA &CD,&19,&BD,&FB,&C9,&21,&41,&A0,&CD,&E6,&BC,&3E,&02,&CD,&1C,&BD
90 DATA &C9,&00,&00,&00,&00,&00,&81,&4C,&A0,&00,&00,&00,&3A,&69,&A0,&3D
100 DATA &32,&69,&A0,&FE,&00,&28,&08,&FE,&02,&C0,&3E,&02,&C3,&1C,&BD,&3E
110 DATA &06,&32,&69,&A0,&3E,&00,&C3,&1C,&BD,&06
https://cpcwiki.de
Dein Deutsches CPCWiki!

oobdoo

Das bekomm ich aber net mit Copy/Paste in den CPC rein.  :zunge0020:
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

Devilmarkus

#10
Hab mal bissl am Code gefummelt...
So ist er etwas Übersichtlicher:

org &a000

uppermode equ 0
lowermode equ 1
resetmode equ 1

ld hl,free4
ld bc,tab1
call &bcd1
ret

.free4
defs 4
.tab1
defw ntab

jp init2
jp aus
.ntab
defb "O","N"+&80
defb "O","F","F"+&80
defb 0

.init2
ld a,0
call &bd1c
call &bd19
ld hl,block
call &bce3
di
ld a,6
ld (auf),a
call &bd19
ei
ret

.aus
ld hl,block
call &bce6
ld a,resetmode
call &bd1c
ret

.block
defw 0
defw 0
defb 0
defb &81
defw routi
defb 0
defw 0

.routi
ld a,(auf)
dec a
ld (auf),a
cp 0
jr z,mod0
cp 2
ret nz
ld a,lowermode
jp &bd1c
.mod0
ld a,6
ld (auf),a
ld a,uppermode
jp &bd1c

.auf
defb 6


Was mich ja mal interessieren würde:
Bekommt man den Mode-Split um genau 1 Pixelzeile nach Oben verschoben?
https://cpcwiki.de
Dein Deutsches CPCWiki!

oobdoo

Quote from: Devilmarkus on 21. February 2015, 20:25:15
Bekommt man den Mode-Split um genau 1 Pixelzeile nach Oben verschoben?
Was mich interessieren würde ist, kann man überhaupt am CPC auf die gewünschte Rasterzeile warten?
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

TFM

Ja mit viel Mathematik (nicht so schlimm, Du musst das ja nur einmal berechnen) und das HALT Kommando.

HALT wartet bis ein Interrupt auftritt, es geht also noch dem HALT Kommando im Code dann weiter, wenn sich der Elektronenstrahl auf einer von sechst ganz definierten Stellen befindet.

Um abzufragen ob der Elektronenstrahl gerade zurück läuft kann man folgendes benutzten:


02006                     ;Auf FRAME warten
02007                     ;
02008                     ;Manip. AF, B
02009                     
02010  93B9  06 F5         FRA     LD    B,&F5
02011  93BB                JSZ
02011  93BB  ED 78                 IN    A,(C)
02011  93BD  0F                    RRCA 
02011  93BE  30 FB                 JR    NC,JSZ       ;V-Sync abwarten
02012                     
02013  93C0  C9                    RET   

TFM of FutureSoft
http://www.futureos.de --> Das Betriebssystem FutureOS (Update: 20.12.2023)
http://futureos.cpc-live.com/files/LambdaSpeak_RSX_by_TFM.zip --> RSX ROM für LambdaSpeak (Update: 26.12.2021)

oobdoo

Sehe ich das richtig, das zwischen einem DI&EI ein HALT ewig warten würde?

Mir ist aber immer noch nicht klar, wie ein Rasterzeileninterrupt auf dem CPC funktioniert.
Hab eh noch meine Schwierigkeiten, das mit einem Interrupt richtig hin zu bekommen (siehe Lustige Bugs in FruttyMan).

Obwohl ich bei den Bildschirmausgaben DI/EI verwende, habe ich dort merkwürdige grafische Effekte.  :(
CPC 464/6128, 464/6128+, GX4000 | Atari 2600, 600XL, 800XL/XE, Portfolio | C64/II/G/R/SX, VC20, TC64 | LC 80, MPF-I | ZX81, AX81, ZX Spectrum 48k, ZX Spectrum+2 | Amiga 500/600/2000, A2630, A2088

Devilmarkus

Kann es sein, dass du Speicher aus dem ROM einblendest? Im Screen-RAM?
https://cpcwiki.de
Dein Deutsches CPCWiki!