Bu başlığı taslaklarda buldum. 2014'de yazmış ve taslaklara atmışım. Muhtemelen eksiktir ve hatalar da vardı. Ama 5 senedir orada duracağına yayınlıyorum Retro camiasında sık sık dile getirilen bir soru vardır: Madem CPC ve Speccy ailesi bu kadar benziyor, peki uyumluk oranı ne kadar yüksek ve gerçekçi? Şimdi size bu konuya dair örneklem teşkil edebilecek enteresan bir çalışmadan bahsedeceğim. Haberdar olmayanlar için ilginç olacaktır.
Olay şu: 40Crisis nickli bir user, bazı Speccy oyunlarını CPC üzerinde çalışacak şekilde modifiye etmiş. Kendi açıklaması şu şekilde:
For performance reason, Z80 code is not emulated.
Original Zx Spectrum rom and ram code from Maziacs Zx Spectrum is executed by CPC Z80 at the same memory locations and behave on the cpc exactly as it does on a real zx spectrum.
Only calls to routines doing I/O hardware (keyboard/joystick/sound) and display routines are patched in code to point to CPC emulated routines.
Özetle; Z80 kodu performans kaygılarından dolayı emule edilmedi, Maziacs'a değin Speccy RAM ve ROM kodları CPC Z80'i tarafından aynı hafıza adreslerinde çalıştırıldı ve CPC üzerinde tamamen Speccy'deki gibi tepki verdi diyor. Devamında da şunu ekliyor: Kod üzerinde sadece; Giriş/Çıkış birimlerine(Tuştakımı-Joy-Ses) ve görüntülemeye istinaden doğrudan çağrı rutinleri, CPC tarafından emule edilmiş rutinleri kullanacak şekilde yamalandı.
Bir diğer nokta ise; işin bir kısmı CPC Z80'i tarafından ve kalanı da bizati CPC tarafından yapılacak şekilde yamalandı ise neden Speccy Romlarına ihtiyaç duyulduğu hadisesi ki; o konuda da 40Crisis'in şöyle bir açıklaması mevcut:
Partial Sinclair Zx Spectrum 48k Rom emulation is implemented because the original game
use about 11K of Zx Spectrum Basic to handle menus.
Kısaca; orjinal oyunun menü olaylarını halletmek için Spectrum Basic'in 11K'lık bir kısmını kullanmasından dolayı, kısmi Speccy Rom emulasyonu uygulandı diyor.
Elbette önemli bir husus da, bu emulasyon sonucu olarak iki makina arasındaki hız farkı ve grafiklerin ekrana basılması hadisesi. Bu noktada 40Crisis'in yanıtı şöyle:
Zx spectrum version renders the 3d display zone in a linear buffer of 116 lines 32 bytes long,
then this buffer is transfered to zx spectrum video memory line by line 30 bytes per line
copied with ldir instruction.
The display for this buffer is most of the time in black and white colors but the white color
can be changed to other color in specific occasions (ammno shoots, end of rescue ).
Only text messages can have multiple colors on ant attack spectrum. They are added by calling the basic
rom which writes directly in video ram.
So the graphics stay all the time monochromatics in the working buffer.
The graphics being monochromatics, to render this on the cpc I just have to convert
8 pixels on one byte on the spectrum into two bytes on the cpc at the cpc format
with minimal instructions unrolled for the whole line to
avoid looping. I use the stack to get data from the zx spectrum buffer.
I wrote a first version that was like this:
push ix
ld ixh,116 ; 116 lines to copy
ld (save_sp),sp
ld sp,$A181 ; zx source buffer
ld de,$E042 ; dest cpc video memory
ld c,$0F ; mask
trans1:
ld b,$F0
trans:
; !!!! missing in this listing unroll 14 times the following block !!!!!
pop hl
ld a,l
and b
ld (de),a
inc e
ld a,l
add a,a
add a,a
add a,a
add a,a
ld (de),a
inc e
ld a,h
and b
ld (de),a
inc e
ld a,h
add a,a
add a,a
add a,a
add a,a
ld (de),a
inc e
pop hl
ld a,l
and b
ld (de),a
inc e
ld a,l
add a,a
add a,a
add a,a
add a,a
ld (de),a
inc e
ld a,h
and b
ld (de),a
inc e
ld a,h
add a,a
add a,a
add a,a
add a,a
ld (de),a
pop hl
ld hl,2048-59
add hl,de
jr nc,no_overflow
ld de,$C000+64
add hl,de
no_overflow:
ex de,hl
dec ixh
jp nz,trans1
ld sp,(save_sp)
pop ix
ret
save_sp: .dw 0
Then I found an optimisation (4 add a,a instructions replaced with an and instruction) by
duplicating the black color, using only 3 colors for the display.
Pen 0 is white pen 1 is black pen 2 is black.
It looks now like this:
push ix
ld ixh,116 ; 116 lines to copy
ld (save_sp),sp
ld sp,$A181 ; zx source buffer
ld de,$E042 ; dest cpc video memory
ld bc,$F00F ; mask for left/right pixels on cpc
trans1:
; !!!! missing in this listing unroll 14 times the following block !!!!!
pop hl
ld a,l
and b
ld (de),a
inc e
ld a,l
and c
ld (de),a
inc e
ld a,h
and b
ld (de),a
inc e
ld a,h
and c
ld (de),a
inc e
pop hl
ld a,l
and b
ld (de),a
inc e
ld a,l
and c
ld (de),a
inc e
ld a,h
and b
ld (de),a
inc e
ld a,h
and c
ld (de),a
pop hl
ld hl,2048-59
add hl,de
jr nc,no_overflow
ld de,$C000+64
add hl,de
no_overflow:
ex de,hl
dec ixh
jp nz,trans1
ld sp,(save_sp)
pop ix
ret
save_sp: .dw 0
In zx Spectrum emulator Fuse I measured 100074 Tstates to transfer whole buffer.
1 Tstate = 1 / 3500000 s
In Cpc emulator Arnold I measured 42102 Nops to transfer whole buffer.
1 Nops = 1 / 1000000 s
If I'm right Zx spectrum display routine is 0.042102/0.028592 = 1.47 faster than cpc display
http://cpcrulez.fr/GamesTest/ant_attack.htmThe Making of 'Ant Attack!'http://www.cpcwiki.eu/forum/news-events/ant-attack-sinclair-zx-spectrum-emulator-for-amstrad-cpc-6128()/http://www.cpcwiki.eu/forum/news-events/maziacs-sinclair-zx-spectrum-emulator-for-amstrad-cpc/