ZX Spectrum Haladóknak
Felhasználói segédlet
1986 - Meggyesházi János, Pintér Tibor
Hűen a Spectrum hazájának számítógépes-irodalmi tradícióihoz, a könyv létrehozásában segédkezők közül szeretnénk köszönetét mondani: Berényi Péternek, Fried Katalinnak, Juhász Lehelnek, Szulyovszky Zsoltnak a baráti és alkotói együttműködéséért. |
Tartalom
A mikroelektronika legdinamikusabban fejlődő ága a számítógépek világa.
Rohamléptekkel terjed a PC-láz. Tünet vagy divat? Talán mindkettő. A kisszámítógépek egyre több helyen nyernek polgárjogot: munkahelyeken, iskolákban, otthonokban. Kiemelkedik közülük a brit ipar "fenegyerekének", Clive Sinclairnek - bocsánat: Sir Clive-nak! - egyik legsikeresebb konstrukciója, a ZX Spectrum.
Könyvünk nem gépismertető, nem tankönyv, nem divatos módszerek summázata. A címben foglaltakra vállalkozik: haladó fokon szeretne segíteni a gépet használók széles táborának.
Reméljük, hogy munkánk elmélyíti az Olvasó Spectrummal kötött barátságát.
A szerzők
A gép hardver jellemzőit itt csak vázlatosan érintjük, figyelmünket inkább a tárfelosztásra és a BASIC értelmezőprogram (interpreter) sajátosságainak ismertetésére fordítjuk.
1.1. Hardver áttekintés
A nyomtatott áramköri kártya legfontosabb elemei:
A fenti, jelentősebb alkotóelemek mellett a következőket találhatjuk az áramköri kártyán: tár IC-k, feszültségszabályozó, hangszóró, órajel-generá-tor, hűtőlemez, átmeneti tárak, kiszolgáló áramkörök, adatsín, címsín, ill. néhány kisebb alkatrész.
Szakaszunk elején a Spectrum tárcímeinek felhasználását bemutató tártérképet láthatjuk. A legalsó, a 0 és 16383 közötti tárcímeken ROM (read-only memory = csak olvasható tár található. A gyártó cég egy 16 kbyte, azaz 128 kbit hosszú, NMOS technológiájú, 27128 típusjelű ROM integrált áramkörben rögzítette a Spectrum alapszoftverét, a monitorprogramot. Ez tartalmazza a BASIC értelmezőprogramot kb. 8, az operációs rendszert kb. 7 és a karaktergenerátort kb. 1 kbyte területen. A számok körülbelüliek: a ROM-ban valamivel több, mint 1 k üres terület maradt. Alapvető funkciója, hogy a felhasználó BASIC programokat írhasson, ill. futtathasson általa. A rendszer üzembe helyezése után a vezérlés automatikusan a monitorprogramra kerül, kivéve a felhasználó által készített Z80 gépi kódú programokat. A ROM-rutinok használatáról részletesebben szól a 6. fejezet.
A ROM fölötti tárterületet RAM (random access memory = írható-olvasható tár) tölti ki. Két változatban került forgalomba: a 16 k-s a 32767-ig, míg a 48 k-s 65535-ig terjedő címtartományt használja. A RAM felső címhatárát a P RAMT nevű rendszerváltozó tárolja.
A 16384 és 22527 közötti címeken, a képernyőterületen (display file) tárolja a Spectrum a nagyfelbontású tévéképet. A képernyő minden karakterpozíciója egy 8x8-as elemi képpontokból felépülő négyzet, amelyen minden egyes képpont 0 (paper = papírszín), ill. 1 (ink = tintaszín) értéket vehet fel. Ez nagyon hasonló a Sinclair cég előző gépén, a ZX81-en használatos PLOT és UNPLOT funkcióhoz, csak lényegesen finomabb felbontásban. A teljes kép 24 függőleges és 32 vízszintes pozíciót tartalmaz, így összesen 49152 bit, azaz 6144 byte képinformációról beszélhetünk.
A 768 karakterpozícióból valamennyi felveheti a nyolc papír, ill. nyolc tintaszín valamelyikét, fényessége lehet normál, ill. extra, villogása be- vagy kikapcsolt. A 22528 és 23295 közötti címtartomány tárolja a karakterpozíci-ók aktuális jellemzőit (attributes). A tár felülről lefelé soronként, egy soron belül balról jobbra haladva tartalmazza a jellemzőket, az ún. attribútumokat. Egy byte-on belül a
beállítását tartalmazza.
A képinformáció az előbbi jellemzőkkel együtt tehát összesen 6912 byte-ot foglal el.
A 23296 és 23551 címek által határolt tartomány a ZX Printer átmeneti tárolója. Neve nyomtatópuffer (printer buffer). Ezt a 256 byte-ot emellett felhasználhatjuk rövid, gépi kódú rutinok tárolására, ill. áthelyezhető rutinok paraméterátadására.
A következő 182 byte hosszú területet (23552.. .23733) a rendszerváltozók (system variables) kötik le. Részletes tárgyalásukat 1. a 2. fejezetben.
A 23734 címen kezdődő terület a Microdrive térkép. Felhasználásához szükséges az Interface 1 és Microdrive egység csatlakoztatása. (Részletesen 1. a 7. fejezetben.)
A következő tartomány, a csatornainformáció kezdőcíme a CHANS rendszerváltozó tartalmától függ. Alapkiépítése esetén négy csatornáról beszélhetünk:
Bővítők nélküli gépen az információk a 23734 és 23754 címek közti 21 byte-on helyezkednek el.
BASIC programunk a PROG rendszerváltozóban tárolt címtől kezdődik. Ez alapkiépítésű gépen 23755. Természetesen Microdrive egység(ek) csatlakoztatása esetén a kezdőcím feljebb tolódik. A BASIC terület méretét a programsorok száma határozza meg.
A tárolás menete: az első két byte a programsor számát jelöli, elöl a nagyobb, hátul a kisebb helyértékű byte. A harmadik és negyedik byte a fennmaradó hosszúságot jelöli, elöl a kisebb, hátul a nagyobb helyértékű byte áll. Az ötödik byte-tól a sorvégi ENTER karakterig tárolódik az aktuális BASIC sor, ami alfanumerikus karakterek esetén az ASCII kódot jelenti, kulcsszavak és speciális karakterek esetén a Sinclair rendszer kódjait.
A BASIC változók a BASIC terület fölött találhatók. Területük kezdőcímét a VARS rendszerváltozó értéke, hosszát a definiált változók mennyisége határozza meg. Utolsó byte-ja a végjelző karakter (dec. 128).
Az éppen szerkesztés alatt álló BASIC parancs- vagy programsort a szerkesztési terület tartalmazza. Kezdőcíme az E LINE rendszerváltozóban van.
A munkaterület kezdőcímét a WORKSP rendszerváltozó értéke határozza meg. A Spectrum rendszer ezt a tartományt használata után törli, így igen takarékosan bánik a munkaterülettel. Feladata a füzér- (string-) kezelés, adatbevitel stb.
A kalkulátorverem az ún. LIFO (Last In First Out) elv szerint működik, azaz a verem tetején tárolt érték a legutolsó. Kezdőcímét az STKBOT, végeimét az STKEND rendszerváltozó mutatja. Feladata lebegőpontos számok, egészek, ill. füzérparaméterek 5 byte-os tárolása.
A kalkulátorverem és a processzorverem közötti területet, amely a felhasználó számára szabadon hozzáférhető, tartalékterületnek nevezzük.
Az ezután következő processzorverem a Z80 processzor munkaterülete. Veremmutatója az utolsóként betöltött byte-ra mutat.
A GO SUB verem a szubrutinhívás visszatérési címét tárolja, a tárban lefelé bővülve.
Végül a tár legfelső 168 byte-ját az UDG terület, azaz a felhasználói karakterek területe foglalja el. A felhasználó az A-tól U-ig terjedő betűk bitmintáit megváltoztathatja, ezzel 21 saját karaktert definiálhat.
1.3. Szoftver áttekintés
A Spectrumon BASIC nyelvű és gépi kódú programokat futtathatunk. A BASIC programokat a Spectrum BASIC interpretere segítségével hozhatjuk létre, ill. hajthatjuk végre. (Vigyázat! A Spectrum BASIC semmilyen más mikroszámítógép BASIC-jével nem kompatibilis! 1986-ban került forgalomba a HT 3080C számítógép, amely egy segédprogram (emulátor) segítségével kompatibilis a Spectrummal.) Az interpreter hatékonyan támogatja a programellenőrzést, a programok összefésülését és az automatikus indítást. Gépi kódú programokat különböző fordítóprogramok (assemblerek) segítségével hozhatunk létre. Visszafejtésükhöz többféle disassembler programot használhatunk. Részletesebben ezt a 3. fejezetben tárgyaljuk.
A gépi kódú programok alapvető védelmét a CLEAR n parancs biztosítja (ahol n az érvényes RAM cím, 23821 és 32767, ill. 65535 között). Ily módon a RAMTOP rendszerváltozó értéke változtatható. Ennek elmulasztása esetén a rendszer felülírhatja a RAMTOP alatti területet, ami a program szempontjából végzetes lehet. Viszont a beállított RAMTOP érték feletti területet a rendszer nem használja működéséhez, még a NEW utasítás sem befolyásolja. Törlése csak a gép kikapcsolásával vagy szoftver úton való törléssel, ill. felülírással lehetséges.
1.4. Kazettás állománykezelés
A ZX81 meglehetősen bizonytalan magnetofonkezelésből okulva a gyártó cég egy igen megbízható tárolási rendszert dolgozott ki, amely egyszerű kazettás magnetofon használata esetén is jól működik. Tekintsük át a kazettás állomány- (file-) kezelés legfontosabb utasításait!
Betöltés
LOAD "<név>"
esetén a gép csak az általunk megadott nevű BASIC programot tölti be, törli a tárban levő programot és változókat.
LOAD ""
működése az előzőhöz hasonló, itt a következő, a rendszer által felismert BASIC programot tölti be.
A továbbiakban csak a két idézőjeles jelölést használjuk, de a fentiek a következő állománytípusokra is alkalmazhatók.
LOAD "" SCREEN$
automatikusan a 16384 címtől, azaz a képernyőterület (screen = képernyő) kezdőcímétől kezdi el a kód betöltését. Felhasználása a képernyőtartalom hasonló formátumú kimentésén alapul. A korábban kazettára tárolt kép kódjának betöltésével kész ábrák állíthatók elő. Hasznos alkalmazása a hosszú, azaz közel öt perc betöltési idejű programok előtt valamilyen hatásos ábra megjelenítése, amit a különböző szoftver cégek reklámcélra használnak. Másik érdekes alkalmazási területe: némely "ügyesen" elbújtatott másolóprogram tárolása, hiszen a képernyőterület gyakorlatilag a RAM legelején van.
LOAD "" CODE
gépi kódú állomány betöltésére szolgál. Használata előtt ajánlatos a RAMTOP értékét a (betöltendő kód kezdőcíme mínusz 1) értékre beállítani. Természetesen nem szükségszerű, hogy a program kezdőcíme azonos legyen az indítócímmel.
LOAD "" CODE m, n
működése az előzőhöz hasonló, de a betöltés az m címtől kezdve, maximálisan n hosszúsággal végezhető el.
LOAD "" DATA a()
numerikus tömb betöltését végzi el.
LOAD "" DATA a$()
füzértömb betöltésére használható.
Kimentés
SAVE "<név>"
BASIC program kazettán való tárolására használható. Betöltés után a rendszer 0 OK üzenettel jelentkezik be.
SAVE "<név>" LINE n
automatikus indítást biztosít, azaz a vezérlést betöltés után az n sorszámú BASIC programsorra adja át. Megjegyzendő, hogy hosszú, sok változót tartalmazó program esetén érdemes kimentés előtt kiadni a direkt CLEAR parancsot, mert így időt és szalagot takaríthatunk meg.
SAVE "<név>" SCREEN$
kazettán rögzíti az aktuális képernyőtartalmat.
SAVE "<név>" CODE m, n m
kezdőcímtől, n hosszan tárol gépi kódú állományt.
SAVE "<név>" DATA a()
numerikus tömböt tárol.
SAVE "<név>" DATA a$()
füzértömböt tárol.
Ellenőrzés
VERIFY ""
BASIC programot ellenőriz.
VERIFY "" CODE
gépi kódú állományt azonosít.
A VERIFY a LOAD-hoz hasonló működésű, de a programot nem tölti a RAM-ba, hanem csak összehasonlítja a már ott levő tartalommal. Ha az összehasonlítás sikertelen, Tape Loading Error (Szalagbetöltési hiba) üzenetet kapunk.
A VERIFY a képernyőtartalom ellenőrzésére nem használható!
Összefűzés
MERGE ""
működése a LOAD utasításhoz hasonló, de segítségével több programot láncolhatunk össze. Az eredeti programhoz hozzáfésüli a láncolandó program azon számú sorait, amelyek nem szerepelnek az eredeti programban, ill. azonos sorszám esetén törli a régi sort és változót. Használatánál ügyelnünk kell arra, hogy az összefésülendő programokban lehetőleg ne legyenek azonos sorszámú sorok. Ajánlatos egy rendszert kidolgoznunk, ami szerint rutinjainkat bizonyos sorszámkonvenció szerint csoportosítjuk. Ennek az elvnek figyelembevételével BASIC programjaink modul- felépítésűek lehetnek, azaz gyakran használt rutinokat nem kell többször, gyakran fáradtságos munkával újra rögzítenünk.
A MERGE utasítás csak BASIC programok esetén használható. Még egy tulajdonságát említjük: az automatikus indítással kimentett programok összefésülése esetén a program nem indul el, tehát nem kell a sokszor bizonytalan kimenetelű BREAK-et használni.
1.5. Néhány tanács
Kazettatárunkat ne építsük fel 60 percnél hosszabb (90, ill. 120 perces) lejátszási idejű kazettákból!
Felhasználói szempontokat figyelembe véve különböztessünk meg tároló (archiváló), munka- és adatkezelő kazettákat! Tároló kazetta esetén használhatunk 60 perces kazettát, de ne feledkezzünk meg a dokumentálásról, azaz vezessük pontosan a kazettán található programok állományneveit és a hozzájuk tartozó számlálóállásokat! Ezzel sok bosszúságtól, keresgéléstől kímélhetjük meg magunkat. Munkaszalagnak célszerű rövidebb lejátszási idejű, a hazai belföldi forgalomban is árusított kazettát választanunk.
A gyakran használt segédprogramokat, ill. rutinokat is célszerű rövid kazettán tárolnunk.
Adatkezelő kazetta az a szalag, amelyre bizonyos szoftvertermékeknek szükségük van működésükhöz. (Rajz-, adatbáziskezelő programok stb.) Ennek lejátszási idejét a tárgyprogram által kezelt állomány hossza szerint méretezzük!
Ha egy kazettára már nem akarunk több programot felvinni, végső biztosítékként törjük ki a kazetta hátsó oldalán tárolható két kis fület, így programjaink védve lesznek a véletlen beletörlésektől!
Rendszeresen tisztítsuk meg magnetofonunk lejátszó-, ill. felvevőfejét!
Kazettát ne tároljunk tv-készülék (különösen színes) közelében! Hasonlóképpen SAVE, ill. LOAD közben a magnetofon a lehető legtávolabb legyen a tv-től.
Ha egy kazettán egy bizonyos programot keresünk, üssünk be a LOAD után egy nem létező, kitalált állománynevet! Így nemcsak "fül" után kereshetjük a programot, hanem a szalagon található programok nevei és típusai megjelennek a képernyőn. Miután megtaláltuk a keresett programot, a szalagon a program elejére állva LOAD ""-dal töltsük be!
Igen sokféle másolóprogram van forgalomban. A helyzet tulajdonképpen egy várostromhoz hasonló, amennyiben a szoftvertermékek gyártói különböző módon igyekeznek programjaikat megvédeni, míg a felhasználók szeretnék ezt a védelmet megkerülni és a programot másolhatóvá tenni. Gondos mérlegelést kíván, hogy egy bizonyos programot milyen másolóval lehet birtokba venni. Részletesebben 1. a 8. fejezetben!
Végszükség esetén folyamodhatunk direkt (hangfrekvenciás) másoláshoz, de ennek kimenetele - különösen a gyorsított LOAD esetén - gyakran kétes.
Célszerű gépünkre RESET (alaphelyzetbe állító) kapcsolót szereltetni, így megkíméljük magunkat és a gépet az állandó ki- és becsatlakoztatástól. Lásd a 6. fejezetben!
Ha egy program betöltése nem sikerül, ne adjuk fel, kísérletezzünk! Próbáljuk meg a magnetofon hangerő- és hangszínszabályozójának több állásában megismételni a betöltést!
Ne sajnáljuk az időt a kimentett program ellenőrzésére, vagy ha ez nem lehetséges, töltsük be és próbáljuk ki a programot!
Képernyőterv (SCREENS) esetén legalább két kimentést javaslunk!
Ha igen hosszú ideje dolgozunk egy programon, vagy munkánkat félbeszakítjuk, végezzük el a kimentést, hiszen váratlan külső tényezők (pl. hálózati áramkimaradás) miatt esetleg több órás munkánk veszhet kárba!
Tartózkodjunk programozás közben a gép mozgatásától, rángatásától!
Ha pénztárcánk engedi, csatlakoztassunk professzionálisabb billentyűzetet a Spectrumhoz, hiszen a gumibillentyűzet a gép gyenge pontja! Természetesen a gyártó cég ezt figyelembe vette a Spectrum + fejlesztésénél, azt már a Sinclair QL-hez hasonló billentyűzettel látta el. Belülről azonban az is fóliaérintkezős megoldású!
Játékprogramokhoz használjunk botkormányt (joystick), ami nemcsak a játék élvezetét fokozza, de egyben kíméli a billentyűzetet a játék hevében olykor előforduló erőteljes igénybevételtől!
Ha magnetofonunk az EAR és MIC egyidejű csatlakoztatásakor felvétel esetén gerjed, akkor mindig csak az éppen használt (SAVE vagy LOAD), az üzemmódnak megfelelő dugót csatlakoztassuk!
Ha gépünket színes tévékészülékhez kívánjuk csatlakoztatni, ne használjunk a szériagyártás elejéről származó, azaz régi típusú magyar készüléket, ill. szovjet televíziót, mert azok csak SECAM rendszerben dolgoznak!
A rendszerváltozók a 23552..23733 közötti tárterületen helyezkednek el. A Spectrum rendszere a ROM használata során a különböző rutinok érintésekor lekérdezi a működésükhöz szükséges rendszerváltozók tartalmát. A tartalom megváltoztatásával BASIC-ből is beavatkozhatunk a gép rendszerébe. A kétbyte-os rendszerváltozók általában címeket tartalmaznak. Emeljük ki, hogy kétbyte-os forma esetén az első byte lesz a kisebb, a második a nagyobb helyértékű.
A rendszerváltozók vizsgálatára a PEEK, értékük megváltoztatására a POKE utasításokat használhatjuk. Legyen n a rendszerváltozó címe, v a beírandó érték. Két byte-os változó kiolvasására használjuk a PEEK n+256*PEEK (n+1) kifejezést!
Érték beírását pedig így végezhetjük el:
POKE n,v-256*INT (v/256)
POKE n+1,INT (v/256)
Tekintsük át az alapkiépítésű Spectrum rendszerváltozókat!
23552 KSTATE
Ezen a nyolc byte akkor használatos, amikor a rendszer a billentyűzetről olvas (KSTATE = keyboard State = billentyűzetállapot).23560 LAST K
Funkciója: a billentyűzeten legutoljára megnyomott gomb kódjának tárolása (LAST K = last key = utolsó billentyű).23561 REPDEL
Alapértéke: 35. Azt adja meg (50-ed másodpercben), hogy mennyi ideig kell egy billentyűt lenyomva tartani ahhoz, hogy kódja megismétlődjön (REPDEL = repeat delay = ismétlési késleltetés).23562 REPPER
Alapértéke: 5. Azt az időt adja meg (50-es másodpercben), amennyi egy leütött billentyű két, egymás utáni ismétlése között eltelik (REPPER = repeat period = ismétlési periódusidő).23563 DEFADD
Mindkét byte alapértéke 0. A programban definiált függvények argumentumának címét szolgáltatja (DEFADD = defined function address = definiált függvényeim).23565 K DATA
Alapértéke 0. Tárolja a színvezérlés második byte-ját, amit a rendszer a billentyűzetről kapott (K DATA = keyboard data = billentyűzetadatok).23566 TVDATA
A képernyőre irányuló színezés és pozicionálás (AT és TAB) vezérlésének tárolása (TVDATA = tv adatok).23568 STRMS
Stream és aktuális csatornacímek.23606 CHARS
Alapállapotban a 15360 címre mutat, ami a ROM-ban található karakterkészlet címénél 256-tal kisebb érték (CHARS = characters = karakterek). A NEW végrehajtása után kezdőértékét az INITIALISATION ROM rutin állítja be. A felhasználó az olyan programjaiban, amelyekben 21-nél több grafikus karakterre van szüksége, vagy ha a SCREEN$-t akarja használni a grafikus karakterekben, megváltoztatja a CHARS értékét, így akár több karakterkészletet is definiálhat. Különösen lényeges ez a sok grafikai elemet alkalmazó játékprogramoknál.23608 RASP
Alapértéke: 64. A figyelmeztető hang (búgás) hosszúságát határozza meg. Itt jegyezzük meg, hogy a NEW végrehajtása nem állítja vissza a RASP, a PIP, a P-RAMT, és az UDG rendszerváltozók korábbi értékeit! A rendszert alapállapotba a RANDOMIZE USR 0 hozza (RASP = csikorgás).23609 PIP
Alapértéke 0. A billentyű lenyomása után megszólaló hang hosszúságát határozza meg. Átállítása olyan programokban javasolt, ahol kiemelt funk-ciója van a billentyűzetről bevitt információnak (pl. segédprogramok).23610 ERR NR
Az INITIALISATION során az IY regiszterpárt tölti fel a rendszer az ERR NR rendszerváltozó címével. Értéke az üzenetkódnál mindig eggyel kisebb, tehát alapértéke a -1 miatt 255. (ERR NR = error number = hibaszám).23611 FLAGS
A BASIC interpreter vezérlésére szolgáló 7. bitje a szintaktikai jelzőbit. A ROM rutinba lépés során ez a jelzőbit törlődik, és ugyanebbe a rutinba történik a visszatérés szintaktikai hiba esetén. A hibaszámot a rendszer az ERR NR rendszerváltozóba tölti (FLAGS = jelzőbitek).23612 TV FLAG
A TV FLAG a televízióval kapcsolatos jelzőbiteket tartalmazza.23613 ERR SP
A processzorverem azon elemének címe, amely hiba esetén a visszatérési cím. Értéke alaphelyzetben 48 k-s gépen 65364, 16 k-s gépen. 32764 (ERR SP = error stack pointer = hiba veremmutató).23615 LIST SP
Az automatikus listázás visszatérési címének címe (LIST SP = listázási veremmutató).23617 MODE
Ez a rendszerváltozó a K, L, C, E, G kurzort határozza meg. Beállítását a ROM KEYBOARD-INPUT rutinja végzi. Jegyezzük meg, hogy ez a ROM rutin a LAST K és a FLAGS rendszerváltozó 5. bitje segítségével irányítja a bevitelt a billentyűzetről. Ez a rutin szabályozza a CAPS LOCK jelzőbitjét a FLAGS2 rendszerváltozó 3. bitjének segítségével (MODE = üzemmód).23618 NEWPPC
Az a sor, amire történik az ugrás (NEWPPC = new processor program counter = új utasításszámláló-érték).23620 NSPPC
Egy soron belül, ugrás esetén az utasítás száma. Természetesen előbb mindig a NEWPPC állítandó át (NSPPC = new statement processor program counter = "új utasítás" utasításszámláló-érték).23621 PPC
Annak a sornak a száma, amelyik éppen végrehajtódik (PPC = processor program counter = utasításszámláló értéke).23623 SUBPPC
Annak a soron belüli utasításnak a száma, amelyik éppen végrehajtódik. Szintén a BASIC interpreter vezérlő rutinja állítja be.23624 BORDCR
Alapértéke 56. Általában értéke a keretszín nyolcszorosa, de a képernyő alsó részének attribútumait is tárolja. Ha a képernyő alsó részét használjuk, az ATTR T rendszerváltozó a BORDCR értékét veszi fel.23625 E PPC
A program kurzor által kijelölt, aktuális sorszáma (E PPC = edited processor program counter = szerkesztési utasításszámláló-érték).23627 VARS
A változók (variables) címmutatója. A ROM fő végrehajtó rutinja több szubrutinban is vizsgálja tartalmát. Egy egyszerű fogás: ha nagyobb terjedelmű program elé egy rövid BASIC betöltőt készítünk, és szeretnénk befésülhetetlenné tenni, vigyünk a rendszerváltozó által megcímzett tárbyte-ba 0-át! Direkt utasítással: POKE PEEK 23627+256*PEEK 23628,0. Hasonlóképpen adjunk értéket egy változónak, pl. LET A=0. Ezután mentsük ki a betöltőt! Vigyázat, a program nem tartalmazhat változókat!23629 DEST
Az értékadásban szereplő változók címét tartalmazza (DEST = destination = célcím).23631 CHANS
Csatornaadat címmutató (CHANS = channels = csatornák).23633 CURCHL
A be/kivitelben szereplő információk címmutatója (CURCHL = current character location = aktuális karakterszám).23635 PROG
A BASIC program tárcíme. A 0 sorszámú és nem szerkeszthető sor előállítása: POKE PEEK 23635+256*PEEK 23636+1, 0.23637 NXTLIN
A programban következő sor címe (NXTLIN = next line = következő sor).23639 DAT ADD
A programlistában levő következő DATA listaelem címe.23641 E LINE
Az éppen beírt parancs címmutatója (E LINE = entered line = bevitt sor).23643 K CUR
A programkurzor címe.23645 CH ADD
A következő értelmezendő karakter címe. A monitorprogram RST 18H és RST 20H elemei hívják le a CH ADD rendszerváltozó tartalmát (CH ADD = character address = karaktereim).23647 X PTR
A kérdőjel utáni karakter címmutatója (X PTR = X pointer = X mutató).23649 WORKSP
A munkaterület kezdőcíme (WORKSP = workspace = munkaterület).23651 STKBOT
A kalkulátorverem alsó címe (STKBOT = stack bottom = a verem alja).23653 STKEND
A tartalékterület kezdőcíme. A ROM fő végrehajtó és automatikus listázó rutinjai vizsgálják (STKEND = stack end = a verem vége).23655 BREG
A kalkulátor b regiszterét tartalmazza.23656 MEM
A kalkulátor tárának kezdőcíme.23658 FLAGS2
A ROM KEYBOARD-INPUT rutinja által vizsgált jelzőbitek. POKE 23658,8 esetén nagybetűs üzemmód. Ha tartalma 0, a rendszer visszavált kisbetűkre (FLAGS = jelzőbitek).23659 DF SZ
A képernyő alsó részén található sorok száma. Vigyázat! 0-ba állítása a program "elszállását" okozza! (DF SZ = define size = méretmeghatározás).23660 S TOP
Szintén a ROM listázó rutinja használja. Értéke a legfelső programsor száma a listában (TOP = tető).23662 OLDPPC
Az az utasítássorszám, ahonnan a CONTINUE parancs kiadása után a programvégrehajtás folytatódik (OLDPPC = old processor program counter = régi utasításszámláló-érték).23664 OSPCC
Funkciója az előzőhöz hasonló, de itt az utasítás soron belüli száma tárolódik.23665 FLAGX
A rendszer által használt jelzőbitek.23666 STRLEN
Értékadás esetén a füzérváltozó hosszát tartalmazza (STRLEN = string length = füzérhossz).23668 T ADDR
A rendszer szintaktikai táblázatából a soron következő elem címét tartal-mazza (T ADDR = table address = táblázatcím).23670 SEED
Az RND kezdőértéke. Ezt módosíthatjuk a RANDOMIZE-zal (SEED = csíra).23672 FRAMES
Ez a hárombyte-os rendszerváltozó figyeli a rendszer belső óráját. Az összes perifériakezelő és kommunikációs műveleti idő alatt felfüggeszti működését. Legelöl áll a legkisebb helyértékű byte, értéke ötvened másodpercenként egyesével növekszik. Értéke 255 után 0 lesz, és a második byte eggyel nő. Tehát minden 256/50 másodperc esetén a második byte értéke is nullázódik, és akkor a harmadik byte értéke nő eggyel. Használatáról részletesen szól a gépkönyv 18. fejezete (FRAME = keret).23675 UDG
A felhasználó által definiált karakterterület kezdőcíme.23677 COORDS
23678
Az aktuálisan kijelzett képpont x, majd y koordinátája.23679 P POSN
Nyomtatási karakterpozíció (32-oszlopszám). (P POSN = printer position = nyomtatási pozíció.)23680 PR CC
Az LPRINT utasítás használja. A nyomtatandó pozíció címének kisebb helyértékű byte-ja (PR CC = printer character counter = nyomtatási karakterszámláló).23681
A rendszer nem használja.23682 ECHO E
A bemeneti puffer végétől számított oszlop- és sorszám (32-oszlopszám), (24-sorszám) (ECHO = karaktervisszaírás).23684 DF CC
A PRINT pozíció címmutatója a képernyőtárban (DF CC = display file character count = képernyőtárbeli karaktersorszám).23686 DFCCL
Funkciója az előzőhöz hasonló, csak a képernyő alsó részére vonatkoztatva (L = lower = alsó).23688 S POSN
23689
Az első byte a kiíratandó pozíció oszlopszámát, a második byte pedig a sorszámát adja meg (32-oszlopszám), (24-sorszám) (S POSN = screen position = képernyőpozíció).23690 SPOSNL
A funkciója az előzőhöz hasonló, csak a képernyő alsó részére vonatkozik. (L = Lower = alsó.)23692 SCR CT
A képernyő felfelé léptetéseinek száma (scroll count). Alapértéke 1. Ha a kiíratások előtt ennél nagyobb értéket adunk a változónak, úgy képernyő megteltekor elmarad a "Scroll?" kérdés, és a léptetés folyamatossá válik. A képernyőmozgatásokról, részletesen szól az 5. fejezet.23693 ATTR P
23694 MASK P
23695 ATTR T
23696 MASK T
23697 P FLAG
A ROM PRINT ANY szubrutinja vizsgálja ezt az öt rendszerváltozót. Belépéskor a DFCC, ill. DF CCL a HL regiszterpárba kerül, míg a BC regiszterpár a pozicionáló rendszerváltozók értékét veszi fel. Az A regiszter tartalmazza a karakterkódot. A P FLAG az aktuális karakter OVER vagy INVERSE módját jelzi. Ennek megfelelően állítja a rutin az attribútumokat, azaz a színinformációt tartalmazó ATTR P és T, ill. az ennek a P FLAG-től függő kihasználására szolgáló MASK P és T rendszerváltozók értékeit. (ATTR = attributes = attribútumok, MASK = maszk, P = permanent = tartós, T = temporary = ideiglenes.) Ideiglenes színek beállítását egy szubrutin végzi, amelynek végrehajtása során a P rendszerváltozók tartalma átmásolódik a T rendszerváltozókba. Végrehajtása során a rutin a P FLAG páratlan bitjeit a párosokba tölti. A képernyő alsó részén az ATTR T értéke a BORD CR értékét veszi fel. A MASK T nulla lesz. A P FLAG páros bitjei 0-t vesznek fel.23698 MEMBOT
Ezen a 30 byte-on tárolja a kalkulátor azokat a számokat, amelyeket a veremben nem tud elhelyezni (MEMBOT = memory bottom = alsó tár).23728
Ezt a byte-ot a rendszer nem használja, kivéve a hibás NMI rutint.23730 RAMTOP
A BASIC számára fenntartott terület utolsó byte-jának címe. Értékének változtatásáról gépi kódú program esetén l. részletesebben az 1. fejezetet (RAMTOP = RAM-tető)!23732 P RAMT
A RAM utolsó byte-jának címe, azaz a használható tárterület fizikai vége (P RAMT = physical RAM-top = fizikai RAM-tető).
A következőkben katalógustömörséggel áttekintjük a Z80 mikroprocesszor jellemzőit, elsősorban programozói szempontból.
PC (program counter)
Utasításszámláló: 16 bites regiszter. Ez a regiszter címezi a következő utasítást a tárban. A CPU azt az utasításkódot olvassa a tárból, amelyet a PC címez meg. Az Ml gépi ciklus, "memory fetch" (felhozatal a tárból) után automatikusan inkrementálódik.SP (stack pointer)
Veremmutató: 16 bites regiszter. Ez a regiszter címzi a veremként használt tárterületet (amely természetesen csak a RAM-ban lehet). A verem szubrutinhíváskor vagy a regiszterek tartalmának gyors tárba mentésénél használatos.IX, IY (indexregisters)
Két, indexelt címzésre használatos (16 bites) regiszter. Két-két 8-bites regiszterként használva, jelölésük:
XL, XH YL, YH.I (interrupt page address)
Megszakítási lapcímregiszter: 8-bites. Használatát l. később.R (refresh)
A dinamikus RAM 8-bites frissítő számlálója. A CPU minden egyes Ml ciklus után inkrementálja (mód 128) és az I regiszter tartalmával együtt kiküldi a címsínre. Az A15.A8 címvonalakra az I, az A7.A0 címvonalakra az R regiszter tartalma kerül.A (accumulator)
Akkumulátor: 8-bites regiszter. Az akkumulátorban aritmetikai/logikai műveletek hajtódnak végre az ALU segítségével.F (flags)
Jelzőbitek: 8-bites regiszter. A müveletvégrehajtás körülményeiről, ill. eredményéről ad kiegészítő tájékoztatást.
Felépítése:
S Z X H X P/V N C 7 6 5 4 3 2 1 0
C (0. bit: carry flag)
Átvitelijelző bit.
1 értéke jelzi, ha a művelet során a 7. bitről a fiktív 8. bithelyre átvitel kerülne. (Kétbyte-os műveleteknél a 15. bitről a 16-ra való átvitelt jelzi.)N (1. bit: add, subtract flag)
Összeadás, kivonás jelzőbit. Értéke
1, ha az előző művelet kivonás, ill.
0, ha az előző művelet összeadás volt. Ennek az ADD,A utasításnál van jelentősége, hogy a CPU helyesen módosítson.P/V (2. bit: parity / overflow flag)
Paritás/túlcsordulás jelzőbit. Értékeinek jelentése:
1 - túlcsordulás; páros paritás
0 - nincs túlcsordulás; páratlan paritás.X (3. bit)
Nincs specifikálva.
A CPU használja a vezérlésekhez.H (4. bit: half carry)
Félátvitel jelzőbit.
BCD (binárisan kódolt decimális) aritmetikánál használható.
1 értéke azt jelzi, hogy a 3-4. bit között van átvitel.X (5. bit)
Nincs specifikálva.Z (6. bit: zero flag)
Nulla jelzőbit. Értéke:
1, ha a művelet eredménye zérus volt.- S (7. bit: sign flag)
Előjel jelzőbit. Értéke:
1, ha az eredmény a kettes komplemens aritmetikában negatív volt.B,C,D,E,H,L (generál purpose registers)
Általános célú 8-bites regiszterek.A', F', B', C', D', E', H', L' (alternate registers)
Háttérregiszterek (valamennyi 8-bites). A CPU választhatóan vagy a fő- vagy a háttérregiszterekkel dolgozik.
Címsín
A0...A15 tárrekesz vagy be/kiviteli port címzésre használja a CPU. A 16 vonalon 2^16 byte = 64 kbyte címezhető.Adatsín
D0...D7. Az adatforgalmat biztosítja. A 8 vonalon egy byte-nyi adat továbbítható párhuzamosan.Vezérlőjelek
3.3. A Z80 utasításkészlete és címzési módjai
Az utasítások főbb csoportjai:
A címzési módok:
Közvetlen címzés: az operandus az utasításban szerepel. Például:
LD A,255
LD HL,65535
LD A,B
ADD HL,DE
Közvetett címzés: az operandus címe áll az utasításban. Például:
LD A,(HL)
LD A,(65535)
LD HL,(65535)
Indexelt címzés:
Az utasításban az operandus címeltolását adjuk meg. Például:
LD A,(IX+127)
Módosított nullalapos címzés:
0000H
0008H
0010H
0018H
0020H
0028H
0030H
0038H
helyeket szubrutinhíváskor e speciális címzési móddal minden más eljárásnál gyorsabban (11 gépi ciklussal) elérhetjük. Ez a címzés csak az RST utasításban használható.
Az utasítások áttekintése ábécérendben
ADC | OP1, OP2: összeadás, a C jelzőbittel együtt OP1:=OP1+OP2+C |
ADD | OP1, OP2 : összeadás OP1:=OP1+OP2 |
AND | OP1: Az A és OP1 között logikai ÉS műveletet végez. |
BIT | OP1, OP2: Az OP2 byte OP1-edik bitje invertálva a Z jelzőbitbe kerül. |
CALL | [OP1], OP2: szubrutinhívás (SP-1):=PCh (SP-2):=PCl PC:=OP2 |
CCF | C komplementálása |
CP | OP1 A:=A A-OP1 |
DAA | BCD konverziót hajt végre A:=A+konv. |
DEC | OP1: OP1 mértékét eggyel csökkenti OP1:=OP1-1. |
DI | a maszkolható megszakításkérést tiltja. |
DJNZ | e : B:=B-1 eredménye alapján, ha B<>0 PC:=PC+e feltételes relatív ugrást hajt végre. |
EI | megszakításengedélyezés. |
EX | OP1, OP2 : OP1 és OP2 tartalmát felcseréli. |
EXX | A BC, DE és HL regiszterpárokban lévő minden egyes 2 byte-os érték rendre felcserélődik a BC', DE' és HL' regiszterpárokban lévő 2 byte-os értékkel. |
HALT | a következő megszakításig megállítja a CPU-t. |
IM | 0,1,2: megszakításmód beállítása. |
IN | OP1, (OP2): OP2 perifériáról olvas az OP1-be. |
INC | OP1: növeli eggyel az OP1-et. OP1:=OP1+1. |
JP | OP1: PC:=OP1 ugrást hajt végre. |
JR | OP1: relatív ugrást hajt végre. PC:=PC+OP1 |
LD | OP1, OP2: OP2 tartalmát OP1-be másolja. OP1:=OP2 |
NEG | az akkumulátor kettes komplemensét képezi. A:=0-A |
OR | OP1: Az A és OP1 között logikai VAGY műveletet végez. |
OUT | (OP1),OP2: OP2-t kiküldi az OP1 perifériára. |
POP | OP1: OP1-be másolja a verem tetején levő elemet. OP:=(SP); SP:=SP+2 |
PUSH | OP1: a verem tetejére teszi OP1-et. (SP):=OP1; SP:=SP-2 |
RES | OP1, OP2: OP2 OP1-edik bit 0-ra állítja. OP2(OP1):=0. |
RET | visszatérés a szubrutinból. PC: = SP; SP:=SP+2 |
RLC | |
RL | |
RR | |
RRC | |
SLA | |
SRA | |
SRL | |
RST | p: 0 lapos szubrutinhívás PC:=0000+p |
SBC | OP1,OP2: kivonás C jelzőbittel együtt. OP1:=OP1-OP2-C |
SET | OP1,OP2: OP2 OP1-edik bitjét 1-re állítja. OP2(OP1):=1. |
SUB | OP1, OP2: kivonás. OP1:=OP1-OP2 |
XOR | OP1: Az A és OP1 között logikai kizáró VAGY műveletet végez. |
Az utasítások ismertetése funkcionális csoportok szerint
A részletes utasításleírásban a következő rövidítéseket használjuk (kódgeneráláskor a fordító a zárójelben felsorolt elemek - pl. regiszterek - nulláról indított sorszámát veszi figyelembe):
n | egybyte-os konstans (0...255) |
nn | kétbyte-os konstans (0...65535) |
r | regiszterek (B, C, D, E, H, L, A) |
m | egybyte-os operandus (B, C, D, E, H, L, (HL), A) |
s | m és n |
cc | állapotjelzők (NZ, Z, NC, C, PO, PE, P, M) |
pp | regiszterpárok (BC, DE, IX, SP) |
regiszterpárok (BC, DE, HL, AF) | |
rr | regiszterpárok (BC, DE, IY, SP) |
ss | regiszterpárok (BC, DE, HL, SP) |
ii | indexregiszterek (IX, IY) |
b | bitcím (0...7) |
d | címeltolás (offset) (-128...127) |
e | relatív cím (-126...129) |
i | XL, XHI, YL, YH az indexregiszterek alsó, ill. felső byte-jai |
rn | 16 bit-es cím ((BC), (DE), ..., (nn)) |
lo | logikai műveletek (ADD, ADC, SUB, SBC, AND, OR, XOR, CP) |
bs | bit teszt (BIT, RES, SET) |
cs | forgató, léptető műveletek (RLC, RRC, RL, RR, SLA, SRA, SLL, SRL) |
sc | jelző bitek (cc 1...4) |
p | 0 lapos szubrutinhívás (00, 08, 10, 18, 20, 28, 30, 38) |
bm | (LD, CP, IN, OUT) |
bv | (I, IR, D, DR) |
Az utasítások táblázata:
(1 gépi ciklus 3,5 MHz órajel-frekvencia mellett 0,286 µs)
8-bites töltő utasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
LD m,s | DD v. FD 40+08*m+s és XOR 40, ha va n d n az LD(HL),(HL) tiltott kód |
19 4 7 |
LD A,rn | 8*rn+0A nnL nnH |
7 13 |
LD rd,A | 8*rn+02 nnL nnH |
7 13 |
16-bites töltő utasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
LD ss,nn | DD v. FD 10*ss+01 |
10 |
LD ss,(nn) | ED 40+10*ss+0B nnL nnH |
20 |
LD (nn), | HL=22 nnL nnH |
16 |
LD ii,(nn) | DD v. FD 2A nnL nnH |
20 |
LD SP,HL LD SP,IX |
DD v. Fd F |
6 10 |
(A nagyobb érték mindig az indexregiszterekre vonatkozik!) | ||
PUSH qq | DD v. FD 60+10*qq+05 |
11 15 |
POP qq | DD v. FD 60+10*qq+01 |
10 14 |
8-bites aritmetikai utasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
ADD A,S | FF v. FD 80+lo*08+5 d és n ha n van, XOR 40 az A kódra |
n 7 ii 19 |
INC m | DD v. FD 00+m*08+04 |
(HL) 11 ii 23 |
DEC m | DD v. FD 00+m*08+05 |
r 4 (HL) 11 ii 23 |
16-bites aritmetikai utasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
ADD HL,ss ADD IX,pp ADD IY,rr |
DD v .FD 10*ss+09 pp rr |
11 15 15 |
ADC HL,ss | ED |
15 15 |
INC ss INC IX INC IY |
00+10*s+03 |
6 10 10 |
DEC ss DEC IX DEC IY |
00+10*ss+0B |
6 10 10 |
Eltolások, mozgatások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
cs m | CB 00+cs*8+M |
R 8 (hl) 15 II 23 |
RLCA ls (00) | 00+ls+8+07 |
4 |
RRCA ls (01) | ||
RLA ls (02) | ||
RRA ls (03) | ||
RLD | ED 6F |
18 |
RRD | ED B7 |
18 |
Ugróutasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
JP nn | C3 nnL nnH |
10 |
JP cc,nn | C0+8*cc+02 |
10 |
JR e | 18 e-2 |
12 |
NZ e | 10 e-2 |
8 / 13 |
(Nagyobb érték, ha a feltétele igaz.) | ||
JR sc,e | 18*ss+02 |
7 / 12 |
JP (HL) JP (IX) JP (IY) |
DD v. FD E9 |
(HL) 4 ii 8 |
Szubrutinhívások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
CALL nn | CD nnL nnH |
17 |
CALL cc,nn | C0+8*cc+08 |
10 / 17 |
RET | C9 |
10 |
RET cc | C0+8*cc+00 |
5 / 11 |
RETI | ED 4D |
14 |
RETN | ED 45 |
14 |
RST p | C0+8*cc+07 |
11 |
Be- / kiviteli műveletek:
mnemonik | kódgenerálás |
idő gépi ciklusban |
IN r,(C) | ED 80+r*8+00 ED |
12 |
OUT(C),r | 80+r*8+01 |
12 |
IN A,(n) | DB n |
11 |
OUT (n),A | D3 n |
11 |
Blokkműveletek (bm):
LD - töltés
CP - összehasonlítás
IN - beolvasás
OUT - kiírásA vezérlésállapotok (bv):
DE HL BC I +1 +1 -1 IR +1 +1 -1 mindaddig, míg BC 0 nem lesz D -1 -1 -1 DR -1 -1 -1 mindaddig, míg BC 0 nem lesz
mnemonik kódgenerálásidő gépi ciklusban [bm] [bv] ED
A0+8*bm+bv6 / 21 Egyéb utasítások:
mnemonik | kódgenerálás |
idő gépi ciklusban |
NOP | 00 |
4 |
DI | F3 |
4 |
EI | FB |
4 |
DAA | 27 |
4 |
SCF | 37 |
4 |
CPL | 2F |
4 |
CCF | 3F |
4 |
HALT | 76 |
4 |
IM 0 | ED 46 |
8 |
IM 1 | ED 56 |
8 |
IM 2 | ED 5E |
8 |
EXX | D9 |
4 |
EX AF,AF' | 08 |
4 |
EX(SP),HL | E3 |
4 |
EX(SP),IX | DD E3 |
4 |
EX(SP),IY | FD E3 |
4 |
EX DE,HL | EB |
4 |
NEG | ED 44 |
8 |
Jelzőbitek
A következő utasítások módosítják a jelzőbiteket:
Túlcsordulás-vizsgálat eredménye van a P/V bitben:
ADD | CP | (csak 8-bites OP esetén) |
ADC | NEG | |
SUB | INC | |
SBC | DEC |
Paritásvizsgálat eredménye van a P/V bitben:
AND | RR | SRA | RRD |
OR | RLC | SLL | DAA |
XOR | RRC | SRL | IN |
RL | SLA | RLD |
Egyéb utasítások:
CPL | SCF | CCF | BIT |
Megszakítási rendszer
A Z80-nak két megszakításvonala van: az egyik nemmaszkolható (nem tiltható), a másik maszkolható (tiltható, engedélyezhető). Az NMI (non-maskable interrupt = nemmaszkolható megszakítás) lábra érkező jel hatására PC: = 0066H
Itt kell tárolni azt a Z80 rutint, amely kiszolgálja a CPU-t. Ez azonban a Spectrumon nem működik. Valószínűleg programhibáról van szó, de lehet, hogy a gyártó szándékosan intézte így. A Spectrum rendszer RESET-et hajt végre, NMI ADD tartalma 0, visszatérés: RETN. Az INT (interrupt = megszakítás) lábra érkező jel hatására a CPU állapotától (mode) függően különböző módon aktivizálódik.
MODE 0:
A CPU az adatsínről veszi a végrehajtandó utasítás kódját (kódjait).
MODE 1:
CPU A 0038H címre ugrik, és ott hajtja végre az utasításokat.
MODE 2:
A CPU egy indextáblát feltételez az I/EXT címen, ahol I = A15.. ,A8, a tábla báziscímét tartalmazza; EXT = A7..,A0 perifériák vagy bármilyen programozói logika szerint elhelyezett byte az adatsínen. A CPU az így meghatározott címről (az indextábla adott eleméből) kiolvassa a kiszolgáló rutin címét, majd odaugrik.
IM 0, 1, 2-ből RETI utasítással tér vissza a CPU. Célszerű A0 = 0 érték, mert a legutolsó elem címe kilóg a tárlapból. Az I regiszter értéke a Spectrumon csak 80...FF lehet, mert különben az ULA leállítja a CPU-t vagy korlátozza a működést.
3.4. Assemblerek, disassemblerek
Ebben a szakaszban azokat az assembler és disassembler programokat tárgyaljuk, amelyekhez könnyen hozzáférhetnek a felhasználók a Spectrum klubokban.
3.4.1. EDITAS/MONITOR
16k-s és 48k-s változatban került forgalomba a PICTURESQUE programja. 48k-s gépeken egyszerre lehet hozzáférni a monitorhoz és az assemblerhez. A különböző tárméretre készült programok kombinálva is alkalmazhatók:
16k-s monitor és 48 k-s assembler vagy 16 k-s assembler és 16 k-s monitor.
MONITOR
Tárfelhasználása:
Töltése: LOAD ""
Indítása:
Bejelentkezése: Press BREAK for MONITOR
">" jel jelzi, hogy a monitor kész a parancs fogadására. Parancsok:
M nnnn (modify memory)
Tármódosítás, az nnnn címtől kezdődően. A rendszer a címmel és a tartalommal jelentkezik vissza, pl.:
>M 8000
> 8000 00
Utána nn beírásával a tartalom megváltoztatható, vagy ENTER lenyomásával továbbléptethető a vizsgált címtartomány. (X parancs az üzemmódból kilépteti a programot.)X (exit from command)
Megszünteti az adott parancsot, ill. kilép, és a ">" parancsváró karakter (prompt) jelenik meg. Nemcsak a sor elején adható ki, hanem bármikor, amikor a rendszer billentyűlenyomásra vár.I bbb llll nn (insert memory block)
Beszúr a bbbb címtől nn darab 00 byte-ot úgy, hogy llll címig a jelzett tárterületet legfeljebb tolja.D bbbb llll nn (delete memory block)
Töröl a bbbb címtől nn byte-ot úgy, hogy az llll címtől lefelé helyezi a tárblokkot. Az I parancs fordítottja.
I 8000 9000 FF
D 8000 90FF FF után a tár változatlan marad.A bbbb llll nnnn (area relocate)
Területáthelyezés: a bbbb címtől (1. byte) az llll címig (utolsó byte) terjedő tárblokkot áthelyezi az nnnn címre.F bbbb llll xx (fill memory)
Tárfeltöltést végez a bbbb címtől llll címig xx értékkel.Y (return)
Visszatérés a BASIC rendszerhez, mivel a monitor nem rendelkezik töltő, ill. tároló utasítással, így a BASIC SAVE-LOAD-ját használhatjuk a programok mentésére, ill. visszatöltésére.B aaaa (breakpoint)
Töréspontot helyez el az aaaa címen. Ha többbyte-os utasítást akarunk törésponttal lefedni, mindig az első byte-jának címét adjuk meg a B parancsban! A rendszer az aaaa címtől kezdve a CD, 0F, F7, CD, 0F, 77 byte-okat helyezi el, ez pedig nem más, mint a monitorhívás.J aaaa (jump adress)
Ugrás az aaaa címre és az ott talált gépi kódú program végrehajtása.K (kill breakpoint)
Visszahelyezi a töréspont előtti tártartalmat a visszajelzett címre (egyszerre csak egy töréspontot lehet beiktatni).R (registers)
Kiírja a CPU regiszterek tartalmát. (Töréspont után ad csak helyes eredményt.)C (continue from breakpoint)
Folytatja a törésponttól a végrehajtást, a töréspont ugyanott marad. (Ez ciklusok vizsgálatánál hasznos.)P bbbb llll (print memory contents)
A bbbb címtől kezdve az llll címig kiírja a tártartalmat. Egy sorba 8 byte-ot helyez.S aaaa (string entry)
Szöveg elhelyezése a tárban, az aaaa címtől kezdve. A parancsból a STOP billentyű lenyomására léphetünk ki.Z bbbb llll (disassembler)
A bbbb címtől az llll címig Z80 mnemonikok formájában írja ki a tár tartalmát.N (number conversion)
D xxxxx decimálisból hexadecimálissá, H yyyy hexadecimálisból decimálissá alakítja a számot.
EDITAS
Töltése: LOAD ""
Indítása: automatikus vagy
Bejelentkezése: NEW TEXT OR CONTINUE
N esetén hidegindítást,
C esetén melegindítást hajt végre.
Számok:
Műveletek: +, - Az EDITAS ezt a két műveletet fogadja el.
Konstansok: Bármely ASCII karakter " " közé zárva konstansként épül be a tárgyprogramba.
Parancsok:
K [/n]
Opcionális sorban, ahonnan a listázást kérjük. Tíz soronként szünetet tart. A listázást a szóközbillentyű lenyomásával folytathatjuk. "/" esetén a lista a ZX-Printer-en készül.CS/1 n
Az n számú sor a szerkesztési területre másolódik, és a képernyőn szerkeszthető úgy, mint a BASIC-ben.D [n]
n sorszámtól, vagy ha elhagyjuk, az előző értéktől automatikus sorszámozás jön létre, 10-es lépésközönként.A
Hidegindítást hajt végre, mindent töröl.N [n]
n lépésközzel n induló sorszámmal átszámozza a forrássorokat.Y
Kilépés az EDITAS-ból.X
Törli a forrásszöveget, de a szimboltáblát meghagyja.S "<név> T[EXT] / C[ODE]
A névvel jelzett állományt kimenti a szalagra: T opció esetén a forrás szöveget, C esetén a tárgykódot úgy, hogy az ORG parancsban megadott helyre lehet visszatölteni.V "<név>"
A névvel jelzett (ill. név hiányában a következő) állományt megkeresi a szalagon, és ellenőrzi a tárban levő kódot vagy szöveget.J "<név>"
A névvel megadott (ill. név hiányában a következő) állományt betölti a szalagról.
Assembler direktívák:
ORG <(kifejezés)>
A lefordítani kívánt tárgykód kezdőcímét adja meg. Ezzel a direktívával kell kezdeni a forrásszöveget. Csak egy lehet a forráslistában belőle. A megadott cím mindig nagyobb kell, hogy legyen, mint (PROG) = (STKEND+256). Ha az ORG parancs után "*" áll, akkor a munkaterület címe lesz az ideiglenes programszámláló.END
A forrásszöveg végét jelzi.DEFB nn (define byte)
Egy byte értékét helyezi el a fordítási címszámláló értékére.DEFW nnnn (define words)
Két byte-nyi értéket szúr a fordításba.DEFS nnnn (define storage)
Üres helyet (00) hagy a program futásánál esetleg felhasználni kívánt tárrészen. Lehet elhatárolni két modult is. Például:
L1
UJORGNOP
DEFS UJORG-L1
LD A,0FFHEz a módszer nagy tárlekötést von maga után.
DEFM "<füzér>" (define message)
Karaktersorozatot szúr be a tárgykódba.L DEFL <kifejezés> (define label) és
L EQU <kifejezés> (equal)
Az első címkedeklaráció, amely a továbbiakban újradefiniálható. A második értékadás, a későbbiekben nem módosítható (<kifejezés> a pillanatnyi tárgykód címmutatója is lehet).
Például:
L14
L14DEFL 8000H
LD A,L14
...
DEFL 9000H
LD HL,L14
...
Fordítás:
R <karakter>
Ha nincs megadva paraméter, csak a szimbólumtábla listázódik. Ha van paraméter, akkor forráslista és szimbólumtábla készül. Ha a paraméter "/"akkor a ZX-Printerre készül lista. Az M billentyű a listázást megállítja addig, míg lenyomva tartjuk. Ha a képernyőterületre akarunk programot fordítani, akkor:
- Y: vissza BASIC-be, majd
- direkt állítással:
POKE PROG, 0: POKE PROG+1,04: RAND USR EDITASEkkor már a rendszer elfogadja az ORG 4000H direktívát.
Ha a 48 k-s assemblert a 16 k-s monitorral töltjük be, akkor az EDITAS-ból M paranccsal a monitor, a monitorból J 0EE2DH paranccsal az EDITAS aktivizálható.
3.4.2. ASTRON/DISTRON
Egyszerűbben megvalósított assembler-disassembler programcsomag, így szerényebb lehetőségeket biztosít.
DISTRON (disassembler)
Töltése:
16k:
CLEAR 29291
LOAD "" CODE
48k:
CLEAR 59999
LOAD "" CODE
Indítása:
Bejelentkezése:
H esetén a számok hexadecimális, D esetén decimális alakban jelennek meg.
END ADDRESS, START ADDRESS-re (vég-, ill. kezdőcím) válaszolva kérjük a disassembler listát.
Parancsok:
S
Megállítja a visszafordítást.R
Új cím adható meg, ahonnan listáz.N
scroll-ból kilép.
A program áthelyezhető, ha
után a NEW ADDRESS DISTRON? kérdésre válaszolva az átfordított DISTRON-t a szalagra kimentjük, vagy a következő programmal relokáljuk:
LD DE,<(új cím)> (ez nagyobb, mint STKEND)
LD HL,6000
LD BC,2912
LDIR
RET
ASTRON (assembler)
Töltése: LOAD ""
Indítása: automatikus
Bejelentkezése: saját menü
Direktívák:
START
Kezdetjelző.END
Végjelző.ORG x,y
x a tárgyprogram puffere, y ahova a fordítás történik.DATAB
Megfelel az EDITAS DEFB direktívájának.DATAW
Megfelel az EDITAS DEFM direktívájának.DEFS
Ugyanaz mint az EDITAS-ban.DEFM
Ugyanaz mint az EDITAS-ban.
Parancs:
A (assembly)
Fordítás:
Az ASTRON-ban nincs EQU és DEFL, de van állandó címke, amely % jellel kezdődik. A többi címke mindig újradefiniálható. A programot a BASIC EDITOR-ával REM utasítás után írhatjuk be. A mentés, ill. a töltés a BASIC rendszer segítségével történik.
3.4.3. CRYSTAL COMPUTING monitor/assembler
Monitor
Töltése: LOAD ""
Indítása:
Bejelentkezése: LOADED OK
Parancsok:
A <(érték)> (assign)
Regiszter-értékadás. A regiszterhez rendelt decimális számot a £ jel vezeti be.B aaaa (break)
Az aaaa címen töréspontot helyez el. Amikor a végrehajtás a törésponthoz ér, a monitor a következő üzenettel jelentkezik.
"Q"-QUIT "C"-CONT "M"-MONITOR:
- Q: (quit) visszatérés a monitorba.
- C: (continue) a futás folytatása.
- M: a monitor speciális módja jelentkezik be, hogy különböző módosításokat és ellenőrzéseket hajthassunk végre.
C bbbb, llll, nnnn (copy)
bbbb címtől kezdve llll címig átmásol nnnn címre úgy, hogy semmilyen fölülírás nem történik.D aaaa (disassemble)
aaaa címtől kezdve visszafordított listát készít; kilépés BREAK-kel.E aaaa (edit)
Léptetés a következő tárcímre.
I: léptetés vissza, egy tárcímmel;
Q: kilépés a parancsmódhoz.F bbbb, llll, <minta> (find)
A mintát keresi bbbb címtől llll címig.
A minta lehet:
- 1 hexadecimális byte;
- 7 hexadecimális byte (a 7 közül bármelyikre megáll a keresés);
- ezek decimális alakban, "£" jellel bevezetve;
- max. 20 karakter hosszú karaktersorozat;
- a fentiek kombinációi.
G aaaa (goto)
aaaa címre adódik a vezérlés úgy, hogy a regisztertükör bemásolódik a CPU megfelelő regisztereibe.J, <cím1>,<cím2> (jump)
A <cím2>-<cím1>-2 kifejezést írja ki, ez az érték pl. egy relatív ugrás címeltolása lehet.M aaaa, <füzér> (message)
aaaa címtől kezdve elhelyezi a tárban a megadott karaktersorozatot.P aaaa (print)
aaaa címtől kijelzi a következő 64 byte tartalmát ASCII formában.R (registers)
Megjeleníti a regiszterek és jelzőbitek tartalmát. A paranccsal értékük megváltoztatható.S bbbb,llll,tp,sp (substitute)
Felcseréli az összes tp értékű byte-ot sp értékűre a bbbb címtől llll-g tartó tárblokkban.T aaaa (tabulate)
A P-hez hasonló, csak a tártartalmat hexadecimális formában írja ki.V bbbb,llll,nnnn (verify)
Két blokkot hasonlít össze, az egyik bbbb címtől kezdődik és llll-ig tart, a másik nnnn címnél kezdődik.Z bbbb,llll (zero)
bbbb címtől llll címig 00 tartalommal tölti fel a tárat.
Assembler (ZEUS)
Töltése: LOAD ""
Indítása: automatikus
Bejelentkezése: copyright szöveg és kurzor
Konstansok:
Műveletek: +, -, !, (logikai VAGY), & = (logikai ÉS).
Parancsok:
I x,y (index)
Automatikus sorszámozás, x kezdőértéktől, y lépésközzel.L x,y,z (list)
Listázás az x sortól y-ig úgy, hogy z soronként szünetet tart.R x,y,z (renumber)
Átsorszámoz x kezdeti értékkel, y lépésközzel, z sorszámtól kezdve.D x,y (delete)
x, y sorok között töröl a forrásszövegből.F "<füzér>" x,y,z (find)
A füzért keresi az x,y intervallumban, és a z-edik előfordulásánál leáll.N x (new)
Törli a forrásállományt, és új puffért jelöl ki az x címen.O x (overwrite)
Átírja a puffer címét.P I/O (printer)
ZX-Printer be/ki.Q (quit)
Kilépés.S x (symbol table)
A szimbólumtábla listázása; x soronként megáll.T (text)
A forrásszöveg kezdetét és végét írja ki.A x (assemble)
Az assemblert indítja, x hiba után leáll a fordítás. Alapérték: x=14.
Direktívák:
ORG
Annak a címnek a megadására szolgál, ahol a program futni fog. Több is lehet a forrásszövegben.DISP (displacement).
Címeltolás. A tárgykódú puffer ORG-tól számított kezdőcíme.ENT
Belépési címet határoz meg. A G parancs ideugrik, hogy végrehajtsa a tárgykódot.EQU
DEFB
DEFW
DEFM
Értelmezése a más assemblereknél látottal azonos.Nincs DEFS, ehelyett ORG és DISP használható.
Nincs DEFL, ami néha hasznos lenne a lokális címkéknél.
Részletesebb leírás a kazettához mellékelve található, amely az egész képernyőn szerkesztő EDITOR-t is bemutatja. Ennek működése hasonló a többi egészképes szerkesztőprogramhoz.
3.4.4. GENS3 / MONS3
A HISOFT cég monitor/assembler programja. Ismeretes a GENS3M/ MONS3M nevű változat is, amelyet a Microdrive kezelésére terveztek. Aki ismeri a HISOFT PASCAL és C fordítót, annak feltűnik, hogy azok szerkesztő parancsai teljesen megegyeznek a GENS3 parancsaival.
MONS3 (monitor)
Töltése: LOAD "" CODE, aaaa
Az aaaa cím (MSTART) a RAMTOP fölött bárhol elhelyezkedhet.
Indítása: RAND USR aaaa
RAND USR aaaa+29 (újraindításnál).
Bejelentkezése: Regiszterértékek kiírása és a ">" parancsváró karakter.
Parancsok:
CS/1 (EDIT)
Visszatérés a BASIC rendszerbe.CS/2 (CAPS LOCK)
C/L kurzor váltó.SS/3 (#)
Hexadecimális-decimális átváltó; alapértelmezés hexadecimális.SS/4 ($)
A tármutatótól (MP = memory pointer) kezdődően assembly lista készítése. Tetszőleges billentyű lenyomására folytatja a listát. Visszatérés: SS/4.ENTER
MP=MP+1nn ENTER
(MP) = nn tártartalom-módosításCS/7 ()
MP=MP-1CS/5 ()
MP=MP-8CS/8 ()
P=MP+8SS/N (,)
MP=(SP) segítségével gyorsan megtekinthető a visszatérési cím környéke.SS/M (.)
A regisztermutatót pörgeti (SP és IR regisztereket átugorja, ezeket ui. nem lehet módosítani).nnnn SS/M
Az aktuális regiszterbe az nnnn értéket írja.M nnnn
MP=nnnnG nn,nn,nn,...
Hexadecimális alakban (nn) megadott karakterekből álló sorozatot keres, MP-től kezdve.N
Új címtől kezdve ismétli a G parancsot.H
Decimálisból hexadecimálisba konvertál.I
(first? last? to?)
Blokkot mozgat a tárban, first = kezdőcím, last = végcím, to = új kezdőcím,J nnnn
Tárgykód végrehajtása, nnnn címtől. Kilépés ""W
Töréspont elhelyezése az MP által mutatott címre.SS/Z (:)
Lépésenkénti programvégrehajtás (EI utasításra jutva a MONS3 összeomlik).SS/K ( + )
Programvégrehajtás PC értékétől.SS/T (>)
Az MP-nél kezdődő utasítás után töréspontot helyez el, majd SS/K parancsot hajt végre. Hasznos CALL vagy RST utasítás esetén, ha a hívott rutin követése felesleges.L
Tárkiíratás MP-től kezdve. Ha a képernyő betelt, akkor CS/5 ()-tel kiléphetünk, vagy tetszőleges billentyű lenyomásával folytathatjuk a megjelenítést.SS/P (")
Hatása azonos az L parancséval, csak a lista a nyomtatón készül.O
Az MP által mutatott byte-nak megfelelő relatív címre viszi MP-t.P
(first? last? with?)
Adott értékkel (with) tölti fel a first kezdőcím és a last végcím közötti tárterületet.Q
A háttérregisztereket jeleníti meg.T
(first? last?)
A first.. .last tárblokkról disassembly listát készít a képernyőre, ill. a nyomtatóra.U
MP-t visszaviszi a legutolsó 0-val definiált relatív ugrásból.V
Visszatérés X-ből.Y
ASCII karakterek beírása
GENS3 (assembler)
Töltése: LOAD "" CODE, aaaa
Az aaaa (GSTART) cím értékét a RAMTOP felett, a tár alsó részén érdemes kijelölni, hogy a szöveg és a tárgykód számára elegendő hely maradjon.
Indítása: RANDOMIZE USR aaaa
RANDOMIZE USR aaaa+ 56 (hideg újraindítás)
RANDOMIZE USR aaaa+ 61 (meleg újraindítás)
Bejelentkezése: Buffer size?:
A T parancsban és a * F assembler utasításban használt puffer méretét kérdezi 256 byte egységekben. Alapértelmezés szerinti mérete 4.
Számok:
Műveletek
(Nincs prioritáskezelés, a műveletek sorrendben hajtódnak végre!)
Direktívák:
ORG nnnn
A fordítás erre a címre szerveződik.EQU,
DEFB,
DEFW,
DEFS, ill.
DEFM
A szokásos értelmezésű.ENT <(kifejezés)>
A kifejezés értéke lesz a tárgykód belépési címe az R parancs kiadásakor. (Praktikus alkalmazása: ENT $ hatására a rutin futása a következő sortól indul.)IF <feltétel>: <utasítás1> ELSE <utasítás2> END
Feltételes fordítás. Hasonló a BASIC IF-THEN-ELSE szerkezethez. Ha a feltétel igaz, <utasítás1>-et, ha hamis, <utasítás2>-t fordítja le az assembler. (Megjegyzés: az ELSE elmaradhat, de az END kötelező!)
Utasítások:
*E
3 üres sort szúr be a fordítási listába.*H <füzér>
A füzért kiírja a lap tetejére, majd 3 soremelést végez.*L+-
Listázásvezérlés (+ = igen, - = nem).*D+-
A címmegadás számrendszerének beállítása (+ = decimális, - = hexadecimális).*C+-
- = rövid, vagy + = teljes assembly listát ad.
A rövid lista formátuma: címke, műveleti kód, operandus, megjegyzés.
A bővített lista alakja: cím, tartalom, címke, műveleti kód, operandus, megjegyzés.*F <füzér>
A füzért (amelyet előzőleg a GENS3/MONS3 T paranccsal vittünk szalagra) megkeresi és blokkonként lefordítja. A blokkméretet a bejelentkezéskor a Buffer size? kérdésre adott válasz határozza meg. A szöveg végét jelző TEXT-END értékét a GENS3 a GSTART + 54/55 címen tárolja, ezt MONS3-ban kiadott T parancs esetén POKE-kal külön be kell írnunk. A *F utasítás használata hosszú programok esetén elengedhetetlen.A n
Fordítás, n értelmezése egy bináris 6-bites érték, ahol az egyes bitek jelentése (ha az adott sorszámú bit értéke 1):
- 0 - szimbólumtábla készül,
- 1 - nem lesz tárgykód,
- 2 - nem lesz lista a fordítás után,
- 3 - a lista a ZX-Printeren készül,
- 4 - a tárgykód a szimbólumtábla végére kerül,
- 5 - semmiféle ellenőrzést nem végez (a tárgykód felülírhatja a GENS3-at).
Hibakódok:
1: | Hibás (az assembler által nem felismert) szövegsor. |
2: | Hibás (vagy nem létező) mnemonik. |
3: | Hibás a formátum (pl. hiányzik a szóköz stb.). |
4: | Többször definiált szimbólum. |
5: | Tiltott karakter. |
6: | Hibás vagy tiltott operandus. |
7: | Illegális szimbólum. |
8: | Hibás regiszterhivatkozás (pl. LD A,BC). |
9: | Több regisztert ismert fel a fordító (általában 6-os hibánál fordul elő). |
10: | Az operandus nem fér el 1 byte-ban (pl. LD C, 358). |
11: | JP (ii+n) tiltott. |
12: | Hibás direktíva. |
13: | Nem definiált szimbólum. |
14: | 0-val osztás. |
15: | Aritmetikai túlcsordulás. |
BAD ORG: | Az ORG felülírná a GENS3-at. (A programot akkor előbb szalagra kell menteni, majd az A n utasítás 4. bitjét 0-ra kell állítani.) |
BAD MEMORY: | A tár betelt. |
OUT OF TABLE SPACE: | Kicsi a szimbólumtábla. |
3.4.5. EDITOR-SPECTREMAC/SPECTREMON
Ez a programcsomag 3 fő részből
EDITOR
Utasítások:
A (again find)
Továbbkeresés az adott mintának megfelelően.B (Bottom of lile)
Állomány végére pozícionál.C (change mode)
Szövegfelírás. Minden más parancs hatástalan, kivéve az A parancsot, amelyet ekkor SS/A-val adhatunk ki.D (delete line)
Sortörlés. (D n: n sorra, D *: az állomány végéig, D -: a sor elején levő - jelig.)G (get file)
Egy állományt olvas be a szalagról, vagy ellenőriz a szalagon.H (help)
A kezelő tájékoztatására kiírja a parancskészletet. Kilépés: CS1 (EDIT).I (insert).
A szövegbe beszúrást végez. A szöveg többi része hátrább tolódik.J (Join) Hozzámásol a szalagról az adott állományhoz.
K (copy)
Blokkmásolás.
Kezdetét: -**,
végét: - jelenti.
E vezérlőkaraktereknek a 0. képernyőoszlopban kell lenniük.L (locate string)
Szöveget keres.
A parancs kiadása után megkérdezi, hogy hová illessze a mintát: A = tetszőleges helyre, S = sor elejére.
Ezután megkérdezi a mintát. A minta belsejében *-ot megadva az adott pozíción tetszőleges karaktert elfogad, míg a /?-lel jelölt pozíción csak számot fogad el.O aaaa (set workspace)
A munkaterület címét az aaaa értékre állítja be. (A munkaterület általában szövegállomány után van.) Eredeti helyére *-gal lehet visszaállítani.P (print file)
Állománykiírás az ZX-Printerre, - jelig vagy végig, a kurzortól kezdve.Q (quit)
Kilépés, visszatérés a hívó programhoz (BASIC-be).R <eredeti szöveg> <új szöveg> <cserék száma> (replace string)
Szövegrész kicserélése az adott paraméterek szerint.S
Puffer vége, oszlopszámváltás.T (top of file)
Az állomány elejére ugrik.W (write file)
Az állományt kiküldi a magnetofonra.Z (assemble file)
Az assembleropciók beállítása. A parancs kiadása után be lehet gépelni a kívánt opciósort, amelyet minden esetben a K opcióval kell lezárni. Az opciók:
- E - fordításhiba esetén a kurzor a hibára mutat,
- L - lista készül,
- S - szimbólumtábla készül,
- T - makró-szimbólumtábla készül,
- P - kiírás ZX-Printerre,
- M - fordítás után elhelyezés,
- K - új könyvtár készül.
SS/A (STOP)
"A" parancs kiadása C, ill. I parancsok után.CS/1 (EDIT)
Kilépés az adott parancsból.CS/0 (DELETE)
Karaktertörlés.ENTER
Új sor.CS/5 ()
A kurzor balra léptetése.CS/8 ()
A kurzor jobbra léptetése.CS/6 ()
A kurzor egy sorral lejjebb léptetése.CS/7 ()
A kurzor egy sorral feljebb léptetése.CS/SPACE
Sortörlés a kurzortól a következő ENTER-ig.SS/SPACE
Tabulálás.SS/ENTER
Tabulálás törlése.CS/ENTER
Ugrás a sor elejére.
SPECTREMAC (makró assembler)
Kényelmes, ha a sűrűn szükséges utasítássorozatokat a programszövegben egyetlen programsor leírásával helyettesíthetjük. Ezeket a magasabb szintű, több assembly sort összefoglaló utasításokat makróknak nevezzük. A makrók jelentését természetesen felhasználásuk előtt definiálni kell. Erre szolgál a DEFMAC utasítás, amelyben megadjuk a makró "nevét", majd a jelentését.
A makróban természetesen definiálhatnak állandókat, paramétereket és változókat. Az állandók azok a szintaktikai egységek, amelyek értéke a programvégrehajtás során nem változik. A makrókban szereplő paraméterek a makró hívásakor kapnak - a hívó programtól - konkrét értéket. A változók a makrónak mint rutinnak a saját változói. Az állandókat a DEFCONST, a paramétereket a DEFSET, a változókat pedig a DEFVAR paranccsal kell megadni.
A paramétereket a makrónévben *-gal jelöljük, a definíció törzsében #0.#9-cel hivatkozhatunk rájuk. A szám az adott paraméter névbeli sorszáma.
A paraméterdefinícióban (DEFSET) a lehetséges paraméterértékek halmazát soroljuk fel. A makró törzsében a halmaz egyes elemeit is elérhetjük. Ha pl. adott a
DEFSET R=(B,C,D,E,H,L,A)
definíció, akkor
R[0] = B,
R[5] = L.
A SPECTREMAC az állandókra, paraméterekre és változókra a következő üzeneteket engedélyezi:
prioritás művelet értelmezés 5 !negáció (1-es komplemens) 4 x«yx balra léptetése y bittel 4 x»yx jobbra léptetése y bittel 4 x*yszorzás 4 x/yosztás 4 x%yx mod y 3 +összeadás 3 -kivonás 2 &logikai ÉS 2 |logikai VAGY 2 "logikai kizáró VAGY 1 <, >, <=,
>=, =relációk
A makrókban feltételes és ciklikus fordítási szerkezeteket is előírhatunk. Ezek:
A SPECTREMAC a makrók kifejezéséhez saját belső rendszerváltozókat használ. Ezek a következők:
1. ZX-Printer opció
3. LIST opciói
7. ERR/STOP opció
8. T parancs opció
9. M parancs opció
10. Töltés/fordítás opció
12-15. Felhasználói opciók
(A hiányzó biteket a rendszer magának tartja fenn.)
Hogy a SPECTREMAC használatát megkönnyítsük, a következőkben tömören összefoglaljuk a program szintakszisát:
DEFCONST (<paraméterlista>). {konstansdefiníció}
<paraméterlista> ::= <paraméter>,<paraméterlista>
DEFSET <név> = (x TO y). {intervallumdefiníció}
<konstanslista> ::= <konstans>, <konstanslista>
DEFSET <név> = (x TO y). {intervallumdefiníció}
DEFVAR (<változólista>). {változódefiníció}
<változólista> := <változó>, <változólista>
DEFMAC (<név-paraméterlista>) END. {makródefiníció}
<név-paraméterlista> = <név> | <hivatkozás> |, <paraméterlista>
Előre definiált makrók:
Hívása: | DB <kifejezéslista> |
<kifejezéslista> | ::= <kifejezés>, <kifejezéslista> |
<kifejezés> | ::= <változó> | <konstans> | <szám> | "<karaktersor>"> <operátor> | <kifejezés> |
<változó> | ::= <név> |
<konstans> | ::= <név> |
<szám> | ::= <dec> | <hex> | <okt>| <bin> |
<hex> | ::= <0...D>H |
<dec> | ::= <0...9> |
<bin> | ::= <0...1>B |
<okt> | ::= <0...7>O |
<karaktersor> | ::= <karakter> | <karaktersor> |
<operátor> | ::= + | - | ! | « | » | * | / | % | + | - | & | // | = | > | >= | <= | < |
A SPECTREMAC használatát néhány hasznos makró definíciójával szemléltetjük:
DEFSET nn (0 TO 65535) ; a paraméterek értéktartományának megadása DEFSET n = (0 TO 256) DEFMAC ("FTECH *",nn)
DB 2AH
DB # 0 -256* # 0 / 256
DB # 0 / 256
DB 0,0,0
END.; byte-behozás DEFMAC ("STORE *",nn)
DB 22H
DB # 0 - 256 * # 0 / 256
DB # 0 / 256
DB 0,0,0
END.; tárolás DEFMAC ("ADD *",nn)
DB 1EH
DB # 0 - 256 * # 0 /256
DB 16H
DB # 0 / 256
DB EDH
DB 5AH
END.; összeadás DEFMAC ("SUB *",nn)
DB 1EH
DB # 0 % 256
DB 16H
DB # 0 / 256
DB ED
DB 52H
END.; kivonás DEFMAC ("LOAD *",nn)
DB 21H
DB # 0 % 256
DB # 0 / 256
DB 0,0,0
END.; betöltés DEFMAC ("SKIP *",n)
DB C3H
DB (# 0 + $0) % 256
DB (#0 + $0) / 256
DB 0,0,0
END.; ugrás
SPECTREMON
Töltése: LOAD ""
Indítása: automatikusan indul
Tárigénye: 0F000H-0FFFFH
07000H-07FFFH
Bejelentkezése: regisztertartalom-, tártartalom- és egyéb (előlap = front panel) információk
Parancsok:
B bb, aaaa, cccc
Töréspont beállítása;
bb = sorszám, aaaa = cím, cccc = aktivizálódási sorszám.C uu, ssss, llll
Tárfeltöltés;
uu = feltöltési érték, ssss = kezdőcím, llll = hossz.D ssss, eeee, llll
Disassembly parancs;
ssss = kezdőcím, eeee = végcím, llll = az egyszerre kiírt sorok számaE ssss
A futtatás kezdőcímének megadása.
(Ha hiányzik, akkor a végrehajtás a PC értékéből indul.)F
Előlapinformáció-megjelenítés be/ki.I ssss, dddd, llll
Tárblokk másolása;
ssss = kezdőcím, dddd = célcím, llll = hossz
Megismerkedve a Z80 utasításkészletével, néhány mintaprogram és ötlet után vizsgáljuk meg a Spectrum ROM-ban tárolt operációs rendszerét, a BASIC értelmező (interpreter) működését.
6.1. A ROM felépítése
A ROM elején a következő rutinok, ill. mutatók helyezkednek el:
0000 - rendszerindítás,
0008 - hibakezelő rutin,
0010 - karakterkivitel,
0018 - a BASIC értelmező aktuális karaktere,
0020 - a BASIC értelmező következő karaktere,
0028 - kalkulátorrutin,
0030 - a munkaterületet kijelölő rutin,
0038 - maszkolható megszakítás rutinja.
A további ROM terület 8 főbb részre bontható:
0095...028D - karakter-, billentyűzet-, rövidítéstáblázat, 028E...11B6 - perifériakezelő rutinok, 11B7...1A47 - maga az operációs rendszer, 1A48...1CED - a BASIC értelmező, 1CEE...24FA - utasításrutinok, 24FB...2D4E - kifejezés-kiértékelő programok, 2D4F...3860 - kalkulátor-, aritmetikai rutinok, 3D00...3FFF - eredeti karakterkészlet.
A ROM felépítésénél a programozók arra törekedtek, hogy a rendelkezésre álló helyet a legjobban kihasználják. így ez néhol a program futásának lassulásához vezetett.
A ROM program magja az operációs rendszer, amelynek részei a következők:
Ezek a részek többnyire csak vezérlési szempontból érdekesek, a felhasználó programjai nem kapcsolódnak az ilyen jellegű feladatokhoz. Fontos lehet viszont a felhasználó számára a különböző perifériakezelő rutinok működésének az ismerete.
6.2. Perifériakezelés
Alaphelyzetben az operációs rendszer hét streamen (logikai csatornán) keresztül négy fizikai perifériát kezelhet. A csatornák közül háromhoz a BASIC rendszer nem fér hozzá.
A programozó természetesen assemblyben módosíthatja a fizikai perifériakonfigurációt, ill. a stream-felosztást. Ezekkel a módosításokkal azonban óvatosan kell bánni, nehogy az operációs rendszer elveszítse a perifériák kezelését, mert így végtelen ciklus, tártörlés, lefagyás lehet a következmény.
A perifériakezelő rutinok:
cím Be: KEY INPUT (bevitel billentyűzetről) 10A8 Ki: PRINTOUT (kivitel képernyőre) 09F4 PRINTOUT (kivitel nyomtatóra) 09F4 ADD CHAR (kivitel a munkaterületre) 0F81
A PRINTOUT rutin egyszerre kezeli a ZX-Printert, ill. a képernyő alsó és felső részét.
ZX-Printer esetén: SET 1,(FLAGS) A képernyő felső része: RES 0,(TV-FLAG) A képernyő alsó része: SET 0,(TV-FLAG)
A rutinok a hét streamre a következőképpen vannak kiosztva:
Be Ki -3 K KEY INPUT PRINTOUT -2 S - PRINTOUT -1 R - ADD CHAR 0 K KEY INPUT PRINTOUT 1 K KEY INPUT PRINTOUT 2 S - PRINTOUT 3 P - PRINTOUT
Egy csatorna megnyitásához a következőket kell végrehajtani. Minden csatornához 5 byte-os leíró blokk tartozik. Ebből egy byte a csatorna kódja (lehetőleg alfabetikus karakter), majd két-két byte a ki-, ill. a beviteli rutin címe. A CHANS rendszerváltozó báziscímének és az 5 byte-os leíró címének a különbségét bejegyezzük a stream címére. Példaként tekintsük a következő programot!
BASELD HL,(PROG)
DEC HL
LD BC,0005
CALL 1655;MAKE ROOM
INC HL
LD DE,BASE
PUSH HL
LDIR
POP HL
LD DE,(CHANS)
AND A
SBC HL,DE
LD(5034),HL
RET
DEFW OUT
DEFW INP
DEFM "A"
; Ez a CHANS vége.
; 5 byte
; Helyet csinál
; Az új hely első byte-ja
; Átmásolja az
; információkat
; Meghatározza
; az eltolást
; beírja a 15. stream-be
Ily módon bármilyen be-/kiviteli struktúrát megvalósíthatunk:
INP
SEND
LOOPCLLD HL,BUFF
EX DE,HL
LD HL,(COUNT)
INC (HL)
JR Z,SEND
ADD HL,DE
LD (HL),A
RET
PUSH DE
XOR (HL)
POP IX
PUSH IX
LD DE,0100
CALL SAVE BYTE-S
POP HL
LD B,0
XOR A
PUSH HL
POP DE
LD (HL),A
INC HL
DJNZ LOOPCL
POP AF
LD (DE),A
RET; HL = puffercím
; A számlálót
; növeli
; "TELE VAN" ugrás
; küldésre
; Egyébként betölti
; a karaktert a pufferba
; Törli a számlálót
; Szalagra ír 256 byte-ot
; Törli a puffert
; 0. elemnek írja a karaktert
Hogy több periféria ne keveredjen össze a perifériaváltásnál, írás-olvasásnál aktuálissá kell tenni a csatornát, mert a Spectrum egyszerre csak egy csatornát tud kezelni.
CALL CHAN OPEN (1601)
Ily módon a CURCHL rendszerváltozó a használt csatornára mutat, és
CALL OUT CODE
CALL INPUT AD(15F2) ill.
(15E6)
meghívja a perifériakezelő rutinokat.
Lezáráshoz a megfelelő stream mutatóját nullázni kell, így a rendszer nem használja bevitelre. Célszerű nem BASIC-ből lezárni a csatornákat, mert a CLOSE# parancs hibás a ROM-ban. A lezárás alapjául szolgáló táblázat ugyanis a végén nem tartalmazza a 00 végjelzőt. Ehelyett a következőt írhatjuk:
LD A,STREAM
CALL CLOSE 16EB; a logikai csatornaszám,
; amit le akarunk zárni
Ez a program az említett hibát kivédi, de nem vizsgálja, hogy nyitva volt-e a kérdéses csatorna.
6.3. Rutinok beillesztése a BASIC-be
Ha különleges BASIC utasításokat akarunk létrehozni, meg kell változtatni az interpreter működését. Ezt assembler rutinok beillesztésével tehetjük meg.
Példaképpen nézzük meg, hogyan választhatjuk meg a
POKE <cím>, <karakter>, ill. a
POKE <cím>, <2-byte-os szám>
utasítást!
A feladat megoldásához több lépésben juthatunk el. Először a hibarutin (ERR) visszatérési címét kell megváltoztatni:
LD HL,(ERR SP)
XOR A
LD (HL),A
INC HL
OR F0
LD (HL),A
RET
Utána össze kell állítani a megvalósítani kívánt utasítás szintaxisát. Ebben segítséget nyújthatnak azok az ún. szintaktikai osztályok (class), amelyeket az operációs rendszer használ a programsorok értelmezésére. Mindegyik osztályhoz egy-egy rutin tartozik, amelyek szintaktikai elemző funkciók mellett az adott egység végrehajtásáról is gondoskodnak. A következőkben felsoroljuk az osztályok számát, a megfelelő rutinok kezdőcímét, ill. az általuk kezelt szintaktikus egységeket.
00 1C10 nincs további paraméter 01 1C1F csak bal oldali operandus lehet (bármilyen változó) 02 1C4E bármilyen kifejezés lehet 03 1C0D numerikus kifejezés, ha nincs, akkor 0 az alapértelmezés 04 1C6C egyjegyű szám 05 1C11 listaelemek 06 1C82 numerikus kifejezés 07 1C96 színlistaelemek 08 1C7A két numerikus kifejezés 09 1CBE színlistaelemek és a 08 osztály 0A 1C8C karakteres kifejezés 0B 1CDB kazettás magnetofon rutinokra adja a vezérlést és az állománynevet a veremben tárolja.
Példánkban a gyorsaság kedvéért nem magukkal az osztályokkal, hanem közvetlenül azok alrutinjaival dolgozunk. Az általunk használt alrutinok:
Alrutinnév funkció STACK A A verem STACK BC BC verem STK STORE A verem
B
C
DEFP TO A verem A FP TO BC verem BC STK FETCH
verem A
B
C
DESCANNING kifejezés kiértékelése és értékének veremre helyezése PRINT FP lebegőpontos szám kiírása
Ezek a rutinok a fejezet végén közölt ROM-rutingyűjteményben megtalálhatók.
Az így összeállított programsoron a
GET-CHAR
NEXT-CHAR
rutinokkal lépdelhetünk végig.
Ha a szintaxis helyes, a sor a helyére kerül a listában.
Utolsó lépésként a megvalósított új utasításból való megfelelő visszatérésről kell gondoskodni. A verem üres, ezért nem lehet egyszerűen RET-tel visszatérni. így helyes végrehajtáskor az STMT NEXT (következő utasítás, 1BF4), hiba esetén a 1303H címre adódik vissza a vezérlés. Ha voltak füzérműveletek (darabolás, ill. összefűzés), a munkaterületen a füzér paraméterei vannak. A változók rendelkezésre állnak (nem törlődnek).
A megadott POKE utasítások megvalósítása:
ORG F000
RST 18 ; get char
CP "*"
JRNZ ERR1
DEC HL
LD A,(HL)
CP "POKE"
JRNZ ERR1
RST 20; next char
CALL SCANNING (24FB)
BIT 6,(FLAGS)
JRNZ ERR1
RST 20; next char
CP ","
JRNZ ERR1
CALL SCANNING
BIT 6,(FLAGS)
JRNZ,NUMERIC
CALL STK FETCH
BIT7,(FLAGS)
JRNZ PEND
PUSH BC
PUSH DE
CALL FP TO BC
JR C,ERR1
LD H,B
LD L,C
POP DE
POP BC
EX DE,HL
LDIR
JR PENDNUMERIC BIT 7,(FLAGS)
JRNZ PEND
CALL FP TO BC
JR C,ERR1
PUSH BC
CALL FP TO BC
JR C,ERR1
POP HL
LD (HL),C
INC HL
LD (HL),BPEND LD HL,F000
EX (SP),HL
JP STMT NEXT (1BF4)ERR1 LD HL,1303
EX (SP),HL
LD HL,ERR NR
LD A,0C
LD (HL),A
RET
A következő feladatcsoport, amellyel foglalkozunk, hogy hogyan lehet egy nagyobb gépi kódú programot a Spectrum operációs rendszerére támaszkodva megírni. Az itt név szerint jelzett rutinokat a fejezet végén részletesen ismertetjük.
Ahhoz, hogy a program helyesen kezdődjön, kezdeti értékeket kell beállítani.
Például képernyőtörlés, keretszín (BORDeR), állandó papírszín, tintaszín beállítása és az S csatorna megnyitása:
LD A,DE
LD (ATTRP),A
LD A,17
LD (BORDC),A
LD A,01
OUT (FE),A
CD B,18
CALL CL LINE
LD A,02
CALL CHAN OP
RET
Ezt követően az esetleges használati utasítást írhatjuk a képernyőre a PRSTRING rutin segítségével. A szövegben szerkesztő kódokat is elhelyezhetünk. Ezután kezdődik a tulajdonképpeni feladatmegoldás.
Lássunk végül néhány, a programírást megkönnyítő ötletet.
Billentyűzet figyelése:
LD A,(LAST K) vagy ha a megszakítás le van tiltva:
CALL KEY SCAN
CALL K CODE
LD A,(LAST K)Ha adott területre karaktersorozatot akarunk tárolni:
ORG 0F85
LD HL,(K CUR)
CALL ONE SPACE
LD (DE),A
INC HL
LD (K CUR),DE
RET
Ez a rutin a ROM-ban van (címe 0F81), s alapértelmezés szerint az E LINE-ba ír. A K CUR rendszerváltozó kezdeti értékét beállítva azonban bárhová írhatunk a tárba. Ügyeljünk, nehogy felülírjuk a BASIC rendszert!
Osztási hiba:
Az osztás 34. bitje elvész, és 0.5 hol 80 00 00 00 00, hol 7F 7F FF FF FF alakban tárolódik.
-65536 tárolási hiba:
vagy rövid, vagy lebegőpontos alakban tárolódik, így a PRINT -65536 eredménye -1 lesz.
Kurzor jobbra hiba:
Nem tárolódik az új PRINT pozíció a PO STORE rutinban.
SCROLL üzenet utáni hiba:
Ha az üzenet után megnyomjuk a CS-t és az SS-t, megjelenik az E LINE tartalma.
Kurzorhiba:
Ha a szerkeszteni kívánt sor az aktuális (belső sormutató által kijelölt) sor után áll, akkor a kurzor a szerkesztett sorba is bekerül.
A kurzort nem lehet a 0. sor végére vinni, rossz a képernyő határát vizsgáló rutin (CHR$ 8 hiba).
SCREEN$ rutin hibája:
Ha a SCREEN$ egyetlen kifejezésben kétszer értékelődik ki, akkor a veremben kétszer fog szerepelni a karakter.
SCAN STR$ rutinhiba:
A rutint a 1>|x| tartományban használva a verem előtöltődik egy 0 konstanssal és programhiba miatt nem íródik felül.
CLOSE hiba:
Mint említettük, a CLOSE STREAM táblázat végén nincs 00 lezáró byte. Ezért a megnyitatlan csatornák lezárása bizonytalan.
0...3 logikai csatornaszám lezárása is hibát okozhat, ha a perifériakezelő rutint nem módosítottuk,
4...15 logikai RST0 újraindítást okoz.
Az NMI rutin hibájának javítása:
Az eredeti rutint úgy javíthatjuk, hogy a 006D címre dec. 32 (JR NZ) helyett 40-et (JR Z) írunk. Ha az NMI ADD tartalma nem 0, akkor az ott talált címre ugrik.
Ehelyett lehet közvetlenül a ROM-ba írni a BASIC visszaállítást az NMI ADD tartalmától függetlenül:
|
marad 12 byte |
Hibái: fölülírja a ROM egy a ZX-81-ből maradt, nem használt rutinját, nem állítja vissza a K kurzort, nem ellenőrzi a RAM szükséges minimális méretét.
A meleg reset rutin rendszerint nem lehet univerzális (ilyen kis helyen), de a hibákért bőségesen kárpótolja a fejlesztőt.
Hardver: a Z80 17-es (NMI) és 29-es (GND) lábait összekötjük kapcsolóval ellátott vezetékkel.
A ROM helyett használt 27128-as EPROM 27-es lábát nem kötjük be, hanem összeforrasztjuk a 28-as lábával. A 20-as lábat negálva vezetjük az ULA 44-es lábához.
6.5. A főbb ROM rutinok áttekintése
CH ADD+1
A szintaktikai vizsgálat során a vizsgálandó karaktert az A regiszterbe tölti. Cím: 0074 Be: - Ki A (A vizsgált elem ASCII kódja) Reg.: A, H, L
KEYBOARD
A billentyűzet figyelését, ill. kódolását végzi. Cím: 02BF Be: - Ki LAST K, A (A lenyomott billentyű bővített Sinclair kódja.) Reg.: A, B, C, D, E, H, L
BEEPER
Hanggeneráló szubrutin. Cím: 03B5 Be: DE - A hang frekvenciájának és időtartamának szorzata.
HL - Periódusok száma.Ki - Reg.: A, B, C, D, E, H, L, IX
SA BYTES
Tártartalom szalagra mentése. Cím: 04D0 Be: DE - Hossz (byte).
HL - Bevezető jel hossza.
IX - Kezdőcím.
A - A blokk kódja:
00: programfej,
01: tömbfej (numerikus),
02: tömbfej (karakteres),
03: CODE fej,
FF: adatblokkKi - Reg.: A, B, C, D, E, H, L, IX, A', F'
LD BYTES (VERIFY)
Tárba töltés a szalagról (összehasonlítás). Cím: 0562 Be: DE - Hossz.
IX - Kezdőcím.
A - A blokk kódja.
C jelzőbit = 1 töltés, ill. 0 ellenőrzés esetén.Ki - Reg.: A, B, C, D, E, H, L, IX, A', F'
MERGE
Két programrészt sorszám szerint rendez, ill. be is tölti a tárba. Cím: 08B6 - töltés, ill.
08D2 - csak rendezés esetén.Be: HL - Az új program címe (csak rendezés esetén).
DE - A régi program címe (csak rendezés esetén).Ki - Reg.: A, B, C, D, E, H, L, A', F'
PO STORE
Az aktuális nyomtatási pozíciót tárolja a rendszerváltozókban. Cím: 0ADC Be: B - Sorszám, a jobb alsó sarokhoz viszonyítva.
C - Oszlopszám.
HL - A képelem címe.Ki - Reg.: B, C, H, L
PO FETCH
A pozícióváltozók BC, ill. HL regiszterpárba töltése. Cím: 0B03 Be: - Ki B - Sorszám.
C - Oszlopszám.
HL - A képelem címe.Reg.: B, C, H, L
PR ALL
8x8-as karakter kinyomtatása a képernyőre. Cím: 0B7F Be: BC - Sor, oszlopszám.
DE - A karakter kezdőcíme.
HL - A karakter címe a képernyőtárban.Ki - Reg.: A, B, C, D, E, H, L, A', F'
CLS
Képernyőtörlés. Cím: 0D6B Be: - Ki - Reg.: A, B, C, D, E, H, L
CLS LOWER
A képernyő alsó részét törli. Cím: 0D6E Be: - Ki - Reg.: A, B, C, D, E, H, L
SCROLL
A képernyő felfelé görgetése. Cím: 0E00 Be: B - Sorfeltolások száma. Ki - Reg.: A, B, C, D, E, H, L
CL LINES
A képernyő alsó sorait törli. Cím: 0E44 Be: B - Sorszám. Ki - Reg.: A, B, C, D, E, H, L
COPY BUFF
A nyomtatópuffer tartalmát küldi ki a nyomtatónak. Cím: 0ECD Be: - Ki - Reg.: A, B, C, D, E, H, L
CLEAR BUFF
Törli a nyomtatópuffert. Cím: 0EDF Be: - Ki - Reg.: A, B, H, L
INPUT AD
Beviteli rutin hívása. Cím: 15E6 Be: CURCHL - A csatorna száma. Ki - Reg.: A rutintól függ.
OUT CODE
Kiviteli kiszolgáló rutin hívása. Cím: 15F2 Be: CURCHL - A csatorna száma. Ki - Reg.: A rutintól függ.
CHAN OPEN
Megnyitha az éppen használni kívánt csatornát. Cím: 1601 Be: A - A csatorna száma. Ki - Reg.: A, D, E, H, L
MAKE ROOM
Területet hoz létre a BASIC rendszerben. (Csak a RAMTOP alatt lehet használni.) Cím: 1655 Be: BC - Hossz.
HL - Kezdőcím.Ki HL+1 - Kezdőcím.
DE - Végcím.Reg.: A, B, C, D, E, H, L
LINE ADDR
Egy BASIC sor címét keresi meg. Cím: 196E Be: BC - A sorszám. Ki HL - A sor címe. Reg.: A, B, C, D, E, H, L
RECLAIM
A használt terület felszabadítása. Cím: 19E8 Be: BC - Hossz.
HL - Kezdőcím.Ki - Reg.: A, B, C, D, E, H, L
EXPT INUM
Numerikus kifejezés kiértékelése.
A kiértékelni kívánt kifejezés címét CH ADD-ben kell megadni.Cím: 1C82 Be: CH ADD - A kifejezés első karaktere Ki A kalkulátorverem utolsó eleme; A kifejezés értéke. Reg.: A használt függvényektől, ill. az operandusoktól függ.
EXPT EXP
Füzérkifejezés kiértékelése. Cím: 1C8C Be: CH ADD - A kifejezés első karaktere Ki A füzér hossza, kezdete a kalkulátorban. Reg.: A kifejezéstől függ.
FREE MEM
A szabad tárhely nagyságát adja.
Vigyázat! Hívása kizárólag: PRINT 65535-USR 7962Cím: 1F1A Be: - Ki - Reg.: B, C, D, E, H, L
STACK A
8 bites egész elhelyezése a verembe. Cím: 2D28 Be: A - Az elhelyezni kívánt egész. Ki -
STACK BC
16 bites egész elhelyezése a verembe. Cím: 2D2B Be: BC - Az elhelyezni kívánt egész. Ki -
IN TO FP
Egész elhelyezése a verembe (lehet nagyobb is, mint 65535). Cím: 2D38 Be: CH ADD - Az első számjegyre mutat. Ki -
INT FETCH
16 bites egészt tölt a veremből a DE regiszterpárba. Cím: 2D7F Be: HL - A verem teteje. Ki DE - A szám.
C - Előjel:
00 - pozitív;
FF - negatív.Reg.: A, C, E, D, H, L
INT STORE
16 bites előjeles egészt tölt a verembe. Cím: 2D8C Be: C - Előjel.
DE - A szám.Ki - Reg.: A, C, D, E, H, L
PRINT FP
Lebegőpontos szám kinyomtatása. Cím: 2DE3 Be: A szám a verem tetején. Ki - Reg.: A, B, C, D, E, H, L, H', L'
7. Az Interface 1 és a Microdrive
7.1. A bővített rendszer elemei
A Sinclair Research Ltd felismerve, hogy a Spectrumhoz alapvetően szükséges egy gyors hozzáférésű háttértár-egység olyan illesztővel együtt, amelynek segítségével a gép egy nagyobb hálózat elemévé válhat, ill. kommunikálhat valamely nemzetközi szabványnak (RS232) megfelelő perifériákkal, kifejlesztette az 1. ábrán látható bővítőket.
1. ábra: Az Interface 1-gyel kiegészített Spectrum
Egy időben a rendszer legsebezhetőbb pontjának tűnt a Microdrive kazetták (cartridge-ok) megbízhatósága és ára. Sokan támadták és támadják szinte puritánul egyszerű műszaki megoldásait. Nos, mindezt cáfolni látszik, hogy a gyártó cég alapkiépítésben 2 Microdrive-ot épített a professzionális személyi számítógép kategóriába számító (16 bites mikroprocesszort, 128 k, 512 k-ig bővíthető RAM-ot tartalmazó) QL típusába, amelyhez a gyártás pillanatától kezdve egyre bővülő szoftverválasztékot kínál (CP/M stb.). Továbbá a nagyszámítógépes rendszereiről ismert ICL cég is megvásárolta a Microdrive licencet, és asztali számítógépébe két egységet épített be. Ugyancsak a fenti háttértároló szabadalmat alkalmazta a British Telecom új, Merlin Tonto gépéhez. A Sinclair cég közlése szerint az 1984-es évben csak az Egyesült Királyságban több mint 500 ezer Microdrive kazettát értékesített. Úgy tűnik tehát, hogy ez a fejlesztés kiállta az idő próbáját és gyorsan népszerűvé vált. A rendszer elterjedését biztosítja, hogy a kazetták árát igen jelentősen - 1985 elejétől 2 L/db-ra - csökkentették, ami kevesebb egy nem sokkal nagyobb tárterületű 5,25 inch-es hajlékony mágneslemez áránál.
A bővített rendszer illesztőegysége tehát a géphez fixen rögzíthető módon illeszkedő Interface 1 (föl lehet csavarozni a gép hátoldalára), amely a következő többletszolgáltatásokat nyújtja:
A Microdrive szerkezetét a 2. ábrán követhetjük nyomon.
2. ábra: a Microdrive szerkezete
Mindig az elsőként csatlakoztatott Microdrive hívószáma 1 és így tovább, max. 8-ig. Betöltési ideje 48 k-s programot tekintve kb. 5-8 másodperc, ugyanez kazettás magnetofonról kb. 5 perc. Összehasonlításként megemlítjük, hogy a hazánkban elterjedt és népszerű C64-es géphez csatlakoztatott 1541 típusú hajlékony mágneslemezegységnél 10-11-szer gyorsabb. A Microdrive használatához szükséges bővített utasításkészletet a későbbiekben ismertetjük.
A Microdrive kazetta szerkezetét figyelhetjük meg a 3. ábrán.
3. ábra: A Microdrive kazetta szerkezete
A kazetta "lelke" a végtelenített mágnesszalag, amely az információrögzítést szolgálja. A gyártó cég 85k-t garantál kazettánként, mint alsó határt, azonban saját gyakorlatunk alapján kijelenthetjük, hogy inkább 90-95 k tárolási területtel számolhatunk. Az eltérések abból adódnak, hogy a kazettaformattálás során a rendszer megjelöli azokat a területeket, amelyekre nem tud írni. Ezek hossza esetenként változó lehet, amit - ugyanannak a kazettának a többszöri formattálásával - kísérleti úton ellenőrizhetünk. A magnetofonkazettákhoz hasonlóan kitörhető a Microdrive kazetta írásvédő füle, ami a véletlen beletörlésektől óv meg. Ha ezt pl. cellux-szal beragasztjuk, a kazetta újra formattálhatóvá és írhatóvá válik. Egy fontos tanács: ne érintsük és ne fogdossuk a kazettából kiálló szalagot!
7.2. Csatornák, streamek
A bővített rendszer által adott lehetőségek új programozói szemléletet tételeznek fel. Ehhez pontosan ismernünk kell a komplex rendszer által használt csatornaazonosítókat:
K = billentyűzet (keyboard);
S = felső képernyő (screen);
P = nyomtató (printer);
M = Microdrive;
N = helyi hálózat (network);
T = RS232 szöveg (text);
B = RS232 bináris.
(A rendszer a kis és nagy betűket az azonosítás során egyaránt értelmezi.) Azt az utat, amelyet az adat továbbítás alatt megtesz, streamnek (logikai csatornának) nevezzük. A rendszer számára ezek megkülönböztetésére a # jel és az azt követő streamszám (ami max. 16 lehet) szolgál. Megemlítjük, hogy 4 stream csatornához rendelése foglalt: #0, #1 (kivitel az alsó képmezőre, bevitel a billentyűzetről), #2 (kivitel a felső képmezőre), # 3 (kivitel a nyomtatóra).
7.3. A bővített rendszer rendszerváltozói
A következőkben tömören áttekintjük az Interface 1 és a Microdrive kezeléséhez szükséges kiegészítő rendszerváltozókat.
23734 FLAGS3
0. bit: a kiterjesztett parancsmódban értéke 1.
1. bit: CLEAR# esetén 1.
2. bit: ERROR SP változásakor 1.
3. bit: a hálózat (Net) esetén 1.
4. bit: LOAD esetén 1.
5. bit: SAVE esetén 1.
6. bit: MERGE esetén 1.
7. bit: VERIFY esetén 1.23735 VECTOR
Ez egy kétbyte-os rendszerváltozó, amely az árnyék ROM hibarutinjának címe. Az értelmező bővítésénél használt cím. Alapértéke: 496 (01F0).23737 SBRT
Ezt a rutint az eredeti ROM az árnyék ROM-ra való lapozás során használja.
LD HL,<érték>
CALL <rutin>
LD (23738),HL
RET23747 BAUD
Ez a kétbyte-os változó az RS232 csatorna jelátviteli sebességét (baud rate) tartalmazza a következő függvény szerint: (3500000/(26*jelátviteli seb.))-2. Alapértéke 12, ami hozzávetőlegesen 19200 baud-os sebességet jelent.23749 NTSTAT
Hálózati állomásszám (1...64).37750 IOBORD
A be/kiviteli műveletek alatti keretszín. Tartalma cserélhető.23751 SER FL
Az RS232 csatorna által használt munkaterület. Az első byte-ja jelző funkciójú, a második a bemenő karakter.23753 SECTOR
A Microdrive kétbyte-os munkaterülete.23755 CHADD
A CH ADD átmeneti tárolására szolgál. A kiterjesztett rendszer szintaxisa szerint vizsgálja a programsorokat.23757 NTRESP
A helyi hálózat válaszkódja, amely - természetesen a fogadó állomásszámon - nyugtázza a következő 8 byte-tal kezdődő fej információt (header).23758 NTDEST
A célállomás azonosítója.23759 NTSRCE
A forrásállomás azonosítója.23760 NTNUMB
0...65535 közötti blokkszám.23762 NTTYPE
A hálózati fejinformáció típuskódja. 0 = adat, 1 = EOF (állomány végjel).23763 NTLEN
Az adatblokk hossza (0...255).23764 NTDCS
Az adatblokk ellenőrző összege (checksum).23765 NTHCS
A hálózat fejinformáció ellenőrző összege (NTDEST-től NTDCS-ig)23766 D STR1
Az állományazonosító első 8 byte-jának kezdete. Ez a két byte vagy a Microdrive számát (1...8), vagy a hálózati célállomány számát, vagy az átviteli sebességet adja meg.23768 S STR1
Streamszám (1...15).23769 L STR1
Csatornaazonosító: M, N, T vagy B.23770 N STR1
Az állománynév hossza.23772 T STR1
Az állománynév kezdőcíme (normálisan a munkaterületen).23774 D STR2
Az állományazonosítók második 8 byte-jának kezdete.23782 HD 00
Az állomány típusa:
0 = program
1 = numerikus tömb
2 = karaktertömb
3 = gépi kód23783 HD 0B
Adathossz (0...65535).23785 HD 0D
Az adat kezdőcíme (0...65535).23787 HD 0F
Programhossz (0...65535).23789 HD 11
Annak a sornak a száma, amelyről a program automatikusan indul. (A 32H kapcsolókód (Hook code) is használja.)23791 COPIES
A SAVE által készített felvétel száma.
7.4. A Microdrive csatorna és a Microdrive térkép
A Spectrum és a Microdrive egység közötti kommunikáció során létrejön egy csatorna, amely 595 byte hosszú, és tartalmazza az 512 byte-os átmeneti tárat is. Kezdőcíme a CHANS rendszerváltozóban van. Felépítése a következő:
0,1 | 0008H |
2, 3 | 0008H |
4 | M |
5, 6 | ROM kiviteli szubrutin címe (MWRCH). |
7, 8 | ROM beviteli szubrutin címe (MRDCH). |
9, 10 | A Microdrive csatorna hossza (!-!). |
11, 12 | CHBYTE - Az adatterület byte-számlálója (0.. .512). |
13 | CHREC - Az átmeneti tár száma (0.. .255). 0-ról indulva mutatja a pozíciót. |
14...23 | CHNAME - Az állománynevet tárolja, amely 10 karakter hosszú lehet. |
24 | CHFLAG - Írás-olvasás jelzőbitek: ha a 0. bit egy, akkor írásra nyitva, ha a 0. bit nulla, akkor olvasásra nyitva. Az 1...7. bitek kihasználatlanok. |
25 | CHDRIV - Microdrive egységszám. |
26, 27 | CHMAP Az adott egység foglaltsági térképének mutatója. |
28...39 | Ez a 12 byte-os fejblokk a munkaterület előkódja (preamble). |
40 | HDFLAG - Csak az első bit használatos (adatblokk vagy programszegmens jelölésére). |
41 | HDNUM Szektorszám (0...255). |
42, 43 | Kihasználatlan. |
44...53 | HDNAME - A használt kazetta neve. |
54 | HDCHK - A fejinformáció ellenőrző összege az előző 40 byte-ra. |
55...66 | Az adatblokk 12 byte-os előkódja. |
67 | RECFLG - Jelzőbitek. A 0. bit nulla, a 2. bit a nem PRINT típusú állományt jelöli, a többi bit kihasználatlan. |
68 | RECNUM - Az átmeneti tárban (0...255) a rekord száma. |
69, 70 | RECLEN - Az aktuális rekord adatbyte-jainak száma (0...512) |
71...80 | RECNAME - Az állománynév karaktereinek száma. |
81 | DESCHK - Az előző 40 byte ellenőrző összege. |
82...593 | CHDATA - Az 512 byte-os átmeneti tár (az adatok). |
594 | DCHK - Az előző adatterület ellenőrző összege. |
A bővített rendszer minden egyes csatlakoztatott Microdrive részére 32 byte RAM-ot biztosít. A 32 byte minden egyes bitje egy kazettaszektornak felel meg. Egy bit értéke akkor 1, ha a szektor le van tiltva, vagy ha adatot tartalmaz.
7.5. A helyi hálózat csatornája
Olyan stream megnyitásakor, amely a helyi hálózatot használja, létrejön egy 276 byte-os terület, amely egy 255 byte-os átmeneti tárat tartalmaz. Felépítése a következő:
0, 1 | 0008H |
2, 3 | 0008H |
4 | N |
5, 6 | ROM kiviteli szubrutin címe (OUT N) |
7, 8 | ROM beviteli szubrutin címe (IN N) |
9, 10 | Tartalma 276. |
A terület következő 8 byte-ja a fejinformációt tartalmazza: | |
11 | NCIRIS - Célállomás-azonosító. |
12 | NCSELF - Saját állomásazonósító. Hasonló az NSTAT-hoz, amikor egy csatorna kiépül. |
13, 14 | NCNUMB - Blokkszám (0...65535) |
15 | NCTYPE - Típuskód; 0 = adat, 1 = EOF. |
16 | NCOBL - Az adatblokk hossza (0...255) |
17 | NCDCS - Az adatblokk ellenőrző összege. |
18 | NCHCS - Az előző 7 byte ellenőrző összege. |
19 | NCCUR - Az átmeneti tár legutolsó karakterének címe. |
20 | NCIBL - Az átmeneti tárba beolvasott byte-ok száma. |
21... | NCB - 255 byte-os átmeneti tár. |
Az adatblokk fej információjának byte-jai leírják, hogy mi következik az adatblokkban. Az adatblokk egy másolata lesz a pillanatnyi átmeneti tárnak. A fejinformáció byte-jait az árnyék ROM OUTPAK szubrutinjának hívása küldi ki. A rutin végrehajtása előtt az E regiszter értéke 8, a HL regiszterpár az NCIRIS címét tartalmazza.
7.6. Az árnyék ROM
A 16 k-s ROM-hoz a bővített rendszerben hozzáadódik az Interface 8 k-s "árnyék" ROM-ja. Ez a 16 k-s ROM alsó 8k-jával (0000...1FFF) azonos címtartománnyal érhető el, így a két párhuzamos tárrész közül egy időben mindig csak az egyik hozzáférhető. A kettő közötti átváltást lapozásnak nevezzük. Tekintsük most át a lapozó technika működését! (A továbbiak-ban minden, az árnyék ROM-ra vonatkozó hivatkozást & jellel jelölünk.)
Az árnyék ROM két esetben kapcsolódik be (lapozódik). Az első, amikor a programszámláló eléri a 0008-at, vagyis az RST 8 végrehajtódik. Az eredeti ROM-ban ezt adatbyte-ok követik, amelyek az RST 8-at kiváltó hiba jellegét mutató hibaüzeneteket határoznak meg. Ha az alapgépen a kiterjesztett BASIC valamelyik utasítását (pl.: CAT stb.) adjuk ki, vagy szintaktikai hibát vétünk, a 16 k-s ROM az RST 8-at használva hibát jelez. Az Interface 1 csatlakoztatásával ez elmarad, és a vezérlés az árnyék ROM-ra kerül. Itt a rendszer megvizsgálja, hogy az RST-t hiba vagy a bővített BASIC használata okozta-e. Ha nem, a 16 k-s ROM hibavizsgálatára tér át. Ha bővített utasítás volt, az árnyék ROM végrehajtja a szintaktikai ellenőrzést, majd kilép, ha tisztázta a lapozás szükségességét. Ez a technika tette lehetővé, hogy a gyártó cégnek ne kelljen változtatnia az alapgép 16 k-s ROM programján, de az árnyék ROM használata kicsit bonyolult a felhasználónak. A nehézségek leküzdésére az árnyék ROM tervezői létrehoztak egy ún. kapcsoló kód (hook code) rendszert, amely lehetővé teszi, hogy a felhasználó által készített rutinok hozzáférjenek az árnyék ROM tartalmához.
A kapcsoló kód az RST8 utasítást követő adat-byte, amely 1B és 32 közé esik.
Az FF-től 1A-ig terjedő kódok egy normál hibaüzenetet adnak, míg a 32 felettiek kapcsolókód-hibát ("Hook code error") jeleznek. A programozónak óvatosan kell használnia a kapcsoló kódokat! Egyes rutinok tiltják a be/kiviteli műveletek előtt a megszakítást, mások hívása előtt azonban le kell tiltani a maszkolható megszakításkérést (l. a 7.8. szakaszt). Ha a programban a BASIC-hez való visszatérés következik (pl. a USR függvény után), akkor ügyeljünk arra, hogy H'L' regiszterpár értéke elő van készítve a Microdrive rutinok számára. Hiba esetén ez összezavarhatja a lebegőpontos kalkulátort, sőt az egész rendszert is. A 32-es címen található kapcsolókód használata a legelterjedtebb, ez teszi lehetővé a lapozás ki- és bekapcsolását. Gyakori probléma a disassembly kísérletek esetén az árnyék ROM- hoz való hozzáférés. Próbáljuk ki a következő programot:
5 CLEAR 32767
10 SAVE * "m"; l; "arnyek" CODE 0,8192
15 LOAD * "m"; l; "arnyek" CODE 32768
A SAVE végrehajtása során másolatot kapunk a kazettára az árnyék ROM-ról, amely a 8000 címtől disassemblálható, de természetesen figyelembe kell venni a címeltolódást.
Az RST 8-on kívül az árnyék ROM akkor is lapoz, ha a PC az 1708 címre mutat, amely a CLOSE # rutinban van. Ez a sajnálatos hiba becsúszott a konstrukcióba.
Csatornák
Az Interface 1 használatánál a rendszer 58 külön byte-ot lefoglal a rendszerváltozóknak, az 5CB6 címtől. Ezt a területet - a #31 kivételével - bármely árnyék ROM rutin vagy kapcsoló kód használata előtt, ill. bármely csatorna igénybevételekor össze kell állítani. #31 esetén:
CF RST 08
31 DEFB #31
Ha nincs az Interface csatlakoztatva a rendszerhez, akkor egy i hibaüzenet jelenik meg. Ezután az Interface-t csatlakoztatva, a gép hibaüzenet nélkül beszúr 58 byte-ot. A bővített rendszerváltozók a szokásosan működnek:
Először a VECTOR változó (5CB7) 01F0-ra állítódik be, de az cserélhető a bővített BASIC utasításokra is.
Az IOBORD (5CC6) 0-ra állítódik. Meghatározza a keret színét bizonyos be/kiviteli műveletek, azaz az RS232-re, a hálózatra és a Microdrive-ra írás alatt. Az IOBORD értéke a POKE 23+50,<színkód> utasítás segítségével állítható be. A keret villogását az írás alatt a POKE 23750,INT (PEEK 23624/8)-cal meg lehet szüntetni.
Az árnyék ROM rutinok
Vizsgáljuk meg néhány árnyék ROM rutin használatát a kapcsoló kódok segítségével! Tekintsük át a ki- és bemeneti feltételeket, vagyis hogy milyen paramétereket kell a programozónak átállítania, továbbá azokat a regisztereket, amelyek értéke a rutinok meghívása alatt változik.
A továbbiak könnyebb megértéséhez vázoljuk röviden az adatok elhelyezkedését a Microdrive kazettán (4. ábra)!
4. ábra: A Microdrive kazetta felosztása
A kazetta 180 szektorra tagolódik, amelyek mindegyike 512 adatbyte-ot tartalmaz. Az adatkezelő rutinok 256 szektort látnak el, de a 0, és kb. a 180 felettiek nem léteznek, ill. nem használatosak. További 2-3 szektornyi területet foglal el a végtelenített szalag összeillesztése. Minden szektort egy 12 byte-os (10 db 00 és 2 db FF) bevezető fejinformáció előz meg, majd 15 byte-nyi változó követ a HDFLAG-től a HDCHK-ig. Minden fejnek különböző száma van (HDNUMB) 1-től kb. 180-ig, amelyek a kazettán követik egymást.
A következő fejinformáció maga a szektor 12 byte-os bevezetővel és 15 byte-nyi változóval (RECFLG-től DESCHK-ig). Ezután következik az 512 adatbyte, amelyet az ellenőrző összeg követ (DCHK). Ha egy szektorban a RECFLG és a RECLEN 1. bitje 1, a szektort a gép nem használja. Az állományok általában több, mint egy szektornyi területet foglalnak el, ezért az 512 byte-os szektorok (0-val kezdődő) sorszámmal ellátott rekordokra darabolják az állományt. Ha egy szektorban 512 byte-nál kevesebb byte van, a RECFLG 1. bitje mutatja, hogy ez az utolsó foglalt szektor. A nem PRINT típusú állományoknál (pl. programokban) a jellemző tulajdonságokat (HD 00-től HD 11-ig) az első 9 byte tartalmazza a 0. sorszámú rekordban.
Az árnyék ROM RS232 rutinjainak használata előtt, a rendszernek ismernie kell a bővített rendszerváltozókat, és be kell állítania a kiválasztott jelátviteli sebességet. A csatorna formázása a 31-es kapcsoló kóddal valósítható meg, a továbbiakban pedig az átviteli sebességet a BAUD (5CC3) rendszerváltozó értékével állíthatjuk be. Használatkor a rendszer átnézi a konvertálótáblázatot (&0AEF-től &0B12-ig, ami 9 byte-párt jelent) a BAUD-ban levő érték átszámításához. Az RS232, a B és a T csatorna megnyitására, ill. lezárására nincsenek külön kapcsoló kódok. Csak a B csatorna küldő/fogadó rutinjának van kódja.
A bővített Spectrum rendszerhez helyi hálózat telepíthető. Egy időben csak egy kommunikáció lehetséges, és az adatátvitel mindig soros, csakúgy mint az RS232-nél, ahol azonban nincs start- vagy stopbit és nincs paritásbit sem. Az adatok számozott küldeményekre tagolódnak, mindegyik legfeljebb 255 byte hosszú lehet. A kiküldés menete a következő:
A küldő állomás megvizsgálja, hogy a hálózat foglalt-e, és ha igen, várakozik. Adás esetén kiküld 8 byte-nyi fejinformációt, amelynek az a feladata, hogy beállítsa az NTDES és NTHCS rendszerváltozók értékeit. Ez a fej különböző információkat tartalmaz a kimenő adatokról, az adó és vevő állomásazonosítójáról, és tartalmaz két ellenőrző összeget is.
Egyszerű adatátvitel esetén a küldő egy byte-formájában megvizsgálja a vevőállomás számát, s ha az azonosítás nem jár sikerrel, akkor a fejinformációt ismét kiküldi a hálózatba.
Ha körözvényről van szó, akkor az ide kapcsolódott állomások nullás azonosítót használnak. Így gyakorlatilag címzett nélkül lehet általános adást végrehajtani, hiszen a bekapcsolt állomások mindegyike fogja a körözvényt. Itt azonban a válasz-byte ellenőrzése elmarad, így az adó nem kap visszajelzést a vételről.
Üres adatszekció esetén az NTLEN értéke 0, ilyenkor nem történik adatátvitel. Ellenkező esetben a byte-ok száma áttevődik, és következik egy újabb ellenőrző válasz-byte (a körözvény esetét kivéve). Ha ennek az azonosítása nem elégséges, akkor a fejinformáció ismétlődik. Az árnyék ROM négy kapcsoló kódot használ a hálózathoz, amelyek közül az egyik használhatatlan.
7.7. Tanácsok az Interface 1 használatához
Az Interface 1 csatlakoztatása után gépi kódú programozáskor ügyeljünk a következőkre:
OPEN M
Egy ideiglenes M csatornát hoz létre a CHANS területén.
Használata: RST 8
DEFB 22Belépéskor: INT be. Kilépéskor: IX = CURCHL = a terület kezdete,
HL = stream elhelyezése ( = IX-CHANS+1),
INT be.Regiszterek: AF, BC, DE, HL, B'C', D'E', H'L', IX Kezdőcím: &1B29 Ennek aktivizálása előtt a D STR1 rendszerváltozó egy drive-számot kell, hogy tartalmazzon. Az N STR1 és a T STR1 a file-név kezdetét mutatja. Bővítés esetén ez az 595 byte-os terület van beszúrva a CHANS terület vége elé (a memóriahelyek engedélyezése esetén) és a jellemző adatok ide másolódnak át. Ha nincs térképterület a drive kiválasztásához, akkor az FF-ekkel töltődik fel. A drive ekkor kezdi keresni a file-nevet. A 0. bit az IX+25 (CHFLAG) 0-ra áll, ha ez PRINT file, egyébként 1. Vigyázzunk, mert itt az írásvédelem nincs ellenőrizve. A védelmet a következő rutin után hajtja végre:
IN A,(EF)
AND 1 ; zérus jelzőbit 1, ha védve van.Ez a rutin a Microdrive-motort nem kapcsolja ki, és a csatornakészítés ideiglenes. A folyamatos megvalósítást a streamben a következő rutin hajtja végre:
LD A,Stream
ADD A,A
LD HL,5C16
LD E,A
LD D,0
ADD HL,DE
PUSH HL
RST 8
DEFB OPEN M
PUSH HL
XOR A
RST 8
DEFB MOTOR
POP DE
POP HL
LD (HL),E
INC HL
LD (HL),D
RES 7,(IX+4)
RET
; Elmenti a stream kezdőcímét.
; Elmenti a stream helyét.
; Kikapcsolja a motort.
; Tárolja az új adatokat STRMS-ben.
; Folyamatossá teszi.
MOTOR
A MOTOR a Microdrive meghajtóját ki- vagy bekapcsolja.
Használata: RST 8
DEFB 21Belépéskor: A = 1-től 8-ig bekapcsol,
A = 0 mindent kikapcsol.Kilépéskor: INT ki, ha a <>0, vagy be, ha A=0. Regiszterek: AF, BC, DE, HL Kezdőcím: &17F7 Ha az akkumulátor nem nulla, a megfelelő Microdrive-motor kikapcsol és nem lehetséges a megszakítás. Ha az akkumulátor nulla, akkor minden egység kikapcsol és a megszakítás lehetséges. Ha a kiválasztott egység nincs csatlakoztatva, a "Microdrive not present" hibaüzenet következik.
CLOSE M
Lezárja az M csatornát.
Használata: RST 8
DEFB 23Belépéskor: IX = az M csatornaterület kezdete. Kilépéskor: INT be. Regiszterek: AF, BC, DE, HL Kezdőcím: &12A9 Ha a kiválasztott csatorna írásra megnyitott állomány volt, akkor az átmeneti tárba kerül. A Microdrive motorja kikapcsol és az 595 byte-os terület újra felhasználhatóvá válik. A megfelelő térképterület akkor marad szabad, ha a rendszer más úton nem használja.
ERASE M
Egy Microdrive állományt töröl.
Használata: RST 8
DEFB 24Belépéskor: - Kilépéskor: INT be. Regiszterek: AF, BC, DE, HL, B'C', D'E', H'L', IX Kezdőcím: &1D6E Alkalmazása előtt a D STR1 feltöltődik a szükséges Microdrive-számmal. A T STR1 és N STRl-ben az állományazonosító törlődik. Egy ideiglenes M csatorna jön létre, amely keresi az állományt a kazettán. Azonosítás esetén törli, ha több van belőle, akkor is csak egyet. Ha a kazetta írásvédett, akkor nem töröl, hanem a megfelelő hibaüzenet jelenik meg. A törlés befejeztével a motor kikapcsol és megszűnik az ideiglenes csatorna.
RECLAIM M
Felszabadítja a Microdrive által használt területet.
Használata: RST 8
DEFB 2CBelépéskor: IX = az M csatornaterület kezdete. Kilépéskor: - Regiszterek: AF, BC, DE, HL Kezdőcím: &10C4 Az 595 byte-os terület felszabadul és a logikai egységek lezáródnak. A térképterület akkor törlődik, ha más csatorna nem használja.
CAT
Egy kazetta katalógusa.
Használata: LD HL,1C58
LD (HD 11),HL
RST 8
DEFB 32Belépéskor: INT be. Kilépéskor: - Regiszterek: AF, BC, DE, HL, A'F', B'C', D'E', H'L', IX Kezdőcím: &1C58 Használatához az S STR 1-nek tartalmaznia kell a stream számot és a D STR1-nek az egységszámot. A CAT utasításhoz nincs közvetlen kapcsolódó kód, így a 32-es kód a HD 11-en keresztül éri el az árnyék ROM rutint. Először a választott stream lesz megnyitva - az 1601 rutint használva, majd egyes ideiglenes M csatorna jön létre. A kazettán minden fejinformációt megvizsgálva az állománynevek a CHANS terület pufferjébe kerülnek, ha nincsenek már ott tárolva, vagy ha nem CHR$ 0-val kezdődnek. A rutin ábécé-sorrendben rakja az állományneveket a pufferbe, ha pedig az egész kazettát leolvasta, vagy ha már 50 nevet megtalált, akkor az egység kikapcsol és a kazetta címe rákerül a választott streamre. Az összes állománynév kikerül a pufferból, és a kazetta neve, a lista és a szabad kbyte-ok száma kiíródik a képernyőre. Az M terület felszabadul.
FORMAT M
Kazettaformattálás.
Használata: LD HL,1B6E
LD (HD 11),HL
RST 8
DEFB 32Belépéskor: - Kilépéskor: INT be. Regiszterek: AF, BC, DE, HL, B'C', D'E', H'L', IX Kezdőcím: &1B6E Használata előtt a D STR1-nek tartalmaznia kell az egységszámot és az N STR1 és T STR1 az adott egység nevére mutat. Az ideiglenes M csatorna és az egység bekapcsolása után egy rövid késleltetés következik, amely alatt a rendszer megvizsgálja az írásvédelmet, és ha szükséges, hibaüzenetet ad. A puffer területe FC-re töltődik, és ebből ismételten a szalagra kerül a beírt kazettanév. Amikor az egész kazetta írásra kész, többszöri ellenőrzés után a motor megáll és az M terület felszabadul.
READ P
Kiolvas egy PRINT állományból egy rekordot.
Használata: RST 8
DEFB 27Belépéskor: IX = az M csatorna terület kezdete. Kilépéskor: INT ki, motor be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A17 A rutin használata előtt a CHDRIV az egységszámot kell, hogy tartalmazza; a CHREC a rekordszámhoz, a CHNAME az állománynévhez szükséges. Először a kiválasztott egység bekapcsol és a SECTOR a 04FD értéket veszi fel. A rutin ezután a kazettán kikeresi az aktuális rekordszámot a választott állományban. Ha megtalálta, és az PRINT állomány, akkor a szektort beolvassa a pufferbe és visszatér. Ha nem PRINT állományt talál, akkor a terület szabaddá válik, és a "Wrong file type" (Hibás állománytípus) hibaüzenet jelenik meg.
Ötszöri hiábavaló keresés után "File not found" (Az állomány nem található) hibaüzenetet kapunk és a terület, ha ideiglenesen foglalt volt, ismét felszabadul.
READ NP
Kiolvassa a következő rekordot egy PRINT állományból.
Használata: RST 8
DEFB 25Belépéskor: IX = az M terület kezdete. Kilépéskor: INT ki, motor be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A09 A rutin használatához a - READ P-hez hasonlóan - a CHDRIV-be az egységszámot, CHNAME-be az állománynevet kell tenni. Először a RECFLG első bitje ellenőrzi az aktuális rekordot, hogy az az utolsó-e, ha igen, akkor az "End of file" (állomány vége) üzenet jelenik meg, ha nem, a CHREC tartalma növekszik, és a READ P folytatódik.
READ S
A következő szektort olvassa.
Használata: RST 8
DEFB 29Belépéskor: IX = az M terület kezdete. Kilépéskor: INT ki, motor be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A86 A READ S meghívása előtt a CHDRIV és CHNAME változókat be kell állítani. A következő fejinformáció és a kazetta következő szektora beolvasódik a csatornaterületre. Ha PRINT állomány, akkor a rutin törli az átviteljelző (C) bitet. Ha nem, akkor törli a puffer tartalmát és C = 1-gyel visszatér.
READ R
Véletlenszerűen olvas egy PRINT szektort.
Használata: ? Belépéskor: IX = az M terület kezdete. Kilépéskor: INT ki, motor be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A4B Megkeresi a kazettán a CHREC szektorszámot, ha megtalálta, betölti a pufferbe. PRINT állomány esetén a C bit nullázódik és a rutin visszatér a rendszerhez. Egyébként a puffer tartalma törlődik, a C bit 1-be áll. Egy alkalommal való sikertelen szektorkeresés után a "File not found" hibaüzenet jelenik meg.
WRITE S
Soros írás egy szektorra.
Használata: RST 8
DEFB 26Belépéskor: IX = az M terület kezdete. Kilépéskor: INT be, motor ki. Regiszterek: AF, BC, DE, HL Kezdőcím: &11FF Hívása előtt a CHBYTE, a CHREC, a CHDRIV és a CHNAME változók a pufferből a megfelelő értékeket veszik fel. A motor bekapcsolása után a rutin megvizsgálja az egész kazettát, az állománynév átmásolódik a CHNAME-ből a RECNAM-be, a CHBYTE és a CHREC, a RECLEN és RECNUM-ba. A HDCHK és a DESCHK elkészíti az ellenőrző összeget és a RECFLG-HDCHK tartomány - ha nincs írásvédelem - az első nem használt szektorba íródik be. A térkép megfelelő bitje beállítódik, a CHBYTE nullázódik és a CHREC növekszik, majd kikapcsol a motor.
WRITE R
Véletlenszerű írás egy szektorra.
Használata: RST 8
DEFB 2ABelépéskor: IX = az M terület kezdete. Kilépéskor: INT ki, motor be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A91 Meghívása előtt a CHREC és CHDRIV beállítódik, a CHNAME pedig a kimentett szektor nevét tartalmazza. A rutin egyszer vizsgálja át a kazetta CHREC számú szektorát. Sikertelen azonosítás esetén "File not found" jelenik meg, egyébként megvizsgálja az írásvédelmet. Ha megtalálja a szektort, a HDCHK-RECFLG byte-ok a kazettára íródnak és beállítódik a térkép aktuális bitje. Jegyezzük meg, hogy a rutin nem ellenőrzi a térképet az írás előtt!
232 IN
Egy byte-ot olvas az RS232-ről.
Használata: RST 8
DEFB 1DBelépéskor: - Kilépéskor: C bit = 1, ha egy byte-ot olvas,
A = byte,
INT be.Regiszterek: AF, BC, DE, HL Kezdőcím: &0B81 Beolvas az RS232 pontról egy byte-ot, túl hosszú várakozást és a SPACE lenyomását kivéve ("Break into program"). Az első byte beolvasása után a C bit 1-be áll.
232 OUT
Kiküld egy byte-ot az RS232-re.
Használata: RST 8
DEFB 1EBelépéskor: INT be. Kilépéskor: A = kód. Regiszterek: AF, BC, DE, HL Kezdőcím: &0C5A A porton keresztül a beállított sebességgel egy byte-ot küld az RS232-re. A BREAK lenyomása az átvitel alatt hibaüzenettel megállítja a kiküldést. A T csatorna igénybevételekor használható a 32-es kapcsoló kód, ami a &0C3C címet hívja, amikor is az A tartalma a karakter kódja.
OPEN R
Megnyitja a RS232-es csatornát.
Használata: LD HL,0B13
LD (HD 11),HL
RST 8
DEFB 32Belépéskor: INT be. Kilépéskor: DE = az új CHANS terület kezdete. Regiszterek: AF, BC, DE, HL Kezdőcím: &0B13 A rutin egy 11 byte-os területet hoz létre a CHANS végén a B vagy T csatorna számára. Alapesetben T csatorna keletkezik, de ha az L STR1 B-t tartalmaz, akkor bináris csatorna jön létre.
OPEN N
Megnyitja az ideiglenes N csatornát.
Használata: RST 8
DEFB 2DBelépéskor: - Kilépéskor: X = DE= (CURCHL) = a CHANS-beli N terület kezdete. Regiszterek: AF, BC, DE, HL Kezdőcím: &0EA9 A rutin meghívása előtt a D STR1-nek az egységszámot, az NTSTAT-nak a Spectrum saját azonosítószámát kell tartalmaznia. A rutin a CHAN terület végén létrehoz egy adattároló területet. A beállított értékek átmásolódnak D STRA-ről az NCIRIS-re, állomásszám esetén az NTSTAT-ból az NCSELF-re, végül az NCNUMB tartalma a puffer utolsó karakterére másolódik. A csatorna ideiglenessé válik, a csatornaazonosító 7. bitjének beállításával. A CURCHL változó az újonnan létrehozott terület kezdetére mutat. Egy folyamatos LAN csatorna használatát a következő rutinban követhetjük nyomon (D STR1 ás NTSTAT beállítása után):
LD A,Stream
ADD A,A
LD HL,5C16
LD E,A
LD D,0
ADD HL,DE
PUSH HL
RST 8
DEFB OPEN N
RES 7,(IX+4)
LD HL,(CHANS)
EX DE,HL
AND A
SBC HL,DE
INC HL
POP DE
EX DE,HL
LD (HL),E
INC HL
LD (HL),D
RET
; HL= a megfelelő elhelyezés az STRMS-ben
; Elmentés
; Az ideiglenes N csatorna megnyitása,
; majd állandóvá tétele.
; HL= a stream elmozgatása
; DE= STRMS elhelyezése
; Tárolja az elmozdítást a STRMS-ben
CLOSE N
Lezárja az N csatornát.
Használata: RST 8
DEFB 2EBelépéskor: CURCHL = A CHANS-beli N terület kezdete. Kilépéskor: INT be. Regiszterek: AF, BC, DE, HL, IX Kezdőcím: &1A24 Ha a csatorna egy íróállomány (NCOBL<>0), akkor a puffer fennmaradó tartalma az EOF-fal végződő küldeményben van. Az átmeneti tár területe felszabadul, de a kapcsolódó stream nem zárul le. Az N terület lehet ideiglenes, vagy a CHANS utolsó csatornája.
WRITE N
Kiad egy küldeményt a helyi hálózatra.
Használata: RST 8
DEFB 30Belépéskor: A = 0 az adatokra,
A = 1 az EOF-ra.
IX = az N terület kezdete.Kilépéskor: INT be,
A = azonosító szám (0 körözvény esetén).Regiszterek: AF, BC, DE, HL Kezdőcím: &0DB2 Meghívása előtt az NCOBL és NCNUMB változókat, a puffertartalmat és a fejinformációt (az ellenőrző összeggel együtt) be kell állítani. Belépéskor az akkumulátornak 0-t kell tartalmaznia, ill. EOF jelző küldemény esetén 1-et. Az érték az NCTYPE-ban tárolódik, míg a keretszínt az IOBORD állítja be. A puffer tartalmának ellenőrző összege az NCDCS, míg az NCIRlS-tól NCDCS-ig terjedő ellenőrző összeg az NCHCS-ben rögződik.
A közlemény alatt nem megengedett a megszakítás, a közlemény elfogadása esetén (a körözvényt kivéve) az NCNUMB értéke nő, a keretszín visszaáll és a továbbiakban engedélyezett a megszakítás.
READ N
Közlemény olvasása a helyi hálózatból.
Használata: RST 8
DEFB 2FBelépéskor: IX = az N terület kezdete Kilépéskor: INT be. Regiszterek: AF, BC, DE, HL Kezdőcím: &1A31 Ez a kapcsoló kód valószínűleg egy küldemény kiolvasására szolgál, de a rutin végén fellépő hiba miatt nem használható. A C bit ellenőrizné egy küldemény kiolvasását, de összezavarodik, amikor a keretszín-visszaállító rutinra lép, amely elállítja a megelőző értéket. A hálózatból való karakterolvasásra ajánlatosabb a 16k-s ROM INPUT rutinját használni (15E6-tól); itt a CURCHL értékét bármilyen csatorna hívása előtt be kell állítani.
PAUSE
Egy billentyű lenyomására vagy ismétlésére vár.
Használata: RST 8
DEFB 1BBelépéskor: - Kilépéskor: INT be,
A = a billentyű kódja.Regiszterek: AF, BC, DE, HL Kezdőcím: &19D9 Minden 1/50 másodpercben megengedett a megszakítás. A billentyű lenyomása alatt a 16 k-s ROM billentyűzetvizsgáló rutinja fut. A karakter kódját LAST K-ból olvassa ki.
PRINT
Egy karakter képernyőre írása.
Használata: RST 8
DEFB 1CBelépéskor: A = karakter kód,
INT be.Kilépéskor: - Regiszterek: AF, BC, DE, HL, A'F', B'C', D'E' Kezdőcím: &19EC Az SCR CT rendszerváltozót FF-re állítja, ami lehetővé teszi az automatikus képfelcsúsztatást. Megnyitja az FF stream-et (S csatorna) és kiírja a karaktert.
LPRINT
Egy karaktert küld a ZX-Printerre.
Használata: RST 8
DEFB 1FBelépéskor: A = karakter kód,
INT be.Kilépéskor: - Regiszterek: AF, BC, DE, HL, A'F', B'C', D'E' Kezdőcím: &19FC A 3-as stream (P csatorna) megnyitása után a karaktert kiküldi a nyomtatóra.
SCAN K
A billentyüzetmátrixot vizsgálja.
Használata: RST 8
DEFB 20Belépéskor: - Kilépéskor: 0, ha nem nyomtuk le a billentyűt,
0-tól különböző, ha igen.Regiszterek: AF, BC, DE, HL Kezdőcím: &1A01 Közvetlenül vizsgálja a billentyűzetet és bármelyik billentyű lenyomása esetén átállítja a Z jelzőbitet.
NEWVARS
Létrehozza a bővített rendszerváltozókat.
Használata: RST 8
DEFB 31Belépéskor: - Kilépéskor: - Regiszterek: AF, BC, DE, HL Kezdőcím: &19A8 A bővített 58 rendszerváltozó előállítására szolgál, valójában &19A8 tartalmazza a RET-et, míg a bővített rendszerváltozókat az RST 8 hozza létre.
SHADOW
Bármely árnyék ROM-rutin hívására szolgál.
Használata: RST 8
DEFB 32Belépéskor: (HD 11) = kezdőcím. Kilépéskor: - Regiszterek: Csak a rutintól függ. Kezdőcím: &19A4 A választott árnyék ROM rutinra a HD 11 meghívása mutat. A gyártó cég által a jövőbeli kiterjesztések számára fenntartott (Reserved for future expansion), így a leghatékonyabb kapcsolódó kód. A rutin csak az A regisztert használja, minden érték az akkumulátoron keresztül tér vissza. A rutin a következő kiegészítéssel képes az aktuális BASIC ROM-ra is lapozni.
LD HL,PAGOUT
LD (HD 11),HL
RST 8
DEFB 32
DEFB PAGOUT
POP HL
POP HL
POP HL
POP HL
; Visszaveszi 0700-t a veremből
; Visszaveszi PAGOUT-t a veremből
; A maradék programA 16 k-s ROM-hoz való visszalapozást a CALL 0700 hajtja végre.
Utasítások:
CAT n
Az n számú Microdrive-ba helyezett kazetta katalógusát adja meg. Betűrendben kiírja az állományneveket és közli (kbyte-ban) a kazettán még felhasználható szabad terület hosszát.CAT# s; n
Az n Microdrive kazetta katalógusát az s streamre küldi ki.CLOSE# s
Az s streamet lezárja, a pufferben levő adatokat továbbítja.ERASE "m"; n; "<állománynév>"
Az n szám egység kazettájáról törli a megadott állományt.FORMAT "b"; x
Az RS232 jelátviteli sebességét állítja be x értékre; x lehetséges értékei:
50, 110, 300, 600, 1200, 2400, 4800, 9600, 19200.FORMAT "t"; x
Az x értéke az előzőek valamelyike lehet; a parancs működése annyiban tér el a FORMAT "b"; x-étől, hogy a szövegcsatorna formattálása után (pl. listázás során RS232 szabványú nyomtatók esetén) a csatornán kimennek a szabályos kocsivissza jelek is.FORMAT "m"; n; "<kazettanév>"
Az n számú egységbe helyezett kazettát a kívánt névvel formattálja.FORMAT "n"; x
Az állomást helyi hálózat esetén x állomásazonosítóval látja el.INKEY$ s
Csak helyi hálózat vagy RS232 esetén használható. A streamből kiemelt karakterrel tér vissza. Adat híján ez üres füzér lesz.INPUT# s, v
A v változót feltölti az s streamből kiolvasott értékkel. Természetesen használata előtt a streamet valamely csatornához rendelve olvasásra meg kell nyitni. A PRINT után elhatároló jelek (; , stb.) íráshoz használják a streamet. LINE használata bővített rendszer esetén is megengedett.LOAD* <csatornaadat>
Az adott csatornáról ("b", "n", "m") beolvassa a kívánt állományt. Szintaxisa a FORMAT-hoz hasonló.MERGE* <csatornaadat>
Használata az előzőhöz hasonló, de nem törli a RAM-ban levő BASIC programsorokat és változókat csak ha azok a befésült programban is előfordulnak. Automatikusan induló programok befésülése kazettáról hibát eredményez.MOVE <forrás> TO <cél>
A forrás és cél csatorna vagy stream lehet. Ezek között történik az állomány mozgatása. Végrehajtása az állományvégjei hatására fejeződik be.OPEN# s, c
A c csatornát olvasásra vagy írásra nyitja meg az s streamen.PRINT# s, &
Az s streamre írja az &-tel jelölt listaelemeket. Használata előtt a streamnek íráshoz nyitottnak kell lennie.SAVE* <csatornaadat>
Az adott csatornára ("b", "n", "m") kimenti a kívánt állományt.
Szintaxisa a FORMAT-hez hasonló.VERIFY* <csatornaadat>
Használata a LOAD*-hoz hasonló, de nem végez tényleges betöltést, csak összehasonlítja az állományt a RAM tartalmával.
Rendszerszintű működés és hibakezelés
A legfontosabb a bővített utasításkészlet használatához az Interface 1 VECTOR rendszerváltozója (5CB7). Alapesetben, mikor 01F0-t tartalmaz, az árnyék ROM területen is végrehajtja a hibakezelést (CHADD CH ADD-ra való visszamásolása után). Nézzük meg, hogy hogyan kezeli az árnyék ROM a rendszer hibáit!
A HL regiszterpár tartalmazza az RST 8-ról való visszatérési címet, és a program megvizsgálja, hogy az 0000 vagy 15FE-e. Az első esetben az árnyék ROM meghívja a 16k-s ROM rutint, a második esetben egy Interface 1 csatorna válik szükségessé. Ha egyik eset sem következik be és még nem léteznek a bővített rendszerváltozók, akkor a rendszer gondoskodik a létrehozásukról.
Ezután a program megvizsgálja a hibaszámot (az RST 8-at követő byte-ot) és ellenőrzi, hogy kapcsoló kód-e. Ha nem, akkor a 16 k-s ROM kapcsolódik vissza, és lekezeli a hibát. Ha kapcsoló kód volt, akkor az Interface 1 ROM végrehajtja a megfelelő utasítást.
Ha a hiba bővített BASIC utasításban lépett fel, akkor a CH ADD tartalma a CHADD-ban tárolódik. A FLAGS3 3. bitje 1 értékű lesz és az árnyék ROM lekezeli a hibát. A lapozás után a hibás sor első karakterét összeveti az Interface tokennel (01B5...01E9). Ha ezt nem ismeri fel, akkor a rutin a VECTOR-ban tárolt címen folytatódik. Ez az ugrás alapesetben (01F0 érték mellett) hibához vezet, de ha ezt az értéket módosítjuk, akkor rutinnal bővített BASIC utasításokat is kezelhetünk.
Néhány tanács a rutinok használatához:
Az árnyék ROM újraindításánál pedig vegyük figyelembe a következőket:
FF | Program finished (Program vége) | 00E7 |
00 | Nonsense in BASIC (A BASIC-ben értelmetlen) | 0139 |
01 | Invalid Stream Number (Hibás streamszám) | 0663 |
02 | Invalid device expression (Hibás csatornamegjelölés) | 062D |
03 | Invalid name (Hibás állománynév) | 064C |
04 | Invalid drive number (Hibás egységszám) | 0681 |
05 | Invalid station number (Hibás állomásazonosító) | 05F6 |
06 | Missing name (Hiányzik az állománynév) | 068D |
07 | Missing station number (Hiányzik az állomásazonosító) | 06A1 |
08 | Missing drive number (Hiányzik a Microdrive sorszám) | 0683 |
09 | Missing baud rate (Hiányzik az átviteli sebesség) | 06B7 |
0A | Header mismatch error (Idegen állományazonosító) | - |
0B | Stream alredy open (A stream már nyitott) | 052F |
0C | Writing to a 'read' file (íráskísérlet olvasáshoz nyitott állományban) | 0D78 |
0D | Reading a 'write' file (Olvasáskísérlet íráshoz nyitott állományból) |
0D1C |
0E | Drive 'write' protected (írásvédett egység) | 128D |
0F | Microdrive full (Betelt a kazetta) | 1219 |
10 | Microdrive not present (A Microdrive hiányzik) | 1828 |
11 | File not found (Az állomány nem található) | 11A3 |
12 | Hook code error (Nemlétező kapcsoló kód) | 1985 |
13 | CODE error (Állományhosszhiba) | 092E |
14 | MERGE error (MERGE hiba) | 07D8 |
15 | Verification has failed (Hiba az ellenőrzés során) | 0930 |
16 | Wrong file type (Hibás állománytípus) | 0902 |
Programsor-ellenőrző rutinok
Bármelyik BASIC parancs kiadása, vagy az adott utasításra való vezérlésátadás után a rendszer megvizsgálja az utasítás szintaxisát. Az eredeti ROM rutinjai, amelyek karakterről karakterre ellenőriznek, a bővített rendszerben is használhatók. Az ellenőrzés az RST 10 segítségével történik a következő módon:
GET CHAR 0018
A sor éppen feldolgozott byte-ját adja vissza.NEXT CHAR 0020
A sor következő byte-ját adja vissza a mutató továbbléptetésével.
Az árnyék ROM is tartalmaz néhány, közvetlenül hívható ellenőrző rutint:
PARAMS# 0701
A Microdrive műveletek paramétereit állítja be.EVALBC# 061E
16-bites számot ellenőriz a BC és DSTR1 segítségével.CHKEND# 05B7
Ellenőrzi az utasítás végjelet. Ha nincs végjel, akkor hibajelzést ad. Ha van, akkor egy RET-et hajt végre.CHKDRV 066D
Megvizsgálja, hogy a D STR1 rendszerváltozó tartalma 1 és 8 közé esik-e. Ha nem, az "Invalid drive number" (Hibás egységszám) hibaüzenet íródik ki.CHKSTS # 062F
Az állománynevek szintaktikai ellenőrzését végzi.
1. Kapcsolókód-hibák:
2. CLOSE probléma:
3. A szintaktikai ellenőrzés hibái:
ERASE <füzér>, pl.: ERASE "teszt";
MOVE <füzér>, <füzér>, pl.: MOVE "a", "b";
FORMAT <füzér>, pl.: FORMAT "teszt";
CAT szám nélkül.
4. A BREAK következetlensége:
5. Az RS232 dupla szóközök:
6. Hosszú állománynév hibaüzenet:
7.11. Új árnyék ROM változatok
A fejezetbeli árnyék ROM címek, ill. belépési pontok az eredeti Interface 1 ROM-ra vonatkoznak (a továbbiakban ROM1). Időközben azonban forgalomba kerültek módosított Interface 1-ek, amelyeknek némiképp más a ROM-ja (ROM2), sőt legújabban néhány byte-os változással megjelent a ROM3 is.
Szeretnénk segítséget nyújtani abban, hogy sikeresen eligazodhassunk a három árnyék ROM szövevényében.
Elsőként azt kell megtudni, hogy milyen ROM van a készülékben. Ha beírjuk, hogy:
SAVE "m";l;"arny" CODE 237,1: LOAD "m";l;"arny" CODE 23296: PRINT PEEK 23296
akkor átmásoltunk egy szignifikáns byte-ot az árnyék ROM-ból a RAM-ba. Tartalma szerint eldönthetjük, hogy milyen sorozatú Interface 1 áll rendelkezésünkre:
ROM1 - 25
ROM2 - 113
ROM3 - 115
Ha nem e 3 szám valamelyike, akkor még ismeretlen az árnyék ROM tartalma.