Obsah
1. Matematické koprocesory na platformě x86: vše se komplikuje
2. Příznaky a výjimky při provádění celočíselných operací
3. Výjimky, které mohou nastat při manipulaci s hodnotami s plovoucí řádovou čárkou
4. Výjimky a příznaky uložené ve stavovém slově matematického koprocesoru
5. První demonstrační příklad: výjimky IE a ZO
6. Druhý demonstrační příklad: výjimka OE
7. Příznakové bity C0, C1, C2 a C3
8. Třetí demonstrační příklad: instrukce FTST
9. Čtvrtý demonstrační příklad: instrukce FXAM
10. Varianty instrukce FCOM pro porovnání dvou operandů
11. Pátý demonstrační příklad: porovnání dvou hodnot instrukcí FCOM(PP)
12. Vztah mezi příznakovými bity FPU a CPU
13. Mapování mezi stavovými bity matematického koprocesoru a příznakovými bity CPU
14. Kopie příznakových bitů FPU do registru FLAGS s následným rozeskokem
15. Zrychlené provedení kopie příznakových bitů matematickým koprocesorem Intel 80287
16. Šestý demonstrační příklad: výsledek testu hodnoty uložené na vrcholu zásobníku
17. Sedmý demonstrační příklad: plné porovnání dvojice hodnot na zásobníku
18. Příloha: seznam všech instrukcí matematických koprocesorů řady 80×87
19. Repositář s demonstračními příklady
1. Matematické koprocesory na platformě x86: vše se komplikuje
Na předchozí dvojici článků o matematických koprocesorech na platformě x86 [1] [2] dnes navážeme. Prozatím již víme, jaké formáty numerických hodnot mohou matematické koprocesory zpracovávat a taktéž známe základní instrukce pro provádění různých aritmetických operací i pro výpočet transcendentních funkcí (viz tabulka umístěná v příloze). Ovšem při provádění těchto operací může dojít k různým situacím, na které je vhodné určitým způsobem reagovat. Může například nastat dělení nulou, může dojít k přetečení či podtečení výsledné hodnoty, výsledkem může být denormalizovaná hodnota (příliš blízko nuly) nebo dokonce může být samotná prováděná operace nevalidní. I na takové situace je vhodné myslet. S nadsázkou je totiž možné říct, že kvalita návrhu IEEE 754 (autorem je profesor Kahan z Berkeley ve spolupráci s firmou Intel[*]) vede k tomu, že se problémy buď vůbec neobjeví, nebo se objeví příliš pozdě.
2. Příznaky a výjimky při provádění celočíselných operací
Na chvíli se vraťme k „jednoduchým“ celočíselným operacím, například k operacím prováděným se šestnáctibitovými hodnotami uloženými ve formátu dvojkového doplňku (two's complement). Při provádění takových operací se nastavuje několik příznaků (flags) a může taktéž dojít k výjimkám (exceptions). Připomeňme si nejprve, o jaké příznaky se jedná právě na platformě x86:
| # | Příznak | Stručný popis příznaku |
|---|---|---|
| 1 | OF | příznak přetečení (overflow) do nejvyššího bitu |
| 2 | CF | příznak přenosu (carry) z nejvyššího bitu |
| 3 | AF | příznak přenosu ze třetího do čtvrtého bitu (auxiliary carry) |
| 4 | ZF | příznak nulovosti (zero) |
| 5 | SF | příznak znaménka (sign), tedy hodnota nejvyššího bitu |
| 6 | PF | příznak (bitové) parity |
Nastat taktéž mohou tři výjimky, které vedou k vyvolání přerušení (interrupt). Na prvním místě je dělení nulou, s nímž se patrně setkala většina vývojářů (ve vyšších programovacích jazycích je totiž většinou vyvolána právě výjimka). Druhá výjimka může vzniknout po provedení instrukce INTO, která testuje, zda nějaká předchozí instrukce nevedla k přetečení výsledku. A třetí výjimka vznikne po provedení instrukce BOUNDS, která zjišťuje, zda se testovaná hodnota nachází v intervalu specifikovaném dolní a horní mezí. Tyto dvě instrukce byly na platformě x86 implementovány proto, aby umožnily snadný překlad programů v jazycích typu Pascal atd., v nichž se (obecně) meze kontrolují.
3. Výjimky, které mohou nastat při manipulaci s hodnotami s plovoucí řádovou čárkou
Matematický koprocesor má taktéž svoji sadu příznaků a výjimek. Navíc je možné výjimky maskovat, tj. specifikovat, jestli se má při vzniku výjimky vyvolat přerušení či nikoli. Podívejme se nejdříve na všechny výjimky, které jsou matematickým koprocesorem detekovány při manipulaci s hodnotami s plovoucí řádovou čárkou:
| # | Označení | Význam |
|---|---|---|
| 1 | IE | výjimka Invalid Operation |
| 2 | DE | výjimka Denormalized Operand |
| 3 | ZE | výjimka Zero Divide |
| 4 | OE | výjimka Overflow |
| 5 | UE | výjimka Underflow |
| 6 | PE | výjimka Precision |
Výjimka IE (Invalid Operation) vznikne ve chvíli, kdy dojde buď k přetečení nebo podtečení zásobníku. Ovšem taktéž k ní může dojít v případě, že je výsledkem hodnota NaN, což je například výpočet druhé odmocniny ze záporné hodnoty.
Výjimka DE (Denormalized Error) vznikne tehdy, pokud je jeden z operandů prováděné operace denormalizovaný nebo pokud je denormalizovaný výsledek (tedy blízký nule). To v důsledku znamená sníženou přesnost výpočtů.
Výjimka ZE (Zero Error) vznikne při dělení nenulové hodnoty nulou, což do jisté míry odpovídá i příslušné celočíselné výjimce (ovšem na FPU dostaneme rozumný očekávaný výsledek – kladné nebo záporné nekonečno).
Výjimka OE (Overflow Error) vznikne v případě, že výsledek je příliš velký pro daný formát hodnot. Pokud je tato výjimka maskována, bude výsledkem kladné či záporné nekonečno.
Naopak výjimka UE (Underflow Error) vznikne v případě, že je výsledek operace naopak příliš malý a musí se provést jeho denormalizace nebo je dokonce výsledkem nula.
Výjimka PE (Precision Error) vznikne tehdy, pokud je výsledek nepřesný, tj. nelze přesně uložit do zvoleného formátu (zdaleka ne všechny hodnoty je možné reprezentovat systémem mantisa×2exponent).
4. Výjimky a příznaky uložené ve stavovém slově matematického koprocesoru
Potřetí a již naposledy si v tomto seriálu uvedeme tabulku s popisem jednotlivých bitů stavového slova matematického koprocesoru. Zajímat nás bude zejména prvních šest bitů, které obsahují právě indikaci toho, že při provádění matematických operací došlo k nějaké výjimce popsané v předchozí kapitole. Ovšem zajímavý je i osmý bit ES, který je nastaven na jedničku tehdy, pokud došlo k libovolné výjimce (z předchozích šesti):
| # | Označení | Význam |
|---|---|---|
| 0 | IE | výjimka Invalid Operation |
| 1 | DE | výjimka Denormalized Operand |
| 2 | ZE | výjimka Zero Divide |
| 3 | OE | výjimka Overflow |
| 4 | UE | výjimka Underflow |
| 5 | PE | výjimka Precision |
| 6 | SF | špatná manipulace se zásobníkem operandů |
| 7 | ES | Error summary |
| 8 | C0 | výsledek porovnání (příznakový bit) |
| 9 | C1 | výsledek porovnání (příznakový bit) |
| 10 | C2 | výsledek porovnání (příznakový bit) |
| 11 | ST0 | ukazatel vrcholu zásobníku |
| 12 | ST1 | ukazatel vrcholu zásobníku |
| 13 | ST2 | ukazatel vrcholu zásobníku |
| 14 | C3 | výsledek porovnání (příznakový bit) |
| 15 | B | busy bit (provádí se operace) |
5. První demonstrační příklad: výjimky IE a ZE
V dnešním prvním demonstračním příkladu si otestujeme chování matematického koprocesoru v případě, že se provádí aritmetická operace podílu a taktéž výpočet druhé odmocniny. Konkrétně při testování operace podílu budeme postupně dělit hodnoty 0/1, 1/1, 1/0 a 0/0. A v případě výpočtu druhé odmocniny budou do výpočtu vstupovat hodnoty 0, 1 a –1. Před každou takovou operací navíc zavoláme (pomalou) instrukci FNINIT, která matematický koprocesor nastaví do výchozího stavu:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fdiv ; podíl 0/1
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fdiv ; podíl 1/1
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fldz ; uložení konstanty 0 na zásobník
fdiv ; podíl 1/0
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fldz ; uložení konstanty 0 na zásobník
fdiv ; podíl 0/0
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldz
fsqrt ; odmocnina z 0
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fsqrt ; odmocnina z 1
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
call print_status_word ; tisk stavového slova
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_status_word:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
and ax, 0xff ; zamaskovat bity, ktere neobsahuji priznaky chyb
print_hex_16 ax ; tisk stavoveho slova v hexadecimalnim formatu
ret
; datova cast
test_word: dw 0
Po spuštění tohoto demonstračního příkladu se vypíše obsah dolních osmi bitů stavového slova mikroprocesoru, protože provádíme maskování instrukcí and ax, 0×ff). Podívejme se tedy nejenom na výsledné bity, ale i na jejich význam, resp. interpretaci:
| # | Provedená operace | Stavové slovo | Nastavené výjimky |
|---|---|---|---|
| 1 | 0/1 | 0×0000 | bez výjimek |
| 2 | 1/1 | 0×0000 | bez výjimek |
| 3 | 1/0 | 0×0004 | ZE – Zero (Divide) Error |
| 4 | 0/0 | 0×0001 | IE – Invalid Operation Error |
| 5 | √0 | 0×0000 | bez výjimek |
| 6 | √1 | 0×0000 | bez výjimek |
| 7 | √-1 | 0×0001 | IE – Invalid Operation Error |
6. Druhý demonstrační příklad: výjimka OE
Dnešní druhý demonstrační příklad je v porovnání s předchozím demonstračním příkladem nepatrně složitější. Budeme v něm zjišťovat, jestli se nastavuje výjimka OE, která by měla indikovat takový stav, kdy výsledná hodnota přesahuje rozsah daného formátu (single, double, extended). Jak takového stavu dosáhneme? Budeme neustále opakovat programovou smyčku, ve které se hodnota uložená na vrcholu zásobníku bude umocňovat. Na začátku, tj. ještě před vstupem do programové smyčky, umístíme na zásobník konstantu 2 a v každé iteraci tuto konstantu umocníme (na druhou) a výsledek uložíme zpět na zásobník. Postupně se tedy bude pracovat s hodnotami 2, 4, 16, 256, …, což poměrně rychle vede k situaci, kdy dojde k přetečení dostupného rozsahu.
Inicializace konstanty na vrcholu zásobníku:
fninit ; inicializace koprocesoru fld1 ; uložení konstanty 0 na zásobník fld1 ; uložení konstanty 0 na zásobník faddp ; nyní je na zásobníku uložena hodnota 2
Zajímavá je implementace programové smyčky, protože v ní vyžadujeme výpočet druhé mocniny. Musíme tedy buď násobit hodnotu na vrcholu zásobníku toutéž hodnotou (což je možné – druhý operand lze adresovat), nebo se nejprve tato hodnota zduplikuje a poté se provede klasický součin. Vzhledem k tomu, že matematický koprocesor (kupodivu) nemá instrukci pro duplikaci hodnoty, použijeme trik – instrukci FLD ST(0), která na zásobník uloží nový prvek obsahující hodnotu přečtenou z původního vrcholu zásobníku:
smycka1:
fld st0 ; duplikace hodnoty na vrcholu zásobníku
fmulp ; výpočet druhé mocniny
call print_status_word ; tisk stavového slova
loop smycka1
Podívejme se na úplný zdrojový kód tohoto demonstračního příkladu:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 0 na zásobník
fld1 ; uložení konstanty 0 na zásobník
faddp ; nyní je na zásobníku uložena hodnota 2
mov cx, 20 ; počet opakování smyčky
smycka1:
fld st0 ; duplikace hodnoty na vrcholu zásobníku
fmulp ; výpočet druhé mocniny
call print_status_word ; tisk stavového slova
loop smycka1
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_status_word:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
and ax, 0xff ; zamaskovat bity, ktere neobsahuji priznaky chyb
print_hex_16 ax ; tisk stavoveho slova v hexadecimalnim formatu
ret
; datova cast
test_word: dw 0
Po spuštění tohoto demonstračního příkladu se do DOSového okna vypíše sekvence hodnot 0×00, která je následována hodnotou 0×28. Jaký je jejich význam?
| # | Hodnota | Stavové slovo | Nastavené příznaky |
|---|---|---|---|
| 1 | 0×00 | bez výjimek | |
| 2 | 0×28 | výjimka OE + nastavení příznakového bitu C1 |
7. Příznakové bity C0, C1, C2 a C3
Matematický koprocesor neobsahuje příznakové bity, které by přímo odpovídaly příznakovým bitům hlavního procesoru – tedy zejména ZF, OF a SF (postupně: příznak nulovosti, příznak přenosu a příznak znaménka). Namísto toho mají programátoři k dispozici čtveřici příznakových bitů s nicneříkajícími zkratkami C0, C1, C2 a C3. Proč tomu tak je? Tyto příznaky totiž mají odlišný význam, který závisí na tom, jaká instrukce je nastavuje. Ukažme si to na trojici instrukcí.
První instrukcí je instrukce nazvaná FTST, která testuje obsah hodnoty uložené na vrcholu zásobníku a nastavuje příznakové bity následovně:
| C3 | C2 | C0 | odpovídá stavu |
|---|---|---|---|
| 0 | 0 | 0 | ST(0) > 0 |
| 0 | 0 | 1 | ST(0) < 0 |
| 1 | 0 | 0 | ST(0) = 0 |
| 1 | 1 | 1 | ST(0) ? 0 (neporovnatelné hodnoty) |
Podobně se chová instrukce FCOM, která porovnává dvojici hodnot:
| C3 | C2 | C0 | odpovídá stavu |
|---|---|---|---|
| 0 | 0 | 0 | ST(0) > druhý operand |
| 0 | 0 | 1 | ST(0) < druhý operand |
| 1 | 0 | 0 | ST(0) = druhý operand |
| 1 | 1 | 1 | ST(0) ? druhý operand (neporovnatelné hodnoty) |
Naprosto odlišný je ovšem význam těchto bitů u instrukce FXAM, která opět (podobně jako FTST) testuje hodnotu uloženou na vrcholu zásobníku. Nyní může nastat sedm kombinací:
| C3 | C2 | C0 | odpovídá stavu |
|---|---|---|---|
| 0 | 0 | 0 | nepodporováno |
| 0 | 0 | 1 | ST(0) obsahuje NaN |
| 0 | 1 | 0 | běžná hodnota (normalizovaná) |
| 0 | 1 | 1 | libovolné nekonečno |
| 1 | 0 | 0 | ST(0) obsahuje nulu |
| 1 | 0 | 1 | prázdný zásobník |
| 1 | 1 | 0 | denormalizovaná hodnota |
8. Třetí demonstrační příklad: instrukce FTST
Vyzkoušejme si nyní chování instrukce FTST, tedy konkrétně to, jaké nastavuje příznakové bity v závislosti na testované hodnotě. Samotný zdrojový kód tohoto demonstračního příkladu je jednoduchý:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldpi ; uložení konstanty Pi na zásobník
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka původní konstanty 1
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fldz
fdiv ; podíl 1/0
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldz
fldz
fdiv ; podíl 0/0
ftst
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
ftst
call print_status_word ; tisk stavového slova
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_status_word:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
print_hex_16 ax ; tisk stavoveho slova v hexadecimalnim formatu
ret
; datova cast
test_word: dw 0
Podívejme se nyní na to, jaké výsledky získáme po spuštění tohoto příkladu a jak je lze vlastně interpretovat:
| Testovaná hodnota | Stavové slovo | C3 | C2 | C0 | Interpretace |
|---|---|---|---|---|---|
| 0.0 | 0×7800 | 1 | 0 | 0 | ST(0) = 0 |
| 1.0 | 0×3800 | 0 | 0 | 0 | ST(0) > 0 |
| π | 0×3800 | 0 | 0 | 0 | ST(0) > 0 |
| –1.0 | 0×3900 | 0 | 0 | 1 | ST(0) < 0 |
| 1/0 | 0×3804 | 0 | 0 | 0 | ST(0) > 0 |
| 0/0 | 0×7D01 | 1 | 1 | 1 | ST(0) ? 0 (neporovnatelné hodnoty) |
| √-1 | 0×7D01 | 1 | 1 | 1 | ST(0) ? 0 (neporovnatelné hodnoty) |
9. Čtvrtý demonstrační příklad: instrukce FXAM
Čtvrtý demonstrační příklad se do jisté míry podobá příkladu předchozímu, protože v něm taktéž testujeme hodnotu uloženou na vrcholu zásobníku. Nyní ovšem pro test hodnoty použijeme namísto instrukce FTST instrukci FXAM, která nastavuje příznakové bity zcela odlišným způsobem dle tabulky uvedené v sedmé kapitole. Nejdříve se podívejme na zdrojový kód tohoto příkladu:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldpi ; uložení konstanty Pi na zásobník
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka původní konstanty 1
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fldz
fdiv ; podíl 1/0
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldz
fldz
fdiv ; podíl 0/0
fxam
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
fxam
call print_status_word ; tisk stavového slova
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_status_word:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
print_hex_16 ax ; tisk stavoveho slova v hexadecimalnim formatu
ret
; datova cast
test_word: dw 0
Podívejme se nyní opět na to, jaké výsledky získáme po spuštění tohoto příkladu a jak je lze vlastně interpretovat:
| Testovaná hodnota | Stavové slovo | C3 | C2 | C1 | C0 | Interpretace |
|---|---|---|---|---|---|---|
| 0.0 | 0×7800 | 1 | 0 | 0 | 0 | ST(0) obsahuje nulu |
| 1.0 | 0×3C00 | 0 | 1 | 0 | 0 | běžná hodnota (normalizovaná) |
| π | 0×3C00 | 0 | 1 | 0 | 0 | běžná hodnota (normalizovaná) |
| –1.0 | 0×3E00 | 0 | 1 | 1 | 0 | běžná záporná hodnota |
| 1/0 | 0×3D04 | 0 | 1 | 0 | 1 | libovolné nekonečno |
| 0/0 | 0×3B01 | 0 | 0 | 1 | 1 | ST(0) obsahuje NaN |
| √-1 | 0×3B01 | 0 | 0 | 1 | 1 | ST(0) obsahuje NaN |
10. Varianty instrukce FCOM pro porovnání dvou operandů
V pořadí již pátém demonstračním příkladu si ukážeme použití jedné varianty instrukce FCOM, která porovná dva operandy (získané ze zásobníku nebo z ST0 a jiného zdroje) a nastaví příslušné příznakové bity. Pokud ovšem využíváme pracovní registry matematického koprocesoru opravdu ve významu zásobníku, budeme mnohdy potřebovat, aby se tato instrukce chovala třemi různými způsoby:
- Oba porovnávané operandy budou na zásobníku ponechány
- Jeden z operandů je odstraněn
- Oba operandy jsou odstraněny (nezajímají nás jiné výsledky, než výsledky relační operace).
Z tohoto důvodu instrukce FCOM existuje ve třech variantách, které postupně odpovídají všem třem očekávaným způsobům chování: FCOM, FCOMP a FCOMPP. Navíc ještě dokáže matematický koprocesor pracovat i s celočíselnými hodnotami, a to včetně jejich porovnání. Proto v instrukčním souboru najdeme i instrukce pro celočíselné porovnávání: FICOM a FICOMP. Později navíc byly přidány varianty pro porovnání operandů, které mohou mít hodnotu QNAN („tiché NaN“, tedy takové hodnoty, které lze předávat do dalších instrukcí, aniž by došlo k signalizaci výjimky).
Na pozdějších variantách matematických koprocesorů (od 80387) tedy máme k dispozici celou řadu funkcí pro porovnání operandů. Tyto funkce ovšem nastavují stejné příznakové bity s jejich totožným významem:
| # | Instrukce | Operandy | Odstranění ze zásobníku | Podpora QNaN | |
|---|---|---|---|---|---|
| 1 | FCOM | s plovoucí čárkou | žádný | ne | |
| 2 | FCOMP | s plovoucí čárkou | jeden | ne | |
| 3 | FCOMPP | s plovoucí čárkou | oba dva | ne | |
| 4 | FUCOM | s plovoucí čárkou | žádný | ano | |
| 5 | FUCOMP | s plovoucí čárkou | jeden | ano | |
| 6 | FUCOMPP | s plovoucí čárkou | oba dva | ano | |
| 7 | FICOM | celočíselný první operand | žádný | ne | |
| 8 | FICOMP | celočíselný první operand | jeden | ne | |
| 9 | FUCOMI | celočíselný první operand | žádný | ano | |
| 10 | FUCOMIP | celočíselný první operand | jeden | ano |
11. Pátý demonstrační příklad: porovnání dvou hodnot instrukcí FCOM(PP)
V dalším demonstračním příkladu si ukážeme použití instrukce FCOM, přesněji řečeno její varianty FCOMPP, která ze zásobníku odstraňuje oba porovnávané operandy. V programu vždy provedeme inicializaci matematického koprocesoru, následně na zásobník uložíme dvě hodnoty, porovnáme je instrukcí FCOMPP a necháme si vypsat stavové slovo koprocesoru. Opět se bude jednat o typické i „zajímavé“ hodnoty:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fldz ; uložení konstanty 0 na zásobník
fdivp ; na zásobník se uloží nekonečno
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich následným odstraněním ze zásobníku
call print_status_word ; tisk stavového slova
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_status_word:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
print_hex_16 ax ; tisk stavoveho slova v hexadecimalnim formatu
ret
; datova cast
test_word: dw 0
Výsledky i jejich interpretace jsou vypsány v tabulce:
| Pravý operand | Levý operand | Stavové slovo | C3 | C2 | C0 | Interpretace |
|---|---|---|---|---|---|---|
| 0 | 0 | 0×4000 | 1 | 0 | 0 | 0 = 0 |
| 1 | 1 | 0×4000 | 1 | 0 | 0 | 0 = 0 |
| 1 | 0 | 0×0100 | 0 | 0 | 1 | 0 < 1 |
| 0 | 1 | 0×0000 | 0 | 0 | 0 | 1 > 0 |
| 1/0 | 1 | 0×0104 | 0 | 0 | 1 | 1 < nekonečno |
| √-1 | 0 | 0×4501 | 1 | 1 | 1 | neporovnatelné hodnoty |
12. Vztah mezi příznakovými bity FPU a CPU
Pokud se podíváte na tabulku s příznakovými bity uloženými ve stavovém slově matematického koprocesoru (čtvrtá kapitola), asi se ptáte, proč jsou vlastně tyto příznakové bity uloženy „zpřeházeně“ s dalšími bitovými poli, které již s příznaky hodnot a operací nesouvisí. Rozmístění těchto příznakových bitů není náhodné, protože souvisí s příznakovým registrem samotného mikroprocesoru. Tento registr se jmenuje FLAGS, má šířku šestnácti bitů a jednotlivé bity mají následující význam:
| Bit | Příznak | Stručný popis příznaku |
|---|---|---|
| 0 | CF | příznak přenosu (carry) |
| 1 | × | rezervováno |
| 2 | PF | příznak (bitové) parity |
| 3 | × | rezervováno |
| 4 | AF | příznak přenosu ze třetího do čtvrtého bitu (auxiliary carry) |
| 5 | × | rezervováno |
| 6 | ZF | příznak nulovosti (zero) |
| 7 | SF | příznak znaménka (sign) |
| 8 | TF | příznak nastavený při krokování |
| 9 | IF | povolení či zákaz reakce na přerušení |
| 10 | DF | směr změny adres při blokových (řetězcových) operacích |
| 11 | OF | příznak přetečení (overflow) |
| 12 | × | na 8086 rezervováno, použito až v 286 |
| 13 | × | na 8086 rezervováno, použito až v 286 |
| 14 | × | na 8086 rezervováno, použito až v 286 |
| 15 | × | na 8086 rezervováno, použito až v 286 |
Ve výše vypsané tabulce jsem schválně oddělil dolních osm bitů a horních osm bitů. Je totiž dobré si uvědomit, že spodní polovina registru FLAGS obsahuje pouze bitové příznaky a horní polovina naopak řídicí bity (a příznak přetečení – důslednost nemůžeme od platformy x86 očekávat). Co to znamená? V případě, že nezasáhneme do horních osmi bitů, nezměníme chování mikroprocesoru (a například zákaz přerušení je velký zásah do toho, jak se mikroprocesor chová). A naopak – modifikace do dolních bitů vlastně ovlivní (velmi zjednodušeně řečeno) jen nejbližší podmíněný skok, protože jakákoli aritmetická nebo logická instrukce hodnoty těchto příznaků stejně přepíše.
13. Mapování mezi stavovými bity matematického koprocesoru a příznakovými bity CPU
Jaká situace nastane ve chvíli, kdy se pokusíme nějakým způsobem přenést horních osm bitů stavového slova matematického koprocesoru do horních osmi bitů příznakového registru FLAGS. To je naznačeno v další tabulce:
| # | FPU SW | FLAGS |
|---|---|---|
| 0 | C0 | CF |
| 1 | C1 | |
| 2 | C2 | PF |
| 3 | ST0 | |
| 4 | ST1 | AF |
| 5 | ST2 | |
| 6 | C3 | ZF |
| 7 | B | SF |
V případě, že vynecháme nepodstatné bity, tedy na straně mikroprocesoru index vrcholu zásobníku a příznak busy a na straně mikroprocesoru neobsazené příznaky, získáme mnohem přehlednější tabulku, která již začíná dávat smysl:
| # | FPU SW | FLAGS |
|---|---|---|
| 0 | C0 | CF |
| 2 | C2 | PF |
| 6 | C3 | ZF |
Toto mapování je z velké části logické, protože například při porovnání hodnot instrukcí FCOM skutečně příznak C3 odpovídá stavu „je rovno“ a u instrukce FTST pak stavu „nulová hodnota“ – a to je vlastně i význam příznaku nulovosti u mikroprocesoru. A příznakový bit C0 mapovaný na CF rozlišuje mezi výsledky „je menší“ a „je větší“. Poslední bit C2 mapovaný na PF slouží pro detekci NaN a s nimi souvisejících problémů.
14. Kopie příznakových bitů FPU do registru FLAGS s následným rozeskokem
To znamená, že pokud dokážeme horních osm bitů příznakového slova matematického koprocesoru přenést do dolních osmi bitů příznakového registru FLAGS (bez modifikace jeho horních osmi bitů!), máme vyhráno. Původní matematický koprocesor Intel 8087 dokázal stavové slovo uložit do paměti (pochopitelně do dvou bajtů). Poté je možné toto slovo načíst do registru AX, popř. načíst jen horních osm bitů slova do registru AH. A následně existuje specializovaná instrukce nazvaná SAHF, která obsah registru AH uloží do spodních osmi bitů příznakového registru – což je přesně to, co vyžadujeme. A posléze již můžeme provést rozeskok na základě příznaků ve FLAGS:
fnstsw word [test_word] ; ulozeni stavoveho slova do paměti mov ax, word [test_word] ; načtení obsahu stavového slova do registru AX sahf ; horních osm bitů se uloží do spodních osmi bitů FLAGS j??? ; provedení rozeskoku na základě nastaveného příznaku či příznaků
15. Zrychlené provedení kopie příznakových bitů matematickým koprocesorem Intel 80287
Matematický koprocesor Intel 80287 přišel s novinkou: instrukcí fnstws ax, která dokázala uložit stavové slovo matematického koprocesoru přímo do registru AX. To na první pohled vypadá jako jednoduché a logické rozšíření instrukčního souboru, ovšem ve skutečnosti to znamenalo citelný zásah do toho, jak vlastně funguje kooperace mezi FPU a CPU. Pokud tato instrukce byla detekována (oběma čipy), převzal řízení FPU, který přes vlastní DMA provedl vlastní přenos a následně řízení předal zpět mikroprocesoru (zcela tedy ovládal řídicí sběrnici). Byla to první snaha o zrychlení a zjednodušení přenosu dat mezi matematickým koprocesorem a mikroprocesorem. V současnosti rozdíl mezi CPU a FPU prakticky zcela zmizel, protože registry mezi těmito dvěma subsystémy jsou sdílené (a navíc význam původního FPU, resp. jeho instrukcí, již není velký, protože máme k dispozici rozšíření instrukčních sad SSEx a AVX-xx, k čemuž se ještě dostaneme).
Ovšem vraťme se k výše zmíněné instrukci fnstsw ax. Tu bylo možné využít takto:
fnstsw ax ; ulozeni stavoveho slova do registru AX fwait ; čekání na dokončení sahf ; horních osm bitů se uloží do spodních osmi bitů FLAGS j??? ; provedení rozeskoku na základě nastaveného příznaku či příznaků
16. Šestý demonstrační příklad: výsledek testu hodnoty uložené na vrcholu zásobníku
Poměrně snadno lze vytvořit kód, který pomocí instrukce FTST otestuje hodnotu uloženou na vrcholu zásobníku a poté příznaky převede do registru FLAGS. Poté je již možné na základě příznaků PF, ZF a CF zjistit typ uložené hodnoty. Nejdříve je nutné testovat PF pro hodnoty NaN a až poté zbylé dva příznaky pro rozeskok do čtyř možných větví:
jnp not_unordered
...
ret
not_unordered:
jnz not_zero
...
ret
not_zero:
jnc positive_value
...
ret
positive_value:
...
ret
Úplný zdrojový kód tohoto demonstračního příkladu vypadá následovně:
; Precteni stavoveho slova matematickeho koprocesoru
; Zapis do registru FLAGS.
; Rozliseni hodnot otestovanych pomoci FTST
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fldpi ; uložení konstanty Pi na zásobník
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka původní konstanty 1
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fld1
fldz
fdiv ; podíl 1/0
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fldz
fldz
fdiv ; podíl 0/0
ftst
call print_test_result ; tisk výsledku testu
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
ftst
call print_test_result ; tisk výsledku testu
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
; | ZF PF CF stav
; | 0 0 0 ST(0) > 0 |
; | 0 0 1 ST(0) < 0 |
; | 1 0 0 ST(0) = 0 |
; | 1 1 1 ST(0) ? 0 (neporovnatelné hodnoty)|
print_test_result:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
sahf ; uložení do příznakového registru
jnp not_unordered
print_string msg_unordered
ret
not_unordered:
jnz not_zero
print_string msg_zero_value
ret
not_zero:
jnc positive_value
print_string msg_negative_value
ret
positive_value:
print_string msg_positive_value
ret
; datova cast
msg_positive_value: db "Positive value", 0x0d, 0x0a, "$"
msg_negative_value: db "Negative value", 0x0d, 0x0a, "$"
msg_zero_value: db "Zero value", 0x0d, 0x0a, "$"
msg_unordered: db "Unordered values!", 0x0d, 0x0a, "$"
test_word: dw 0
Zprávy, které se po spuštění tohoto příkladu vypíšou, jsme doplnil o hodnoty, které se vlastně testovaly:
| Hodnota | Vypsaná zpráva |
|---|---|
| 0 | Zero value |
| 1 | Positive value |
| π | Positive value |
| –1 | Negative value |
| ∞ | Positive value |
| 0/0 | Unordered values! |
| √-1 | Unordered values! |
17. Sedmý demonstrační příklad: plné porovnání dvojice hodnot na zásobníku
Sedmý a současně i dnešní poslední demonstrační příklad používá podobnou techniku jako příklad předchozí. Rozdíl spočívá v tom, že se nyní porovnávají dvě hodnoty uložené na dvou nejvyšších místech zásobníku operandů, poté se příznaky přesunou do registru FLAGS a následně se provede jejich zpracování – rozeskok do čtyř různých větví:
; Precteni stavoveho slova matematickeho koprocesoru
;-----------------------------------------------------------------------------
BITS 16 ; 16bitovy vystup pro DOS
;-----------------------------------------------------------------------------
org 0x100 ; zacatek kodu pro programy typu COM (vzdy se zacina na 256)
start:
jmp main ; skok na zacatek kodu
%include "io.asm" ; nacist symboly, makra a podprogramy
%include "print.asm" ; nacist symboly, makra a podprogramy
main:
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
fninit ; inicializace koprocesoru
fldz ; uložení konstanty 0 na zásobník
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
fninit ; inicializace koprocesoru
fld1 ; uložení konstanty 1 na zásobník
fldz ; uložení konstanty 0 na zásobník
fdivp ; na zásobník se uloží nekonečno
fld1 ; uložení konstanty 1 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
fninit ; inicializace koprocesoru
fld1
fchs ; změna znaménka
fsqrt ; odmocnina z -1
fldz ; uložení konstanty 0 na zásobník
fcompp ; porovnání dvou hodnot s jejich odstraněním ze zásobníku
call print_comparison_results ; tisk výsledku porovnání
wait_key ; cekani na klavesu
exit ; navrat do DOSu
;-----------------------------------------------------------------------------
print_comparison_results:
fnstsw word [test_word] ; ulozeni stavoveho slova
mov ax, word [test_word]
sahf ; uložení do příznakového registru
jnp not_unordered
print_string msg_unordered
ret
not_unordered:
jnz not_equal
print_string msg_equal_values
ret
not_equal:
jnc greater_than
print_string msg_less_than
ret
greater_than:
print_string msg_greater_than
ret
; datova cast
msg_greater_than: db "Greater than", 0x0d, 0x0a, "$"
msg_less_than: db "Less than", 0x0d, 0x0a, "$"
msg_equal_values: db "Equal values", 0x0d, 0x0a, "$"
msg_unordered: db "Unordered values!", 0x0d, 0x0a, "$"
; datova cast
test_word: dw 0
Opět se podívejme na zprávy vypsané tímto příkladem:
| Pravý operand | Levý operand | Vypsaná zpráva |
|---|---|---|
| 0 | 0 | Equal values |
| 1 | 1 | Equal values |
| 1 | 0 | Less than |
| 0 | 1 | Greater than |
| 1/0 | 1 | Less than |
| √-1 | 0 | Unordered values! |
18. Příloha: seznam všech instrukcí matematických koprocesorů řady 80×87
Instrukční soubor matematických koprocesorů se postupně rozšiřoval, takže si vypišme všechny instrukce, které v této řadě postupně vznikly. Některé instrukce (ty nejdůležitější) již známe, další jsou přímým rozšířením existujících (goniometrické funkce) a jiné souvisí spíše s celočíselnými operacemi:
| # | Instrukce | Stručný popis instrukce |
|---|---|---|
| 1 | FADD | součet |
| 2 | FADDP | součet s odstraněním původního operandu |
| 3 | FSUB | rozdíl |
| 4 | FSUBP | rozdíl s odstraněním původního operandu |
| 5 | FSUBR | rozdíl, ale operandy jsou prohozeny |
| 6 | FSUBRP | kombinace FSUBR a FSUBP |
| 7 | FMUL | součin |
| 8 | FMULP | součin s odstraněním původního operandu |
| 9 | FDIV | podíl |
| 10 | FDIVP | podíl s odstraněním původního operandu |
| 11 | FDIVR | podíl, ale operandy jsou prohozeny |
| 12 | FDIVRP | kombinace FDIVR a FDIVP |
| 13 | FIADD | součet celočíselných hodnot |
| 14 | FISUB | rozdíl celočíselných hodnot |
| 15 | FISUBR | rozdíl celočíselných hodnot s prohozenými operandy |
| 16 | FIMUL | součin celočíselných hodnot |
| 17 | FIDIV | podíl celočíselných hodnot |
| 18 | FIDIVR | podíl celočíselných hodnot s prohozenými operandy |
| 19 | FABS | výpočet absolutní hodnoty |
| 20 | FSQRT | výpočet druhé odmocniny |
| 21 | FPREM | výpočet modulo |
| 22 | FPREM1 | výpočet modulo, odlišné výsledky na zásobníku |
| 22 | FPTAN | tangens pro úhel v rozmezí ± π/4 |
| 23 | FPATAN | arkus tangens |
| 24 | FSCALE | násobení či dělení mocninou 2 |
| 25 | F2XM1 | 2x-1 |
| 26 | FYL2X | y log2x |
| 27 | FYL2XP1 | y log2(x+1) |
| 29 | FCOM | porovnání operandů s plovoucí čárkou, na zásobníku jsou oba operandy zachovány |
| 30 | FCOMP | porovnání operandů s plovoucí čárkou, ze zásobníku se odstraní druhý operand |
| 31 | FCOMPP | porovnání operandů s plovoucí čárkou, ze zásobníku se odstraní oba operandy |
| 32 | FUCOM | jako FCOM, ovšem podporuje hodnoty Quiet NaN |
| 33 | FUCOMP | jako FCOMP, ovšem podporuje hodnoty Quiet NaN |
| 34 | FUCOMPP | jako FCOMPP, ovšem podporuje hodnoty Quiet NaN |
| 35 | FICOM | porovnání: první operand je celočíselný, na zásobníku jsou oba operandy zachovány |
| 36 | FICOMP | porovnání: první operand je celočíselný, ze zásobníku se odstraní druhý operand |
| 37 | FUCOMI | porovnání: první operand je celočíselný, podpora Quiet NaN |
| 38 | FUCOMIP | porovnání: první operand je celočíselný, podpora Quiet NaN |
| 39 | FLD | načtení FPU hodnoty z paměti |
| 40 | FLDZ | načtení konstanty 0 |
| 41 | FLD1 | načtení konstanty 1 |
| 42 | FLDPI | načtení konstanty π |
| 43 | FLDL2E | načtení konstanty log2e (e=Eulerovo číslo) |
| 44 | FLDL2T | načtení konstanty log210 |
| 45 | FLDLG2 | načtení konstanty log102 |
| 46 | FLDLN2 | načtení konstanty loge2 |
| 47 | FST | uložení FPU hodnoty do paměti |
| 48 | FSTP | uložení FPU hodnoty + odstranění operandu ze zásobníku |
| 49 | FILD | načtení celočíselné hodnoty z paměti |
| 50 | FIST | uložení celočíselné hodnoty do paměti |
| 51 | FISTP | uložení celočíselné hodnoty do paměti + odstranění operandu ze zásobníku |
| 49 | FLDCW | načtení řídicího slova |
| 50 | FSTCW | uložení řídicího slova (bez čekání) |
| 51 | FNSTCW | uložení řídicího slova |
| 52 | FSTSW | uložení stavového slova |
| 53 | FNSTSW | uložení stavového slova (bez čekání) |
| 54 | FLDENV | načtení 28 bajtů se stavem FPU (bez zásobníku) |
| 55 | FSTENV | uložení 28 bajtů se stavem FPU (bez zásobníku) |
| 56 | FNSTENV | uložení celého prostředí FPU (bez čekání) |
| 57 | FSAVE | uložení celého stavu FPU včetně zásobníku (108 bajtů) |
| 58 | FNSAVE | uložení celého stavu FPU včetně zásobníku (108 bajtů) bez čekání |
| 59 | FRSTOR | obnovení celého stavu FPU |
| 60 | FINCSTP | zvýšení indexu vrcholu zásobníku |
| 61 | FDECSTP | snížení indexu vrcholu zásobníku |
| 61 | FINIT | inicializace matematického koprocesoru |
| 63 | FNINIT | inicializace matematického koprocesoru (bez čekání) |
| 64 | FBLD | načtení BCD hodnoty z paměti |
| 65 | FBSTP | uložení BCD hodnoty do paměti |
| 66 | FCHS | změna znaménka operandu na vrcholu zásobníku |
| 67 | FCLEX | vymazání všech výjimek |
| 68 | FCMOVcc | přenos na základě splněné podmínky |
| 69 | FSIN | výpočet sinu |
| 70) | FCOS | výpočet kosinu |
| 71) | FSINCOS | výpočet sinu i kosinu (užitečné při transformacích) |
| 72) | FFREE | uvolnění zvoleného datového registru |
| 73) | FNCLEX | vymazání všech výjimek (bez čekání) |
| 74 | FNOP | klasická no-op |
| 75 | FRNDINT | zaokrouhlení hodnoty na vrcholu zásobníku |
| 76 | FRNDINT | převod FP hodnoty na celé číslo |
| 77 | FTST | testování obsahu vrcholu zásobníku s nulou |
| 78 | FWAIT | čekání na dokončení operace FPU (typicky vkládáno automaticky assemblerem) |
| 79 | FXAM | prozkoumání hodnoty uložené na vrcholu zásobníku |
| 80 | FXCH | prohození vrcholu zásobníku s jiným registrem |
| 81 | FXTRACT | získání exponentu a mantisy (zjednodušeně řečeno) |
19. Repositář s demonstračními příklady
Demonstrační příklady napsané v assembleru, které jsou určené pro překlad s využitím assembleru NASM, byly uloženy do Git repositáře, který je dostupný na adrese https://github.com/tisnik/8bit-fame. Jednotlivé demonstrační příklady si můžete v případě potřeby stáhnout i jednotlivě bez nutnosti klonovat celý (dnes již poměrně rozsáhlý) repositář:
| # | Příklad | Stručný popis | Adresa |
|---|---|---|---|
| 1 | hello.asm | program typu „Hello world“ naprogramovaný v assembleru pro systém DOS | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hello.asm |
| 2 | hello_shorter.asm | kratší varianta výskoku z procesu zpět do DOSu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hello_shorter.asm |
| 3 | hello_wait.asm | čekání na stisk klávesy | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hello_wait.asm |
| 4 | hello_macros.asm | realizace jednotlivých částí programu makrem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hello_macros.asm |
| 5 | gfx4_putpixel.asm | vykreslení pixelu v grafickém režimu 4 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_putpixel.asm |
| 6 | gfx6_putpixel.asm | vykreslení pixelu v grafickém režimu 6 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel.asm |
| 7 | gfx4_line.asm | vykreslení úsečky v grafickém režimu 4 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_line.asm |
| 8 | gfx6_line.asm | vykreslení úsečky v grafickém režimu 6 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_line.asm |
| 9 | gfx6_fill1.asm | vyplnění obrazovky v grafickém režimu, základní varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_fill1.asm |
| 10 | gfx6_fill2.asm | vyplnění obrazovky v grafickém režimu, varianta s instrukcí LOOP | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_fill2.asm |
| 11 | gfx6_fill3.asm | vyplnění obrazovky instrukcí REP STOSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_fill3.asm |
| 12 | gfx6_fill4.asm | vyplnění obrazovky, synchronizace vykreslování s paprskem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_fill4.asm |
| 13 | gfx4_image1.asm | vykreslení rastrového obrázku získaného z binárních dat, základní varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image1.asm |
| 14 | gfx4_image2.asm | varianta vykreslení rastrového obrázku s využitím instrukce REP MOVSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image2.asm |
| 15 | gfx4_image3.asm | varianta vykreslení rastrového obrázku s využitím instrukce REP MOVSW | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image3.asm |
| 16 | gfx4_image4.asm | korektní vykreslení všech sudých řádků bitmapy | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image4.asm |
| 17 | gfx4_image5.asm | korektní vykreslení všech sudých i lichých řádků bitmapy | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image5.asm |
| 18 | gfx4_image6.asm | nastavení barvové palety před vykreslením obrázku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image6.asm |
| 19 | gfx4_image7.asm | nastavení barvové palety před vykreslením obrázku, snížená intenzita barev | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image7.asm |
| 20 | gfx4_image8.asm | postupná změna barvy pozadí | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx4_image8.asm |
| 21 | gfx6_putpixel1.asm | vykreslení pixelu, základní varianta se 16bitovým násobením | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel1.asm |
| 22 | gfx6_putpixel2.asm | vykreslení pixelu, varianta s osmibitovým násobením | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel2.asm |
| 23 | gfx6_putpixel3.asm | vykreslení pixelu, varianta bez násobení | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel3.asm |
| 24 | gfx6_putpixel4.asm | vykreslení pixelu přes obrázek, nekorektní chování (přepis obrázku) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel4.asm |
| 25 | gfx6_putpixel5.asm | vykreslení pixelu přes obrázek, korektní varianta pro bílé pixely | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/gfx6_putpixel5.asm |
| 26 | cga_text_mode1.asm | standardní textový režim s rozlišením 40×25 znaků | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_mode1.asm |
| 27 | cga_text_mode3.asm | standardní textový režim s rozlišením 80×25 znaků | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_mode3.asm |
| 28 | cga_text_mode_intensity.asm | změna významu nejvyššího bitu atributového bajtu: vyšší intenzita namísto blikání | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_mode_intensity.asm |
| 29 | cga_text_mode_cursor.asm | změna tvaru textového kurzoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_mode_cursor.asm |
| 30 | cga_text_gfx1.asm | zobrazení „rastrové mřížky“: pseudografický režim 160×25 pixelů (interně textový režim) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_gfx1.asm |
| 31 | cga_text_mode_char_height.asm | změna výšky znaků | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_mode_char_height.asm |
| 32 | cga_text_160×100.asm | grafický režim 160×100 se šestnácti barvami (interně upravený textový režim) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/cga_text_160×100.asm |
| 33 | hercules_text_mode1.asm | využití standardního textového režimu společně s kartou Hercules | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_text_mode1.asm |
| 34 | hercules_text_mode2.asm | zákaz blikání v textových režimech | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_text_mode2.asm |
| 35 | hercules_turn_off.asm | vypnutí generování video signálu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_turn_off.asm |
| 36 | hercules_gfx_mode1.asm | přepnutí karty Hercules do grafického režimu (základní varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_gfx_mode1.asm |
| 37 | hercules_gfx_mode2.asm | přepnutí karty Hercules do grafického režimu (vylepšená varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_gfx_mode2.asm |
| 38 | hercules_putpixel.asm | subrutina pro vykreslení jediného pixelu na kartě Hercules | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/hercules_putpixel.asm |
| 39 | ega_text_mode_80×25.asm | standardní textový režim 80×25 znaků na kartě EGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_text_mode_80×25.asm |
| 40 | ega_text_mode_80×43.asm | zobrazení 43 textových řádků na kartě EGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_text_mode_80×43.asm |
| 41 | ega_gfx_mode_320×200.asm | přepnutí do grafického režimu 320×200 pixelů se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_gfx_mode_320×200.asm |
| 42 | ega_gfx_mode_640×200.asm | přepnutí do grafického režimu 640×200 pixelů se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_gfx_mode_640×200.asm |
| 43 | ega_gfx_mode_640×350.asm | přepnutí do grafického režimu 640×350 pixelů se čtyřmi nebo šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_gfx_mode_640×350.asm |
| 44 | ega_gfx_mode_bitplanes1.asm | ovládání zápisu do bitových rovin v planárních grafických režimech (základní způsob) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_gfx_mode_bitplanes1.asm |
| 45 | ega_gfx_mode_bitplanes2.asm | ovládání zápisu do bitových rovin v planárních grafických režimech (rychlejší způsob) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_gfx_mode_bitplanes2.asm |
| 46 | ega_320×200_putpixel.asm | vykreslení pixelu v grafickém režimu 320×200 pixelů se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_320×200_putpixel.asm |
| 47 | ega_640×350_putpixel.asm | vykreslení pixelu v grafickém režimu 640×350 pixelů se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_640×350_putpixel.asm |
| 48 | ega_standard_font.asm | použití standardního fontu grafické karty EGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_standard_font.asm |
| 49 | ega_custom_font.asm | načtení vlastního fontu s jeho zobrazením | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_custom_font.asm |
| 50 | ega_palette1.asm | změna barvové palety (všech 16 barev) v grafickém režimu 320×200 se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_palette1.asm |
| 51 | ega_palette2.asm | změna barvové palety (všech 16 barev) v grafickém režimu 640×350 se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_palette2.asm |
| 52 | ega_palette3.asm | změna všech barev v barvové paletě s využitím programové smyčky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_palette3.asm |
| 53 | ega_palette4.asm | změna všech barev, včetně barvy okraje, v barvové paletě voláním funkce BIOSu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ega_palette4.asm |
| 54 | vga_text_mode_80×25.asm | standardní textový režim 80×25 znaků na kartě VGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_80×25.asm |
| 55 | vga_text_mode_80×50.asm | zobrazení 50 a taktéž 28 textových řádků na kartě VGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_80×50.asm |
| 56 | vga_text_mode_intensity1.asm | změna chování atributového bitu pro blikání (nebezpečná varianta změny registrů) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_intensity1.asm |
| 57 | vga_text_mode_intensity2.asm | změna chování atributového bitu pro blikání (bezpečnější varianta změny registrů) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_intensity2.asm |
| 58 | vga_text_mode_9th_column.asm | modifikace způsobu zobrazení devátého sloupce ve znakových režimech (720 pixelů na řádku) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_9th_column.asm |
| 59 | vga_text_mode_cursor_shape.asm | změna tvaru textového kurzoru na grafické kartě VGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_cursor_shape.asm |
| 60 | vga_text_mode_custom_font.asm | načtení vlastního fontu s jeho zobrazením | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_text_mode_custom_font.asm |
| 61 | vga_gfx_mode_640×480.asm | přepnutí do grafického režimu 640×480 pixelů se šestnácti barvami, vykreslení vzorků | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_640×480.asm |
| 62 | vga_gfx_mode_320×200.asm | přepnutí do grafického režimu 320×200 pixelů s 256 barvami, vykreslení vzorků | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_320×200.asm |
| 63 | vga_gfx_mode_palette.asm | změna všech barev v barvové paletě grafické karty VGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_palette.asm |
| 64 | vga_gfx_mode_dac1.asm | využití DAC (neočekávané výsledky) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_dac1.asm |
| 65 | vga_gfx_mode_dac2.asm | využití DAC (očekávané výsledky) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_dac2.asm |
| 66 | vga_640×480_putpixel.asm | realizace algoritmu pro vykreslení pixelu v grafickém režimu 640×480 pixelů se šestnácti barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_640×480_putpixel.asm |
| 67 | vga_320×200_putpixel1.asm | realizace algoritmu pro vykreslení pixelu v grafickém režimu 320×200 s 256 barvami (základní varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_putpixel1.asm |
| 68 | vga_320×200_putpixel2.asm | realizace algoritmu pro vykreslení pixelu v grafickém režimu 320×200 s 256 barvami (rychlejší varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_putpixel2.asm |
| 69 | vga_gfx_mode_dac3.asm | přímé využití DAC v grafickém režimu 13h | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_dac3.asm |
| 70 | vga_gfx_mode_unchained_step1.asm | zobrazení barevných pruhů v režimu 13h | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_unchained_step1.asm |
| 71 | vga_gfx_mode_unchained_step2.asm | vypnutí zřetězení bitových rovin a změna způsobu adresování pixelů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_unchained_step2.asm |
| 72 | vga_gfx_mode_unchained_step3.asm | vykreslení barevných pruhů do vybraných bitových rovin | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_unchained_step3.asm |
| 73 | vga_gfx_mode_320×400.asm | nestandardní grafický režim s rozlišením 320×400 pixelů a 256 barvami | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_gfx_mode_320×400.asm |
| 74 | vga_320×200_image.asm | zobrazení rastrového obrázku ve standardním grafickém režimu 320×200 pixelů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image.asm |
| 75 | vga_320×200_unchained_image1.asm | zobrazení rastrového obrázku v režimu s nezřetězenými rovinami (nekorektní řešení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_unchained_image1.asm |
| 76 | vga_320×200_unchained_image2.asm | zobrazení rastrového obrázku v režimu s nezřetězenými rovinami (korektní řešení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_unchained_image2.asm |
| 77 | vga_320×400_unchained_image.asm | zobrazení rastrového obrázku v nestandardním režimu 320×400 pixelů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×400_unchained_image.asm |
| 78 | vga_vertical_scroll1.asm | vertikální scrolling na kartě VGA v režimu s rozlišením 320×200 pixelů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_vertical_scroll1.asm |
| 79 | vga_vertical_scroll2.asm | vertikální scrolling na kartě VGA v režimu s rozlišením 320×400 pixelů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_vertical_scroll2.asm |
| 80 | vga_split_screen1.asm | režim split-screen a scrolling, nefunční varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_split_screen1.asm |
| 81 | vga_split_screen2.asm | režim split-screen a scrolling, plně funkční varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_split_screen2.asm |
| 82 | vga_horizontal_scroll1.asm | horizontální scrolling bez rozšíření počtu pixelů na virtuálním řádku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_horizontal_scroll1.asm |
| 83 | vga_horizontal_scroll2.asm | horizontální scrolling s rozšířením počtu pixelů na virtuálním řádku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_horizontal_scroll2.asm |
| 84 | vga_horizontal_scroll3.asm | jemný horizontální scrolling s rozšířením počtu pixelů na virtuálním řádku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_horizontal_scroll3.asm |
| 85 | vga_320×240_image.asm | nastavení grafického režimu Mode-X, načtení a vykreslení obrázku, scrolling | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×240_image.asm |
| 86 | io.asm | knihovna maker pro I/O operace | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/io.asm |
| 87 | vga_lib.asm | knihovna maker a podprogramů pro programování karty VGA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_lib.asm |
| 88 | vga_320×240_lib.asm | nastavení grafického režimu Mode-X, tentokrát knihovními funkcemi | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×240_lib.asm |
| 89 | vga_bitblt1.asm | první (naivní) implementace operace BitBLT | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt1.asm |
| 90 | vga_bitblt2.asm | operace BitBLT s výběrem bitových rovin pro zápis | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt2.asm |
| 91 | vga_bitblt3.asm | operace BitBLT s výběrem bitových rovin pro čtení i zápis | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt3.asm |
| 92 | vga_bitblt4.asm | korektní BitBLT pro 16barevný režim, realizace makry | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt4.asm |
| 93 | vga_bitblt5.asm | korektní BitBLT pro 16barevný režim, realizace podprogramem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt5.asm |
| 94 | vga_bitblt_rotate.asm | zápisový režim s rotací bajtu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt_rotate.asm |
| 95 | vga_bitblt_fast.asm | rychlá korektní 32bitová operace typu BitBLT | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_bitblt_fast.asm |
| 96 | vga_320×400_bitblt1.asm | přenos obrázku v režimu 320×400 operací BitBLT (neúplná varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×400_bitblt1.asm |
| 97 | vga_320×400_bitblt2.asm | přenos obrázku v režimu 320×400 operací BitBLT (úplná varianta) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×400_bitblt2.asm |
| 98 | vga_write_modes1.asm | volitelné zápisové režimy grafické karty VGA, zápis bez úpravy latche | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_write_modes1.asm |
| 99 | vga_write_modes2.asm | volitelné zápisové režimy grafické karty VGA, zápis s modifikací latche | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_write_modes2.asm |
| 100 | vga_write_modes3.asm | volitelné zápisové režimy grafické karty VGA, cílená modifikace latche vzorkem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_write_modes3.asm |
| 101 | instruction_jump.asm | použití instrukce JMP | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_jump.asm |
| 102 | instruction_jnz.asm | použití instrukce JNZ pro realizaci programové smyčky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_jnz.asm |
| 103 | instruction_jz_jmp.asm | použití instrukcí JZ a JMP pro realizaci programové smyčky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_jz_jmp.asm |
| 104 | instruction_loop.asm | použití instrukce LOOP pro realizaci programové smyčky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_loop.asm |
| 105 | instruction_template.asm | šablona všech následujících demonstračních příkladů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_template.asm |
| 106 | instruction_print_hex.asm | tisk osmibitové hexadecimální hodnoty | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_print_hex.asm |
| 107 | instruction_xlat.asm | využití instrukce XLAT pro získání tisknutelné hexadecimální cifry | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_xlat.asm |
| 108 | instruction_daa.asm | operace součtu s využitím binární i BCD aritmetiky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_daa.asm |
| 109 | instruction_daa_sub.asm | instrukce DAA po provedení operace rozdílu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_daa_sub.asm |
| 110 | instruction_das.asm | instrukce DAS po provedení operace rozdílu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_das.asm |
| 111 | instruction_aaa.asm | korekce výsledku na jedinou BCD cifru operací AAA | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_aaa.asm |
| 112 | instruction_mul.asm | ukázka výpočtu součinu dvou osmibitových hodnot | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_mul.asm |
| 113 | instruction_aam.asm | BCD korekce po výpočtu součinu instrukcí AAM | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_aam.asm |
| 114 | instruction_stosb.asm | blokový zápis dat instrukcí STOSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_stosb.asm |
| 115 | instruction_rep_stosb.asm | opakované provádění instrukce STOSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_rep_stosb.asm |
| 116 | instruction_lodsb.asm | čtení dat instrukcí LODSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_lodsb.asm |
| 117 | instruction_movsb.asm | přenos jednoho bajtu instrukcí MOVSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_movsb.asm |
| 118 | instruction_rep_movsb.asm | blokový přenos po bajtech instrukcí MOVSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_rep_movsb.asm |
| 119 | instruction_rep_scas.asm | vyhledávání v řetězci instrukcí SCAS | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_rep_scas.asm |
| 120 | vga_320×200_image_0B.asm | výsledek blokového přenosu ve chvíli, kdy je CX=0 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_0B.asm |
| 121 | vga_320×200_image_64kB.asm | výsledek blokového přenosu ve chvíli, kdy je CX=0×ffff | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_64kB.asm |
| 122 | vga_320×200_image_movsb.asm | blokový přenos v rámci obrazové paměti instrukcí REP MOVSB | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsb.asm |
| 123 | vga_320×200_image_movsw.asm | blokový přenos v rámci obrazové paměti instrukcí REP MOVSW | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsw.asm |
| 124 | vga_320×200_image_movsd.asm | blokový přenos v rámci obrazové paměti instrukcí REP MOVSD | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsd.asm |
| 125 | vga_320×200_image_movsb_forward.asm | blokový přenos překrývajících se bloků paměti (zvyšující se adresy) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsb_forward.asm |
| 126 | vga_320×200_image_movsb_backward1.asm | blokový přenos překrývajících se bloků paměti (snižující se adresy, nekorektní nastavení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsb_backward1.asm |
| 127 | vga_320×200_image_movsb_backward2.asm | blokový přenos překrývajících se bloků paměti (snižující se adresy, korektní nastavení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_image_movsb_backward2.asm |
| 128 | sound_bell.asm | přehrání zvuku pomocí tisku ASCII znaku BELL | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_bell.asm |
| 129 | sound_beep.asm | přehrání zvuku o zadané frekvenci na PC Speakeru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_beep.asm |
| 130 | sound_play_pitch.asm | přehrání zvuku o zadané frekvenci na PC Speakeru, použití maker | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_play_pitch.asm |
| 131 | sound_opl2_basic.asm | přehrání komorního A na OPL2 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl2_basic.asm |
| 132 | sound_opl2_table.asm | přehrání komorního A na OPL2, použití tabulky s hodnotami registrů | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl2_table.asm |
| 133 | sound_opl2_table2.asm | přepis tabulky s obsahy registrů pro přehrání komorního A | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl2_table2.asm |
| 134 | sound_key_on.asm | přímé ovládání bitu KEY ON mezerníkem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_key_on.asm |
| 135 | sound_adsr.asm | nastavení obálky pro tón přehrávaný prvním kanálem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_adsr.asm |
| 136 | sound_modulation.asm | řízení frekvence modulátoru klávesami 1 a 0 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_modulation.asm |
| 137 | keyboard_basic.asm | přímá práce s klávesnicí IBM PC | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/keyboard_basic.asm |
| 138 | sound_stereo_opl2.asm | stereo zvuk v konfiguraci DualOPL2 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_stereo_opl2.asm |
| 139 | sound_opl2_multichannel.asm | vícekanálový zvuk na OPL2 (klávesy), delší varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl2_multichannel.asm |
| 140 | sound_opl2_multichannel2.asm | vícekanálový zvuk na OPL2 (klávesy), kratší varianta | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl2_multichannel2.asm |
| 141 | sound_opl3_stereo1.asm | stereo výstup na OPL3 (v kompatibilním režimu) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_stereo1.asm |
| 142 | sound_opl3_stereo2.asm | stereo výstup na OPL3 (v režimu OPL3) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_stereo2.asm |
| 143 | sound_opl3_multichannel.asm | vícekanálový zvuk na OPL3 (klávesy) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_multichannel.asm |
| 144 | sound_opl3_waveform1.asm | interaktivní modifikace tvaru vlny u prvního operátoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_waveform1.asm |
| 145 | sound_opl3_waveform2.asm | oprava chyby: povolení režimu kompatibilního s OPL3 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_waveform2.asm |
| 146 | sound_opl3_waveform3.asm | vliv tvaru vln na zvukový kanál s FM syntézou | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_waveform3.asm |
| 147 | sound_opl3_waveform4.asm | modifikace tvaru vlny nosné vlny i modulátoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_waveform4.asm |
| 148 | sound_opl3_4operators1.asm | výběr AM/FM režimu ve čtyřoperátorovém nastavení | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_4operators1.asm |
| 149 | sound_opl3_4operators2.asm | výběr AM/FM režimu ve čtyřoperátorovém nastavení | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/sound_opl3_4operators2.asm |
| 150 | timer_basic.asm | základní obsluha přerušení od časovače/čítače | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/timer_basic.asm |
| 151 | timer_restore.asm | obnovení původní obsluhy přerušení při ukončování aplikace | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/timer_restore.asm |
| 152 | timer_restore_better_structure.asm | refaktoring předchozího demonstračního příkladu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/timer_restore_better_structure.asm |
| 153 | timer_faster_clock.asm | zrychlení čítače na 100 přerušení za sekundu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/timer_faster_clock.asm |
| 154 | instruction_push_imm.asm | instrukce PUSH s konstantou | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_push_imm.asm |
| 155 | instruction_imul_imm.asm | instrukce IMUL s konstantou | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_imul_imm.asm |
| 156 | instruction_into1.asm | instrukce INTO s obsluhou přerušení | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_into1.asm |
| 157 | instruction_into2.asm | instrukce INTO s obsluhou přerušení | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_into2.asm |
| 158 | instruction_bound1.asm | instrukce BOUND s obsluhou přerušení (nekorektní řešení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_bound1.asm |
| 159 | instruction_bound2.asm | instrukce BOUND s obsluhou přerušení (korektní řešení) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_bound2.asm |
| 160 | vga_320×200_putpixel286.asm | instrukce bitového posunu s konstantou větší než 1 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_putpixel286.asm |
| 161 | instruction_push_pop.asm | instrukce PUSH a POP se všemi pracovními registry | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_push_pop.asm |
| 162 | instruction_push_pop_B.asm | instrukce s novými segmentovými registry | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_push_pop_B.asm |
| 163 | instruction_near_jz_jmp.asm | blízké skoky | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_near_jz_jmp.asm |
| 164 | instruction_bsf.asm | nová instrukce BSF | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_bsf.asm |
| 165 | instruction_bsr.asm | nová instrukce BSR | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_bsr.asm |
| 166 | instruction_add_32bit.asm | 32bitový součet | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_add_32bit.asm |
| 167 | instruction_inc_32bit.asm | 32bitová instrukce INC v šestnáctibitovém režimu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_inc_32bit.asm |
| 168 | instruction_inc_32bit_B.asm | 32bitová instrukce INC v 32bitovém režimu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/instruction_inc_32bit_B.asm |
| 169 | ems_status.asm | zjištění stavu (emulace) paměti EMS | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ems_status.asm |
| 170 | ems_total_mem.asm | získání celkové kapacity paměti EMS v blocích | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ems_total_mem.asm |
| 171 | ems_free_mem.asm | získání volné kapacity paměti EMS v blocích | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/ems_free_mem.asm |
| 172 | xms_free_mem.asm | získání volné kapacity paměti XMS v blocích | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/xms_free_mem.asm |
| 173 | vga_320×200_short_address1.asm | blokový přenos provedený v rámci prostoru segmentu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_short_address1.asm |
| 174 | vga_320×200_short_address2.asm | rozepsaný blokový přenos provedený v rámci prostoru segmentu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_short_address2.asm |
| 175 | vga_320×200_short_address3.asm | přenos nelze provést přes hranici offsetu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_short_address3.asm |
| 176 | vga_320×200_short_address4.asm | přenos nelze provést přes hranici offsetu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_short_address4.asm |
| 177 | vga_320×200_long_address1.asm | 32bitový blokový přenos | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_long_address1.asm |
| 178 | vga_320×200_long_address2.asm | rozepsaný 32bitový blokový přenos provedený v rámci prostoru segmentu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_long_address2.asm |
| 179 | vga_320×200_long_address3.asm | přístup do obrazové paměti přes segment 0×0000 a 32bitový offset | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_long_address3.asm |
| 180 | vga_320×200_long_address4.asm | otestování, jak lze přenášet data s využitím 32bitového offsetu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/vga_320×200_long_address4.asm |
| 181 | print_msw.asm | přečtení a zobrazení obsahu speciálního registru MSW | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/print_msw.asm |
| 182 | print_cr0.asm | přečtení a zobrazení obsahu speciálního registru CR0 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/print_cr0.asm |
| 183 | prot_mode286.asm | přechod do chráněného režimu na čipech Intel 80286 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/prot_mode286.asm |
| 184 | prot_mode386.asm | přechod do chráněného režimu na čipech Intel 80386 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/prot_mode386.asm |
| 185 | prot_mode_back_to_real_mode286.asm | přechod mezi reálným režimem a chráněným režimem i zpět na čipech Intel 80286 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/prot_mode_back_to_real_mode286.asm |
| 186 | prot_mode_back_to_real_mode386.asm | přechod mezi reálným režimem a chráněným režimem i zpět na čipech Intel 80386 | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/prot_mode_back_to_real_mode386.asm |
| 187 | prot_mode_check.asm | test, zda se mikroprocesor již nachází v chráněném režimu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/prot_mode_check.asm |
| 188 | unreal_mode.asm | nastavení nereálného režimu (platné pro Intel 80386) | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/unreal_mode.asm |
| 189 | float32_constants.asm | vytištění základních FP konstant typu single | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/float32_constants.asm |
| 190 | float64_constants.asm | vytištění základních FP konstant typu double | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/float64_constants.asm |
| 191 | fpu_arithmetic.asm | základní aritmetické operace prováděné matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_arithmetic.asm |
| 192 | fpu_divide_by_zero.asm | dělení nulou matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide_by_zero.asm |
| 193 | fpu_divide_by_neg_zero.asm | dělení záporné hodnoty nulou matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide_by_neg_zero.asm |
| 194 | fpu_divide_by_neg_zero2.asm | dělení hodnoty zápornou nulou matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide_by_neg_zero2.asm |
| 195 | fpu_divide_zero_by_zero.asm | výpočet 0/0 matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide_zero_by_zero.asm |
| 196 | io.asm | pomocná makra pro komunikaci s DOSem a BIOSem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/io.asm |
| 197 | print.asm | pomocná makra pro tisk FPU hodnot typu single a double v hexadecimálním tvaru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/print.asm |
| 198 | fpu_divide.asm | operace podílu | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide.asm |
| 199 | fpu_divide_r.asm | operace podílu s prohozenými operandy | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_divide_r.asm |
| 200 | fpu_sqrt.asm | výpočet druhé odmocniny | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_sqrt.asm |
| 201 | fpu_sqrt_neg_value.asm | výpočet druhé odmocniny ze záporné hodnoty | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_sqrt_neg_value.asm |
| 202 | fpu_check.asm | detekce typu matematického koprocesoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_check.asm |
| 203 | fpu_compare.asm | porovnání dvou hodnot s vyhodnocením výsledku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_compare.asm |
| 204 | fpu_status_word.asm | tisk obsahu stavového slova koprocesoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_status_word.asm |
| 205 | fpu_status_word_stack.asm | tisk obsahu stavového slova koprocesoru | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_status_word_stack.asm |
| 206 | fpu_exceptions_IE_ZO.asm | detekce výjimek IE a ZE matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_exceptions_IE_ZO.asm |
| 207 | fpu_exceptions_OE.asm | detekce výjimky OE matematickým koprocesorem | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_exceptions_OE.asm |
| 208 | fpu_fxam.asm | analýza hodnoty na vrcholu zásobníku instrukcí FXAM | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_fxam.asm |
| 209 | fpu_ftst.asm | analýza hodnoty na vrcholu zásobníku instrukcí FTST | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_ftst.asm |
| 210 | fpu_fcompp.asm | porovnání dvou hodnot instrukcí FCOMPP | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_fcompp.asm |
| 211 | fpu_test.asm | test hodnoty uložené na vrcholu zásobníku | https://github.com/tisnik/8bit-fame/blob/master/pc-dos/fpu_test.asm |
20. Odkazy na Internetu
- The Intel 8088 Architecture and Instruction Set
https://people.ece.ubc.ca/~edc/464/lectures/lec4.pdf - x86 Opcode Structure and Instruction Overview
https://pnx.tf/files/x86_opcode_structure_and_instruction_overview.pdf - x86 instruction listings (Wikipedia)
https://en.wikipedia.org/wiki/X86_instruction_listings - x86 assembly language (Wikipedia)
https://en.wikipedia.org/wiki/X86_assembly_language - Intel Assembler (Cheat sheet)
http://www.jegerlehner.ch/intel/IntelCodeTable.pdf - 25 Microchips That Shook the World
https://spectrum.ieee.org/tech-history/silicon-revolution/25-microchips-that-shook-the-world - Chip Hall of Fame: MOS Technology 6502 Microprocessor
https://spectrum.ieee.org/tech-history/silicon-revolution/chip-hall-of-fame-mos-technology-6502-microprocessor - Chip Hall of Fame: Intel 8088 Microprocessor
https://spectrum.ieee.org/tech-history/silicon-revolution/chip-hall-of-fame-intel-8088-microprocessor - Jak se zrodil procesor?
https://www.root.cz/clanky/jak-se-zrodil-procesor/ - Apple II History Home
http://apple2history.org/ - The 8086/8088 Primer
https://www.stevemorse.org/8086/index.html - flat assembler: Assembly language resources
https://flatassembler.net/ - FASM na Wikipedii
https://en.wikipedia.org/wiki/FASM - Fresh IDE FASM inside
https://fresh.flatassembler.net/ - MS-DOS Version 4.0 Programmer's Reference
https://www.pcjs.org/documents/books/mspl13/msdos/dosref40/ - DOS API (Wikipedia)
https://en.wikipedia.org/wiki/DOS_API - Bit banging
https://en.wikipedia.org/wiki/Bit_banging - IBM Basic assembly language and successors (Wikipedia)
https://en.wikipedia.org/wiki/IBM_Basic_assembly_language_and_successors - X86 Assembly/Bootloaders
https://en.wikibooks.org/wiki/X86_Assembly/Bootloaders - Počátky grafiky na PC: grafické karty CGA a Hercules
https://www.root.cz/clanky/pocatky-grafiky-na-pc-graficke-karty-cga-a-hercules/ - Co mají společného Commodore PET/4000, BBC Micro, Amstrad CPC i grafické karty MDA, CGA a Hercules?
https://www.root.cz/clanky/co-maji-spolecneho-commodore-pet-4000-bbc-micro-amstrad-cpc-i-graficke-karty-mda-cga-a-hercules/ - Karta EGA: první použitelná barevná grafika na PC
https://www.root.cz/clanky/karta-ega-prvni-pouzitelna-barevna-grafika-na-pc/ - RGB Classic Games
https://www.classicdosgames.com/ - Turbo Assembler (Wikipedia)
https://en.wikipedia.org/wiki/Turbo_Assembler - Microsoft Macro Assembler
https://en.wikipedia.org/wiki/Microsoft_Macro_Assembler - IBM Personal Computer (Wikipedia)
https://en.wikipedia.org/wiki/IBM_Personal_Computer - Intel 8251
https://en.wikipedia.org/wiki/Intel_8251 - Intel 8253
https://en.wikipedia.org/wiki/Intel_8253 - Intel 8255
https://en.wikipedia.org/wiki/Intel_8255 - Intel 8257
https://en.wikipedia.org/wiki/Intel_8257 - Intel 8259
https://en.wikipedia.org/wiki/Intel_8259 - Support/peripheral/other chips – 6800 family
http://www.cpu-world.com/Support/6800.html - Motorola 6845
http://en.wikipedia.org/wiki/Motorola_6845 - The 6845 Cathode Ray Tube Controller (CRTC)
http://www.tinyvga.com/6845 - CRTC operation
http://www.6502.org/users/andre/hwinfo/crtc/crtc.html - The 6845 Cathode Ray Tube Controller (CRTC)
http://www.tinyvga.com/6845 - Motorola 6845 and bitwise graphics
https://retrocomputing.stackexchange.com/questions/10996/motorola-6845-and-bitwise-graphics - IBM Monochrome Display Adapter
http://en.wikipedia.org/wiki/Monochrome_Display_Adapter - Color Graphics Adapter
http://en.wikipedia.org/wiki/Color_Graphics_Adapter - Color Graphics Adapter and the Brown color in IBM 5153 Color Display
https://www.aceinnova.com/en/electronics/cga-and-the-brown-color-in-ibm-5153-color-display/ - The Modern Retrocomputer: An Arduino Driven 6845 CRT Controller
https://hackaday.com/2017/05/14/the-modern-retrocomputer-an-arduino-driven-6845-crt-controller/ - flat assembler: Assembly language resources
https://flatassembler.net/ - FASM na Wikipedii
https://en.wikipedia.org/wiki/FASM - Fresh IDE FASM inside
https://fresh.flatassembler.net/ - MS-DOS Version 4.0 Programmer's Reference
https://www.pcjs.org/documents/books/mspl13/msdos/dosref40/ - DOS API (Wikipedia)
https://en.wikipedia.org/wiki/DOS_API - IBM Basic assembly language and successors (Wikipedia)
https://en.wikipedia.org/wiki/IBM_Basic_assembly_language_and_successors - X86 Assembly/Arithmetic
https://en.wikibooks.org/wiki/X86_Assembly/Arithmetic - Art of Assembly – Arithmetic Instructions
http://oopweb.com/Assembly/Documents/ArtOfAssembly/Volume/Chapter6/CH06–2.html - ASM Flags
http://www.cavestory.org/guides/csasm/guide/asm_flags.html - Status Register
https://en.wikipedia.org/wiki/Status_register - Linux assemblers: A comparison of GAS and NASM
http://www.ibm.com/developerworks/library/l-gas-nasm/index.html - Programovani v assembleru na OS Linux
http://www.cs.vsb.cz/grygarek/asm/asmlinux.html - Is it worthwhile to learn x86 assembly language today?
https://www.quora.com/Is-it-worthwhile-to-learn-x86-assembly-language-today?share=1 - Why Learn Assembly Language?
http://www.codeproject.com/Articles/89460/Why-Learn-Assembly-Language - Is Assembly still relevant?
http://programmers.stackexchange.com/questions/95836/is-assembly-still-relevant - Why Learning Assembly Language Is Still a Good Idea
http://www.onlamp.com/pub/a/onlamp/2004/05/06/writegreatcode.html - Assembly language today
http://beust.com/weblog/2004/06/23/assembly-language-today/ - Assembler: Význam assembleru dnes
http://www.builder.cz/rubriky/assembler/vyznam-assembleru-dnes-155960cz - Programming from the Ground Up Book – Summary
http://savannah.nongnu.org/projects/pgubook/ - DOSBox
https://www.dosbox.com/ - The C Programming Language
https://en.wikipedia.org/wiki/The_C_Programming_Language - Hercules Graphics Card (HCG)
https://en.wikipedia.org/wiki/Hercules_Graphics_Card - Complete 8086 instruction set
https://content.ctcd.edu/courses/cosc2325/m22/docs/emu8086ins.pdf - Complete 8086 instruction set
https://yassinebridi.github.io/asm-docs/8086_instruction_set.html - 8088 MPH by Hornet + CRTC + DESiRE (final version)
https://www.youtube.com/watch?v=hNRO7lno_DM - Area 5150 by CRTC & Hornet (Party Version) / IBM PC+CGA Demo, Hardware Capture
https://www.youtube.com/watch?v=fWDxdoRTZPc - 80×86 Integer Instruction Set Timings (8088 – Pentium)
http://aturing.umcs.maine.edu/~meadow/courses/cos335/80×86-Integer-Instruction-Set-Clocks.pdf - Colour Graphics Adapter: Notes
https://www.seasip.info/VintagePC/cga.html - Restoring A Vintage CGA Card With Homebrew HASL
https://hackaday.com/2024/06/12/restoring-a-vintage-cga-card-with-homebrew-hasl/ - Demoing An 8088
https://hackaday.com/2015/04/10/demoing-an-8088/ - Video Memory Layouts
http://www.techhelpmanual.com/89-video_memory_layouts.html - Screen Attributes
http://www.techhelpmanual.com/87-screen_attributes.html - IBM PC Family – BIOS Video Modes
https://www.minuszerodegrees.net/video/bios_video_modes.htm - EGA Functions
https://cosmodoc.org/topics/ega-functions/#the-hierarchy-of-the-ega - Why the EGA can only use 16 of its 64 colours in 200-line modes
https://www.reenigne.org/blog/why-the-ega-can-only-use-16-of-its-64-colours-in-200-line-modes/ - How 16 colors saved PC gaming – the story of EGA graphics
https://www.custompc.com/retro-tech/ega-graphics - List of 16-bit computer color palettes
https://en.wikipedia.org/wiki/List_of16-bit_computer_color_palettes - Why were those colors chosen to be the default palette for 256-color VGA?
https://retrocomputing.stackexchange.com/questions/27994/why-were-those-colors-chosen-to-be-the-default-palette-for-256-color-vga - VGA Color Palettes
https://www.fountainware.com/EXPL/vga_color_palettes.htm - Hardware Level VGA and SVGA Video Programming Information Page
http://www.osdever.net/FreeVGA/vga/vga.htm - Hardware Level VGA and SVGA Video Programming Information Page – sequencer
http://www.osdever.net/FreeVGA/vga/seqreg.htm - VGA Basics
http://www.brackeen.com/vga/basics.html - Introduction to VGA Mode ‚X‘
https://web.archive.org/web/20160414072210/http://fly.srk.fer.hr/GDM/articles/vgamodex/vgamx1.html - VGA Mode-X
https://web.archive.org/web/20070123192523/http://www.gamedev.net/reference/articles/article356.asp - Mode-X: 256-Color VGA Magic
https://downloads.gamedev.net/pdf/gpbb/gpbb47.pdf - Instruction Format in 8086 Microprocessor
https://www.includehelp.com/embedded-system/instruction-format-in-8086-microprocessor.aspx - How to use „AND,“ „OR,“ and „XOR“ modes for VGA Drawing
https://retrocomputing.stackexchange.com/questions/21936/how-to-use-and-or-and-xor-modes-for-vga-drawing - VGA Hardware
https://wiki.osdev.org/VGA_Hardware - Programmer's Guide to Yamaha YMF 262/OPL3 FM Music Synthesizer
https://moddingwiki.shikadi.net/wiki/OPL_chip - Does anybody understand how OPL2 percussion mode works?
https://forum.vcfed.org/index.php?threads/does-anybody-understand-how-opl2-percussion-mode-works.60925/ - Yamaha YMF262 OPL3 music – MoonDriver for OPL3 DEMO [Oscilloscope View]
https://www.youtube.com/watch?v=a7I-QmrkAak - Yamaha OPL vs OPL2 vs OPL3 comparison
https://www.youtube.com/watch?v=5knetge5Gs0 - OPL3 Music Crockett's Theme
https://www.youtube.com/watch?v=HXS008pkgSQ - Bad Apple (Adlib Tracker – OPL3)
https://www.youtube.com/watch?v=2lEPH6Y3Luo - FM Synthesis Chips, Codecs and DACs
https://www.dosdays.co.uk/topics/fm_synthesizers.php - The Zen Challenge – YMF262 OPL3 Original (For an upcoming game)
https://www.youtube.com/watch?v=6JlFIFz1CFY - [adlib tracker II techno music – opl3] orbit around alpha andromedae I
https://www.youtube.com/watch?v=YqxJCu_WFuA - [adlib tracker 2 music – opl3 techno] hybridisation process on procyon-ii
https://www.youtube.com/watch?v=daSV5mN0sJ4 - Hyper Duel – Black Rain (YMF262 OPL3 Cover)
https://www.youtube.com/watch?v=pu_mzRRq8Ho - IBM 5155–5160 Technical Reference
https://www.minuszerodegrees.net/manuals/IBM/IBM_5155_5160_Technical_Reference_6280089_MAR86.pdf - a ymf262/opl3+pc speaker thing i made
https://www.youtube.com/watch?v=E-Mx0lEmnZ0 - [OPL3] Like a Thunder
https://www.youtube.com/watch?v=MHf06AGr8SU - (PC SPEAKER) bad apple
https://www.youtube.com/watch?v=LezmKIIHyUg - Powering devices from PC parallel port
http://www.epanorama.net/circuits/lptpower.html - Magic Mushroom (demo pro PC s DOSem)
http://www.crossfire-designs.de/download/articles/soundcards//mushroom.rar - Píseň Magic Mushroom – originál
http://www.crossfire-designs.de/download/articles/soundcards/speaker_mushroom_converted.mp3 - Píseň Magic Mushroom – hráno na PC Speakeru
http://www.crossfire-designs.de/download/articles/soundcards/speaker_mushroom_speaker.mp3 - Pulse Width Modulation (PWM) Simulation Example
http://decibel.ni.com/content/docs/DOC-4599 - Resistor/Pulse Width Modulation DAC
http://www.k9spud.com/traxmod/pwmdac.php - Class D Amplifier
http://en.wikipedia.org/wiki/Electronic_amplifier#Class_D - Covox Speech Thing / Disney Sound Source (1986)
http://www.crossfire-designs.de/index.php?lang=en&what=articles&name=showarticle.htm&article=soundcards/&page=5 - Covox Digital-Analog Converter (Rusky, obsahuje schémata)
http://phantom.sannata.ru/konkurs/netskater002.shtml - PC-GPE on the Web
http://bespin.org/~qz/pc-gpe/ - Keyboard Synthesizer
http://www.solarnavigator.net/music/instruments/keyboards.htm - FMS – Fully Modular Synthesizer
http://fmsynth.sourceforge.net/ - Javasynth
http://javasynth.sourceforge.net/ - Software Sound Synthesis & Music Composition Packages
http://www.linux-sound.org/swss.html - Mx44.1 Download Page (software synthesizer for linux)
http://hem.passagen.se/ja_linux/ - Software synthesizer
http://en.wikipedia.org/wiki/Software_synthesizer - Frequency modulation synthesis
http://en.wikipedia.org/wiki/Frequency_modulation_synthesis - Yamaha DX7
http://en.wikipedia.org/wiki/Yamaha_DX7 - Wave of the Future
http://www.wired.com/wired/archive/2.03/waveguides_pr.html - Analog synthesizer
http://en.wikipedia.org/wiki/Analog_synthesizer - Minimoog
http://en.wikipedia.org/wiki/Minimoog - Moog synthesizer
http://en.wikipedia.org/wiki/Moog_synthesizer - Tutorial for Frequency Modulation Synthesis
http://www.sfu.ca/~truax/fmtut.html - An Introduction To FM
http://ccrma.stanford.edu/software/snd/snd/fm.html - John Chowning
http://en.wikipedia.org/wiki/John_Chowning - I'm Impressed, Adlib Music is AMAZING!
https://www.youtube.com/watch?v=PJNjQYp1ras - Milinda- Diode Milliampere ( OPL3 )
https://www.youtube.com/watch?v=oNhazT5HG0E - Dune 2 – Roland MT-32 Soundtrack
https://www.youtube.com/watch?v=kQADZeB-z8M - Interrupts
https://wiki.osdev.org/Interrupts#Types_of_Interrupts - Assembly8086SoundBlasterDmaSingleCycleMode
https://github.com/leonardo-ono/Assembly8086SoundBlasterDmaSingleCycleMode/blob/master/sbsc.asm - Interrupts in 8086 microprocessor
https://www.geeksforgeeks.org/interrupts-in-8086-microprocessor/ - Interrupt Structure of 8086
https://www.eeeguide.com/interrupt-structure-of-8086/ - A20 line
https://en.wikipedia.org/wiki/A20_line - Extended memory
https://en.wikipedia.org/wiki/Extended_memory#eXtended_Memory_Specification_(XMS) - Expanded memory
https://en.wikipedia.org/wiki/Expanded_memory - Protected mode
https://en.wikipedia.org/wiki/Protected_mode - Virtual 8086 mode
https://en.wikipedia.org/wiki/Virtual_8086_mode - Unreal mode
https://en.wikipedia.org/wiki/Unreal_mode - DOS memory management
https://en.wikipedia.org/wiki/DOS_memory_management - Upper memory area
https://en.wikipedia.org/wiki/Upper_memory_area - Removing the Mystery from SEGMENT : OFFSET Addressing
https://thestarman.pcministry.com/asm/debug/Segments.html - Segment descriptor
https://en.wikipedia.org/wiki/Segment_descriptor - When using a 32-bit register to address memory in the real mode, contents of the register must never exceed 0000FFFFH. Why?
https://stackoverflow.com/questions/45094696/when-using-a-32-bit-register-to-address-memory-in-the-real-mode-contents-of-the - A Brief History of Unreal Mode
https://www.os2museum.com/wp/a-brief-history-of-unreal-mode/ - Segment Limits
https://wiki.osdev.org/Segment_Limits - How do 32 bit addresses in real mode work?
https://forum.osdev.org/viewtopic.php?t=30642 - The LOADALL Instruction by Robert Collins
https://www.rcollins.org/articles/loadall/tspec_a3_doc.html - How do you put a 286 in Protected Mode?
https://retrocomputing.stackexchange.com/questions/7683/how-do-you-put-a-286-in-protected-mode - Control register
https://en.wikipedia.org/wiki/Control_register - CPU Registers x86
https://wiki.osdev.org/CPU_Registers_x86 - x86 Assembly/Protected Mode
https://en.wikibooks.org/wiki/X86_Assembly/Protected_Mode - MSW: Machine Status Word
https://web.itu.edu.tr/kesgin/mul06/intel/intel_msw.html - 80×87 Floating Point Opcodes
http://www.techhelpmanual.com/876–80×87_floating_point_opcodes.html - Page Translation
https://pdos.csail.mit.edu/6.828/2005/readings/i386/s05_02.htm - 80386 Paging and Segmenation
https://stackoverflow.com/questions/38229741/80386-paging-and-segmenation - 80386 Memory Management
https://tldp.org/LDP/khg/HyperNews/get/memory/80386mm.html - DOSEMU
http://www.dosemu.org/ - Intel 80386, a revolutionary CPU
https://www.xtof.info/intel80386.html - PAI Unit 3 Paging in 80386 Microporcessor
https://www.slideshare.net/KanchanPatil34/pai-unit-3-paging-in-80386-microporcessor - 64 Terabytes of virtual memory for 32-bit x86 using segmentation: how?
https://stackoverflow.com/questions/5444984/64-terabytes-of-virtual-memory-for-32-bit-x86-using-segmentation-how - Pi in the Pentium: reverse-engineering the constants in its floating-point unit
http://www.righto.com/2025/01/pentium-floating-point-ROM.html - Simply FPU
http://www.website.masmforum.com/tutorials/fptute/ - Art of Assembly language programming: The 80×87 Floating Point Coprocessors
https://courses.engr.illinois.edu/ece390/books/artofasm/CH14/CH14–3.html - Art of Assembly language programming: The FPU Instruction Set
https://courses.engr.illinois.edu/ece390/books/artofasm/CH14/CH14–4.html - INTEL 80387 PROGRAMMER'S REFERENCE MANUAL
http://www.ragestorm.net/downloads/387intel.txt - x86 Instruction Set Reference: FLD
http://x86.renejeschke.de/html/file_module_x86_id100.html - x86 Instruction Set Reference: FLD1/FLDL2T/FLDL2E/FLDPI/FLDLG2/FLDLN2/FLDZ
http://x86.renejeschke.de/html/file_module_x86_id101.html - X86 Assembly/Arithmetic
https://en.wikibooks.org/wiki/X86_Assembly/Arithmetic - 8087 Numeric Data Processor
https://www.eeeguide.com/8087-numeric-data-processor/ - Data Types and Instruction Set of 8087 co-processor
https://www.eeeguide.com/data-types-and-instruction-set-of-8087-co-processor/ - 8087 instruction set and examples
https://studylib.net/doc/5625221/8087-instruction-set-and-examples