První přednáška
V čem je výhoda diferenciálního přenosu?
Je méně náchylný na el.mag. šum, jelikož ten se bude nejspíš projevovat na oba vodiče stejně
Je diferenciální přenos rozšířený?
Ano - používá ho většina moderních sběrnic/linek
Co si musíme dopředu dohodnout u diferencionálního přenosu?
Které napětí odečítáme od kterého
Proč je sériový přenos technicky snažší než paralelní? (2)
Není přítomno více vodičů, které by se navzájem mohly elektromagneticky rušit
Nemusíme řešit situace, kdy jeden z vodičů paralelní linky by byl o něco málo kratší/delší než jiný (a to se stává - zatáčky)
Jaké piny má USB?
Napájení (+5V), GROUND a diferenciální DATA+ a DATA-
Termíny
Rising edge (rostoucí hrana) = Místo, kde signál stoupá z úrovně 0 na úroveň 1
Falling edge = Místo, kde signál klesá z 1 na 0
"Šedá zóna" = Rozptyl hladin napětí, kde stav vodiče není chápán ani jako 1 ani jako 0
Diferenciální přenos = Přenos na lince pomocí dvou vodičů. Místo abychom vztahovali napětí na jednom vodiči vůči GROUND, můžeme mít dva vodiče a sledovat rozdíl jejich napětí (pak třeba můžeme říct, že když je rozdíl kladný -> 1, když je záporný -> 0 (nebo obráceně))
Paralelní přenos = Přenos na lince, kdy posílám více bitů zároveň (přes několik vodičů).
Sériový přenos = Přenos na lince, kdy posílám vždy jenom jeden bit najednou.
Druhá přednáška
Jak poznám, jestli na lince přenáším?
Použiju floating state
Nebo definuji jednu z hodnot 1/0 jako idle
Nebo jeden z mnoha symbolů, pokud používám něco jiného než nuly a jedničky
Jak upozornit příjemce, že přecházím z idle do přenášení?
Start bitem
Proč potřebuje příjemce hodiny?
Aby měl podle čeho oddělit několik jedniček poslaných po sobě
Proč potřebuju, aby příjemce a odesílatel měli sesynchronizované hodiny?
Aby příjemce snímal hodnotu linky pouze v tu chvíli, kdy je jasně nastavena na 1/0
Podle čeho příjemce ví, na jaký baud rate nastavit svoje hodiny?
To se musí předem dohodnout - já jako programátor jsem za tohle většinou zodpovědný
Je možné, že se hodiny samy od sebe desynchronizují?
Ano. Žádné hodiny nejsou 100% přesné.
Jak zabráním tomu, aby se desynchronizovaly hodiny příjemce a odesílatele? Možnosti:
Posílám vždy pouze určitý počet data bitů. Na začátku každého přenosu se hodiny sesynchronizují podle start bitu.
Přidám vodič, který bude posílat CLK signál (to má PS/2 (kde ho posílá př. myš, která posílá data do PC (v tu chvíli je myš master a PC řadič, který se o to stará, slave) a taky to má I2C, kdy ho obecně posílá master)
Clock-recovery
Omezená délka přenosu
Kolik bitů bude typicky v jednom bytu?
8
Jak příjemce ví, jak dlouhý bude přenos/byte?
Musí to být předem definováno (třeba v komunikačním protokolu)
Čím je problematické, že omezím délku přenosu?
Každý přenos potřebuje kontrolní bity. Ty tvoří overhead a to nechceme. Čím víc přenosů, tím víc kontrolních bitů a tím víc overheadu.
CLK signál
Tak to nepotřebuji start a stop bity, ne?
I s tímhle budu potřebovat start a stop bity. Neplatí totiž pro všechny linky, že zastavený CLK značí konec přenosu.
Kdy mám jako příjemce číst z linky?
Když detekuji na CLK vodiči rising nebo falling edge. Rising/falling edge se dobře detekují.
Kdy má odesílatel měnit úroveň signálu na datovém vodiči?
Mezi rising/falling hranami CLK vodiče. Aby když nastane rising/falling edge, a tedy moment meření, tak byla na vodiči jednoznačná hodnota 1 nebo 0 (a ne šedá zóna) - je to kvůli impedanci vodiče, potřebuje čas než se změní.
Nojo, takže CLK musí mít 2x větší frekvenci, než je frekvence posílání dat?
Ano, pokud nepoužívám DDR (pak by ta frekvence byla stejná)
Čím je přidání CLK vodiče problematické? (2)
Může se s datovým vodičem po cestě časově rozcházet
Další vodič znamená další elektromagnetický šum
Clock-recovery
Jak to funguje?
Hodiny si synchronizuji průběžně při každé změně na datovém vodiči.
Jenomže co když posílám hodně jedniček / hodně nul za sebou a tedy se dlouho na datovém vodiči nic nemění?
No to je pak blbý a není podle čeho srovnávat hodiny
Potom se x-bitová čísla kódují do x+něco-bitových čísel (např. 8bit do 10bit) tak, že nevyužíváme ty kombinace bitů, které mají moc jedniček nebo nul za sebou. Tím zajistíme, že během komunikace budou průběžně probíhat změny na datovém vodiči a půjdou podle toho synchronizovat hodiny.
Která linka třeba využívá clock-recovery?
USB
Controller
Jak zprostředkovává komunikaci? (3)
Může propojovat dvě různé linky (např. RS-232 a USB)
Může se chovat z obou stran jako slave, aby zařízení na obou koncích linky mohly být mastery.
Může uzpůsobovat data z jednoho zařízení, aby je druhé pochopilo.
Bude controller obsahovat registry?
Určitě. Bude btw nejspíš potřebovat buffer registry.
Taky nejspíš bude mít nějaké konfigurační registry (třeba chceme, aby převáděl na různá zařízení podle toho, jak je nastavený)
Jak souvisí radič s out-of-band signály?
Nejspíš v něm bude muset být nakonfigurované, jaké signály mají být na co nastavené při komunikaci s daným zařízením
Termíny
Floating state (Hi-Z, stav s vysokou impedancí) = Kromě stavů pro všechny symboly (0/1) si zavedu ještě floating state, který signalizuje, že linka je idle
Start bit = Bit zahajující každý přenos dat. Předem definovaný jako 1/0.
Stop bity = Bity následující za datovými bity v přenosu. Předem definováno, jakou hodnotu mají být a kolik jich má být.
Data bit = Bit, který je součástí posílané informace. Tedy cokoliv, co není kontrolní bit.
Kontrolní bit = Bit, který není součástí posílané informace (start bit, stop bit, ... ?)
Byte = Soubor data bitů v jednom přenosu.
Baudy = Běžně mluvíme o počtu bitů poslaných po lince. Počítám jak kontrolní, tak datové.
bit/s = Běžné mluvíme o počtu DATOVÝCH bitů poslaných po lince. Kontrolní nepočítám, pokud se mi to nehodí (viz praktiky ISP)
DDR (Double data rate) = Detekuji na CLK signálu nejen rising/falling edge, ale i falling/rising edge. Prostě obě dvě. Tedy za jeden cyklus hodin přečtu/počlu data 2x.
Clock-recovery viz výše
Komunikační protokol = Návod definující, jak má vypadat paket. Předpokládám, že bývá součástí data sheetu (přednáška 5) zařízení, se kterým komunikuji.
Řadič zařízení (controller) = Zařízení zprostředkovávající komunikaci mezi jinak nekompatibilními zařízeními.
Paritní bit = Dodatečný bit na konci posílaných dat, který se nastaví na 1 nebo 0 tak, aby celkový počet jedniček/nul byl sudý/lichý (podle toho, co se dohodlo). Takhle si může příjemce zkontrolovat, jestli se po cestě něco nepokazilo.
Simplex linka = Linka, na které přenos může probíhat jenom jedním směrem
Full-duplex linka = Linka, na které jsou vodiče jak tam, tak zpátky a tudíž může probíhat komunikace oběma směry (a to možná i zároveň?) Např. RS-232
Half-duplex linka = Linka na které vodič může střídat funkci. Někdy se po něm přenáší tam, někdy zpátky.
Out-of-band signály = Signály, které si posílají zařízení navíc během přenosu. Jsou pro ně většinou dedikované vodiče v kabelu, které nabývají hodnoty 1/0.
!SIG / #SIG / SIG s čarou = Značení, že logika daného signálu má být obrácená. Tedy 1 značí negativní odpověď na pomyslnou otázku a 0 značí kladnou odpověď.
Třetí přednáška
Jak řeší napájení zařízení připojující se přes linky, které na napájení nemají vyloženě vyhrazený vodič?
Napájí se třeba přes out-of-band signálové vodiče
Jak zaručím, že zařízení po zapnutí našeho programu bude v nějakém deterministickém startovním stavu?
Vypnu a zapnu to zařízení tak, že mu na chvíli přeruším přívod napájení
Co se může stát po tom, co bylo zařízení zapnuto?
Vypíše na linku nějaká identifikační data
V jakých pořadích můžeme posílat po lince bity čísla?
MSb first a LSb first
Od jakého čísla indexujeme bity v binárním čísle?
Od 0, aby index = na kolikátou mocníme dvojku
Co se stane, když zapnu program uprostřed toho, co zařízení už posílá nějaká data?
Tak začnu číst pravděpodobně od prostředku a přeházím tak pořadí bytů v paketu → čtu nonsense
Zabráním tomu tak, že první byte v paketu si nějak označím - program si pak může počkat na další první byte a číst od něj
Jak značí šestnáctková čísla Pascal?
prefix
$, př$2avětšina jiných jazyků pomocí prefixu
0x, př.0x2a
Jak nastavím konkrétní bity v čísle?
OR (kde v masce budou jedničĸy, tam ve výsledku taky budou jedničky)
Jak resetuji konkrétní bity v čísle?
AND (kde v masce budou nuly, tam ve výsledku taky budou nuly)
Jak flipnu konkrétní bity v čísle?
XOR (kde v masce budou jedničky, ty bity flipnu)
Termíny
Blokující funkce = Funkce, která nenechá program běžet dál, dokud není vyhodnocena
MSb first (most significant bit first) = Posíláme bity od nejvýznamnějšího (největší násobek dvojky) po nejméně významný (2^0)
LSb first (least significant bit first) = Posíláme bity od nejméně významného po nejvíce významný
Nastavit bit = Většinou míněno jako "nastavit bit na 1"
Resetovat bit = Nastavit bit na 0
Flipnout bit = Nastavit ho na opačnou hodnotu, duh
Defensivní programování = Kde je to možné, počítat s tím, že se jiné programy/zařízení nebudou chovat přesně podle specifikací. Nepočítej s tím, že všechny byty budou mít na sedmé pozici nulu. Raději si tu pozici nejprve vynuluj pro případ, že by tam někdo přece jenom něco nacpal.
Jak obracet hodnotu dvojkového doplňku?
Vezmu číslo, zneguji bity a pak k němu přičtu 1
Tohle funguje jak z kladných do záporných, tak ze záporných do kladných
Čtvrtá přednáška
Když píšeme binární čísla na papír, píšeme je běžně MSb nebo LSb?
MSb. Musíme si představovat, že posíláme bity po lince od toho nejvíc vlevo po ten nejvíc vpravo.
Které reprezentace čísel řeší problém, že přičítání k zápornému čísla by muselo být speciální operací?
Jedničkový doplněk a dvojkový doplněk
Těch problémů je u reprezentace explicitním znaménkem víc btw - třeba porovnávání je obrácené
Která reprezentace čísel řeší problém dvou nul?
Dvojkový doplněk
Jaký je rozsah n-bitového čísla reprezentovaného dvojkovým doplňkem?
až
Je dvojkový doplněk rozšířený?
Ano - téměř univerzálně
Python
Jak Python reprezentuje čísla?
Využívá vždy cca tolik bitů, kolik je na reprezentaci čísla třeba + vždy doplní jeden znaménkový bit
Aby věděl, kolik číslo má mít bitů, má ke každému přiřazené ještě 32-bit číslo právě počtu bitů
Rozsah se tak může zvětšovat dle potřeby
Číslo je tak tvořeno 32-bit "chlívečky" (které jsou inty), jejichž počet sleduje to "počítadlo chlívů"
Co mi vrátí
bit_length()metoda (a = 16; a.bit_length())?Neřekne mi o těch 32 bitech, ve kterých se uchovává počet bitů a neřekne mi ani o znaménkovém bitu.
Jenomže vždyť Python stejně neuloží 5bit číslo do jenom 5ti bitů - systém mu přiřadí vždy nejméně byte!
Jop. Je to neefektivní as heck.
Má to ale výhody - Python int má mnohem větší max. rozsah než 64 bitů (což je největší typ, kterým obvykle disponují jiné jazyky) - a taky nikdy nenastane int overflow, prostě se udělá větší rozsah (zvětšuje se sám dle potřeby).
Můžu v Pythonu pracovat s "normálními" číselnými typy?
Ano - když použiju numpy
Bit truncation / extension
Co se stane, když použiju bit truncation na signed číslo?
Odřízne se mi znaménko → těžko říct jestli výsledné číslo bude kladné nebo záporné
Používá numpy signed extension nebo se mám bát?
V pohodě. Numpy není hloupé.
Termíny
SHL = Shift left (jazyky běžně značí <<). Posunu všechny bity o číselnou pozici směrem k MSb. Matematicky na unsigned integerech, protože binární soustava, odpovídá násobení: Modulí se kvůli přetečení. Na signed integerech nepoužívat, protoře si můžeme vysunout největší bity, co značí znaménko.
SHR = Shift right (>>). Posunu všechny bity o číselnou pozici směrem k LSb. Matematicky, protože binární soustava, odpovídá dělení ( je dolní celá část):
ROL = Roll left. Jako shift left, ale bity, které by se z čísla "vysunuly" se nasunou "zprava" (od LSb)
ROR = Roll right. Jako roll left, ale obráceně.
Reprezentace s explicitním znamínkem = Reprezentace čísla, kde MSb čísla je znaménko, zbytek je jeho absolutní hodnota
Jedničkový doplněk = Reprezentace čísla, kde záporná čísla jsou bitovou negací kladných čísel
Dvojkový doplněk = Reprezentace čísla, kde záporné číslo vypočítám z kladného tak, že ho zneguji a přičtu k němu jedničku (kdybych jen znegoval 5 = 0b0101, dostanu 0b1010, což je ve dvojkovém doplňku = -6)
Bit truncation = Princip toho, co se děje, když uložím vícebitové číslo do méněbitové proměnné. Když uložím 8bit číslo do 4bitové proměnné, oříznou se 4 bity směrem od MSb.
Zero extension = Princip toho, co se děje, když uložím méněbitové číslo do vícebitového a neřeším znaménka. V tomto případě jsou prostě chybějící bity vyplněné nulami. Používá se pro bezznaménková celá čísla.
Signed extension = Princip toho, co se děje, když uložím méněbitové číslo do vícebitového a řeším znaménka. Používá se pro znaménková celá čísla. Aby se hodnota čísla nezměnila, záporné zůstalo záporným, a kladné kladným (kladné znaménkové číslo má MSb 0), tak se nakopíruje most signicant bit (MSb, též se mu v tomto kontextu říká sign bit) na všechny nové bity vyššího řádu. Tedy chybějící bity jsou vyplněné hodnotou MSb.
Pátá přednáška
TODO
Budou i vstupní zařízení (klávesnice, myše, ...) někdy přijímat data?
Je to dost dobře možné - třeba nastavení CAPS LOCK diody
Mohou se role slave a master někdy prohodit?
Určitě
Je CPU někdy slave?
Bývá master. S CPU jako slave se nejspíš nesetkáme a pokud budeme mít třeba myš, která se chová jako master, bude třeba mezi ní a procesor vecpat slave-slave řadič.
Musí mít zařízení, které se bude chtít chovat pouze jako master adresu zařízení?
Nope
Multidrop
Může být na jedné lince více slavů a více masterů?
Ano
Co znamená, že paměť má "n-bitový adresový prostor"?
Že mají adresy rozsah až
Jak zajistíme, že stav sběrnice v obou případech (a) nic není připojené a (b) zařízení jsou připojené, ale nic neposílají?
Definujeme idle stav linky jako buď 1 nebo 0 a pak k ní připojíme buď pull-up nebo pull-down resistor
Termíny
Operační paměť = Datová paměť našeho počítače (X datové paměti jiných zařízení).
Master = Zařízené, které v dané komunikaci navazuje a řídí komunikaci.
Slave = Zařízení, které oslovuje a řídí master.
Point-to-point linka = Linka, která má dva konce. Připojují se na ní dvě zařízení
Multidrop linka = Linka, na kterou lze připojit více než dvě zařízení.
Sběrnice (bus) = Jiné pojmenování pro multidrop linku. Akorát se tak nějak ustálilo říkat i point-to-point linkám sběrnice :-/. Významným příkladem je I²C,. Ta se používá na často na senzory. Data se na ní posílají v MSb first pořadí.
Adresa zařízení (slave address) = Identifikátor, podle kterého slave na multidrop sběrnici pozná, že příchozí komunikace od nějakého mastera je pro něj.
Adresový prostor = Rozsah možných
Pull-up/down resistor = Zařízení, které přes silný odpor dodává na linku napětí, aby na ní nastavilo nějaký ze stavů 1 nebo 0. Pull-up bude vytahovat napětí na nějakou vyšší než standardní hodnotu. Pull-down naopak.
Šestá přednáška
TODO
Co to znamená, když je adresový prostor n-bitový?
Že můžeme používat adresy až
Termíny
Paměťová adresa = ? Adresa určitého bytu v paměti
Adresový prostor = Rozpětí čísel adres, které můžeme u dané paměti použít
Transfer rate = Kolik bytů/megabitů/megabytů/atd. za jednotku času (př. MB/s = megabytů/s)
Access time = Čas, který to trvá od toho, kdy jsem se rozhodl přečíst byte/word (podle toho jak je ta paměť adresovaná = co nejmenšího umí přečíst a poslat) do doby, kdy ho mám
Volatile paměť = Paměť, která po vypnutí proudu ztratí svůj stav (většinou to jsou RAMky)
Sedmá přednáška
Jak identifikuji registry zařízení, které jich má mnoho?
Budu používat adresy a adresový prostor podobně jako na paměti
Bude tam adresový registr, do kterého vždy nejprve zapíšu
Btw: Většinou budou adresy registrů různě rozházené po adresovém prostoru
Máme už v počítači procesor. Podle čeho musíme vybrat paměti, které do počítače strčíme?
Tak, aby procesor podporoval jejich komunikační protokol
Už jenom proto, aby program counter byl dost velký na všechny adresy paměti
Procesor může i vícebitovou (víc než 8) paměť vnímat jako adresovanou po bytech
V tom případě si pak musí přepočítat adresu bytu na adresu slova
Pak si zažádá o slovo, ve kterém je hledaný byte
No a nakonec si ze slova vybere ten byte, který chce a zbytek zahodí
Jestli i dnešní x86-64 procesory chápou paměť jako adresovanou po bytech, to nevím
Můžou být procesorové instrukce navzájem různě velké?
Ano. NOP bude třeba jeden byte, ale jiné instrukce budou mít argumenty → musí být delší.
Procesor bude podle opkódu vědět, o kolik má posunout instruction pointer.
Endianita
V jakém případě musíme řešit endianitu?
Když třeba chceme komunikovat s zařízením, které má jinou endianitu než počítač
Proč neexistuje koncept bit endianity?
Protože se nemůžu paměti dotazovat na jednotlivé bity. Ty bity tedy nemají nijak přiřazené číslování (alespoň programátor ho nemá šanci vidět).
Von Neumann
Co je třeba výhoda Neumanna?
S ním nemusím kopírovat zkompilovaný kód z datové paměti do programové
Můžu používat self-modifying code ( ͡° ͜ʖ ͡°)
Další
Opotřebovávají se RAM paměti?
Nope. Vlastně jako jediné - je to jejich velká výhoda.
Termíny
Program Counter (pc, instruction pointer, ip) = Registr, který v sobě uchovává adresu právě vykonávané instrukce v paměti.
Harvardská architektura = Architektura počítače, kde datová a programová paměť jsou oddělené
Von Neumannova architektura = Architektura počítače, kde datová a programová paměť žijí obě v jednom zařízení
Procesorová instrukce = Posloupnost bytů, kterou si procesor interpretuje jako příkaz
Instrukční sada = Soubor procesorových instrukcí
Opcode = První část procesorové instrukce. Lze si ji představovat jako název funkce. Potom zbytek instrukce lze chápat jako argumenty funkce.
Strojový kód = Posloupnost procesorových instrukcí
Little-endian = Způsob ukládání bytů v paměti. "Little end first". Tedy na nejnižší adrese je nejméně významný byte (least significant byte). Tedy pro 2 bytové číslo 0xa3fe bude mít byte 0xfe např. adresu 0x0a (v decimal 10) a byte 0xa3 adresu 0x0b (v decimal 11).
Big-endian = Způsob ukládání bytů v paměti. "Big end first". Tedy na nejnižší adrese je nejvýznamnější byte (most significant byte). Tedy pro 2 bytové číslo 0xa3fe bude mít byte 0xa3 např. adresu 0x0a (v decimal 10) a0xfe adresu 0x0b (v decimal 11).
Immediate hodnota = Hodnota v assembly, která je přímo v kódu. Něco jako a = 6. Tak ta šestka je immediate hodnota. V assembly nejsou proměnné, ale jen nějaký daný počet registrů, podle procesoru, a pak adresy v paměti, tak realný příklad může být: ADD EAX, 5, čili do registru EAX přiřaď číslo 5.
Osmá přednáška
TODO
Jaké třeba máme příznaky? (3)
Zero: Poslední operace dala jako výsledek nulu.
Sign/Negative: Výsledek poslední operace byl záporný (procesor nerozlišuje signed a unsigned, btw)
Carry
Jak se běžně značí příznakový registr?
P = "processor state"
Jak může programátor ovlivňovat příznaky?
Procesory často mají příkazy na setování a clearování jednotlivých příznaků
Proč se implementuje akumulátorová architektura?
Protože je to levnější
Musí mít procesor s akumulátorovou architekturou jenom jeden akumulátor?
Ne, mohou mít i třeba dva (možná i ještě víc)
Termíny
Příznak (flag) = Hodnota ANO/NE indikující nějaký stav procesoru.
Příznakový registr (flags register) = Registr přítomný (asi) v každém procesoru. Jeho bity reprezentují hodnoty jednotlivých příznaků.
Side effect = Něco, co procesorová instrukce dělá navíc (mimo její hlavní účel). Častými side effecty je nastavování příznaků.
Akumulátorová architektura = Zjednodušená architektura procesoru, kde můžeme typicky přičítat (a jiné operace) jenom k jednomu registru - akumulátoru.
Devátá přednáška
Screenshot z konzultace diagramu nadepsaného LOAD/STORE - je tam pěkně vidět, jak tedy funguje interakce mezi tím, jak procesor adresuje po bytech, ale paměť po slovech

(Nedám sem video, to si Ježek nepřeje, ale dám referenci: Je to z "ZS 2020/21: NSWI120, 09. konzultace ke 09. přednášce", čas 22:38)
Jak měříme rychlost vykonání procesorové instrukce?
Na to, kolik taktů zabere
Které operace třeba moderní procesory zvládnou za jeden takt? (2 konkrétní, 2 skupiny operací)
Sčítání, odčítání, logické operace, bitové posuny
Proč jsou příkazy LOAD a STORE pomalé?
Protože jsou musejí čekat na to, až paměť vrátí požadované hodnoty
Python sucks vol. 2
Kolikrát je typicky Python pomalejší oproti něčemu jako je Cčko?
100x
Z jakých dvou důvodů je Python tak pomalý?
Je interpretovaný
Způsob, jakým reprezentuje čísla
Dynamické typování
S čím vším musí Python operovat, pokud pracuje s číslem? (4)
Typ proměnné, samotná binární hodnota, počet využitých bitů, reference counter pro garbage collecting
Jak se u Pythonu optimalizuje, že při každém přiřazení do Pythonovské proměnné vlastně musí vznikat nová proměnná v paměti?
Proměnné čísel -5 až 256 jsou vytvořeny už při spuštění libovolného Python programu. Už je potom znovu nevytváříme, ale pouze na ně nasměrujeme pointer Python proměnné, když čísla potřebujeme někam přiřadit.
Btw: to vede k tomu, že neintuitivně s některými hodnotami Python pracuje rychleji než s jinými
Kolik bytů bude Python používat na typ proměnné, počet využitých bitů a reference count?
No nejméně využívá 32bit proměnné -> 4 byty na všechno. Takže na takové číslo 257 využije python 4 + 2 + 4 + 4 = 14B.
Proč to zpomaluje dynamické typování?
Typ proměnné se může v průběhu proměnné měnit, a musí se tak kontrolovat:
if podminka: a = 5 else: a = "ahoj" #Co tady znamená +? #Buď sčítání nebo stringová konkacenace #Tak se Python musí podívat na typy proměnných, #a podle toho provést odpovídající věc c = a + b
U jazyků, co jsou staticky typované (třeba C a C++), tak se tyhle kontroly dít na každém kroku nemusí
Násobení a dělení
Jakou architekturu nejčastěji používají mikrokontrolery?
Harvardskou
Jak je to s rychlostí instrukcí násobení a dělení?
Kolik taktů: Sčítání < Násobení < Dělení
Dělení už bývá hodně pomalé
Je násobení a dělení vždy v instrukční sadě?
Často ne (hlavně u mikrokontrolerů) a potom to je třeba implementovat softwarově
Jakým trikem lze o trochu rychleji implementovat (softwarově) dělení a násobení?
Můžu nějak využít bitshift doleva a doprava, jelikož bitshifty jsou efektivně násobení a dělení mocninami dvojky.
Ale bacha, že bitshift doprava je celočíselné dělení, ne reálně dělení.
Btw: Tohle můžu využít i při optimalizaci algoritmů, kde dělím nebo násobím mocninami dvojky
Jaký je ale rozdíl mezi bitovým posunem doprava a celočíselným dělením dvojkou?
Běžně celočíselné dělení zaokrouhluje směrem k nule (C) zatímco bitshift doprava zaokrouhluje dolů (u záporných hodnot je to rozdíl)
Ale Python to má samozřejmě jinak: V něm je celočíselné dělení a bitshift doprava fungují stejně - zaokrouhlují dolů
Fixed-point
Jak vypadá zápis toho, kolik bitů je vyhrazeno pro část před čárkou a kolik pro část po čárce?
x + y NEBO x.y
Co je super na fixed-point číslech?
Můžu se k nim chovat jednoduše jako k celým číslům (dokud nemíchám různěbitové fixed-point reprezentace)
Termíny
Arithmetic overflow (přetečení) = Když přičtu k osmibitově bezznaménkově reprezentované 255 jedničku, dostanu 0. Analogicky u znaménkového čísla 127 + 1 = -128.
Arithmetic underflow = Když odečtu od osmibitově bezznaménkově reprezentované 0 jedničku, dostanu 255.
Mikrokontroler (jednočipový počítač) = Počítač s CPU a pamětí v jednom čipu. Našli bychom je třeba v myčkách, pračkách, ...
Aritmetický bitshift (SAR, SAL)= Bitshift, který narozdíl od logického bitshiftu (SHR, SHL) dává pozor na znaménkový bit a zachovává ho.
Fixed-point reprezentace = Způsob, jakým reprezentovat desetinná čísla v počítači. Je pevně dané, kolik bitů reprezentuje část před čárkou a kolik po čárce. Vlastně nezapisujeme desetinná čísla, ale "půlková" čísla.
Desátá přednáška
KOUKNI SE PAK ZNOVU NA ZÁZNAM - někdy před 1:00:00 je na tabuli hexdump, který ale nesedí s tím, který jsem vytvořil já TŘEBA BUDE VZOROVÉ ŘEŠENÍ
Fixed-point pokračování
Mají programovací jazky podporu pro fixed-point reprezentaci?
Ne
Můžeme si nějak zařídit fixed-point bez toho, aby to programovací jazyk explicitně podporoval?
Ano - využiju k tomu bitshifty a to, že víceméně mohu na fixed point čísla používat celočíselnou aritmetiku
Akorát u násobení a dělení budou problémy s přesností
Co se stane, když vynásobím dvě 5.3 fixed-point čísla?
Získám něco.6 fixed-point číslo. Musím pak shiftnout o tři doprava, abych konvertoval zpět na něco.3
Jaký problém má fixed-point reprezentace s hodně velkými a hodně malými čísly?
Zaokrouhluje je - a to tak, že výsledná hodnota se mnohdy ani neblíží té správné
Jak to udělat, abych dokázal násobit fixed-point proměnné a neztratil v průběhu násobení cifry?
Můžu čísla převést do proměnných vyšší přesnosti, provést násobení, shiftnout a pak zase převést zpět
Floating-point reprezentace
V jakém pořadí jsou podle IEEE754 zapsány mantisa, exponent, sign bit?
Sign bit, exponent, mantisa
Jak se řeší, že exponent musí být znaménkové číslo?
Pomocí reprezentace s posunem
Kolikrát pomalejší je floating-point aritmetika implementovaná sw/hw oproti běžné aritmetice?
SW 3x, HW 2x
Mají procesory hw podporu floating-point aritmetiky?
Moderní procesory ano. Mají na to vyhrazené speciální registry a instrukce.
Sčítání floatů
Jak se sčítají floaty?
Jedno číslo denormalizuji - tedy srovnám jeho exponent s exponentem toho druhého, sečtu mantisy a výsledek zase normalizuji
Btw, tady se mi mohou stát zaokrouhlovací chyby
Speciální hodnoty IEEE754
Pokud všechny bity exponentu jsou nuly, float je ve speciálním denormalizovaném tvaru.
Počítáme pak s tím, že před řádovou čárkou je nula a v mantise je zapsané to, co je za řádovou čárkou
Jaké další hodnoty podporuje IEEE754? (2)
+-inf, NaN
Propaguje se nekonečno a NaN napříč výpočtem?
Ano
Co za blbosti dělá zase Python?
Nepropaguje nekonečno a NaN. Místo toho vyhodí chybu, když některá taková hodnota vyjde.
Ale můžeš to obejít používáním numpy
Non-volatile paměti
Jaké non-volatile paměti např. existují? (3)
ROM
PROM
Když si nechceme nechat sériově vyrobit 1000 stejných kusů, když bych místo toho potřeboval spíš 5 různých
Spálím diody uvnitř paměti
EPROM
Když chceme mít možnost ještě něco poopravit
EEPROM až příště
Termíny
Normalizovaný formát = Speciální případ vědeckého zápisu čísla takový, že před desetinnou čárkou je přesně jedna nenulová cifra (tedy kromě případu, kdy celé číslo je 0).
Skrytá jedna = Praktika používáná u floating-point reprezentace. V binárním normalizovaném formátu bude nalevo od řádové čárky vždy jedině jednička. Potom pokud někde bude vždy jednička, tak si ji nemusíme zapisovat.
IEEE754 = Standard formy floating-point čísel. Definuje single precision (32bit) a double precision (64bit) varianty.
Mantisa (Significant, Mantissa), Exponent, Sign bit = Floating-point číslo se skládá z těchto tří částí tímto způsobem: (-1)^sign * mantisa * 2^exponent = hodnota čísla.
Reprezentace s posunem (With bias) = Reprezentace čísel se znaménkem, kde si předem stanovím bias. Chci-li pak zapsat nějaké číslo pomocí této reprezentace, přičtu k němu bias a zapíšu výsledek. Tímto způsobem mohu zapisovat pomocí kladných čísel záporná i kladná čísla.
Firmware = Software, který bude v zařízení po celou jeho životnost. Často v non-volatile paměti mikrokontrolerů.
Možná přenosová rychlost je něco jako bandwidth a přístupová doba něco jako odezva
http://www.pf.jcu.cz/stru/katedry/fyzika/prof/Tesar/diplomky/pruvodce_hw/komponenty/zakladni/disk/parametry.htm
Jedenáctá přednáška (+ kousek dvanácté)
Co potřebuji na smazání EPROM?
Silné UV záření
Stačí mi ni smazání EPROM sluneční svit?
Ano, ale musel bych tu paměť nechat venku delší dobu
EEPROM a Flash
Jak je na tom přenosová rychlost Flash?
Jako nejpomalejší DRAM
Jak je na tom přístupová doba Flash?
Špatně
Co má více omezený počet zápisů?
Flash
Dokáže Flash přistupovat k jednotlivým bytům?
Nope. Musíš si načíst celý blok.
V jakém řádu jsou tak velké bloky Flash paměti?
V KiB
Co bude u Flash paměti naprd?
Náhodný přístup
Proč je pojmenování NVRAM špatně?
Protože Flash/EEPROM paměti nejsou random-access (to by musel náhodný přístup být stejně rychlý jako přístup k bytům v jednom bloku)
Mikrokontroler
Co nejspíš bude kromě procesoru a paměti zabudované do mikrokontroleru? (2 + 1)
ADC a DAC řadiče a GPIO
Co nejspíš bude součástí GPIO?
Směrový registr. V něm je uložené, které GPIO linky jsou teď vstupní a které výstupní.
Jaká technologie se často používá jako permanentní datové úložistě v mikrokontrolerech?
EPROM
HDD
Kolikabytové se dřív dělaly sektory?
512B
Kolikabytové sektory se dělají dnes?
4KiB ("Advanced format")
Pohybují se hlavy samostatně?
Ne. Hlavy všech ploten se pohybují společně.
Jak jsou číslované stopy?
Od vnějšku dovnitř
Má HDD omezený počet zápisů?
Ne
Rychlost HDD
Sekvenční zápis/čtení
Jo ten je rychlý
Zápis/čtení pozpátku
No ten je na houby, protože přečty byte a pak čekám, až se celá plotna otočí, abych se dostal k tomu bytu před ním.
Zápis/čtení napříč více stopami
Ještě pomalejší, protože rychlost, než se hlava přesune na jinou stopu, není velká (fyzikálně omezená)
Jak jsou rozdělené sektory na stopách?
Vnější stopy mají násobně více sektorů než vnitřní, protože je tam čtení rychlejší
CD/DVD/BlueRay
Jsou taky tyto nosiče rozdělené na sektory?
Ano
Jak velký je typicky sektor CDčka?
2 KiB
Mají CDčka taky stopy jako koncentrické kružnice?
Ne - mají jednu spirálovitou stopu
Jak jsou číslované sektory na CDčku?
Zvnitřku ven
Můžu si tedy klidně CDčko oříznout a nebude problém, dokud se někdo nepokusí číst moc vysoké číslo sektoru.
Komunikujeme s úložným zařízením
Co bude v řadiči hard disku? (4)
Adresový registr, příkazový registr, buffer, info registr
K čemu je u hard disku buffer?
Nejprve se načtou data z disku do bufferu a odtamtud teprve si je bere procesor (a obráceně při zápisu)
Jo a tím pádem tam nejspíš bude nějaký autoinkrementační registr čtení bufferu
Co bude v info registru HDD?
Údaje o velikosti zařízení, velikosti sektoru, počtu sektorů, ...
Adresuji u HDD jednotlivé sektory pomocí C/H/S?
Ne. Moderní HDD používají stejný protokol jako CD/DVD mechaniky.
No ale jak můžu adresovat HDD pomocí LDA?
Nějakou funkcí se namapují C/H/S hodnoty na lineární LDA
Jakou výhodu má, že k HDD přistupuji jako k mechanice?
Že nemusím rozlišovat HDD, SSD, mechaniky. Prostě se ke všem chovám stejně.
Jakou technologii používá SSD?
Flash
Jak je rozděleno SSD na sektory?
Sektor = flash paměť blok
Soubor
Kde jsou uložena metadata souboru?
Jak která. Ta, která se týkají toho, kde je umístěný a jak se jmenuje, budou někde na začátku disku. Metadata specifická pro určitý druh souboru budou už nejspíš přímo v něm - v jeho hlavičce.
Pamatuje si souborový systém od kterého ke kterému sektoru existuje soubor?
Ne. Pamatuje si vyloženě seznam těch sektorů, protože soubor může být fragmentovaný klidně po celém disku.
Proč otvíráme soubory (takové to f.open())?
Protože se nechceme u každého přístupu k souboru ptát souborového systému, na kterém sektoru soubor najdeme. Proto si rovnou do f.open() načteme metadata toho souboru (včetně toho, na kterých sektorech existuje) (tuším, že o tohle se starají file descriptory).
Co ještě třeba uchovává v Pythonu file objekt?
Offset, na kterém momentálně jsem
Co určitě musí být v hlavičce?
Délka souboru, protože poslední ze svých sektorů soubor nemusí zabírat zcela - abychom pak nečetli nesmysly
Musí vždy soubor začínat na začátku sektoru?
ANO
Ne. Případ kdy začíná jinde může nastat, když jiný soubor nezabírá kompletně poslední ze svých sektorů. Pak další soubor můžeme uložit tam, kde ve zmíněném sektoru končí první zmíněný soubor.Leda asi u nějakých spešl souborových systémů
Jaké místo zabírá prázdný soubor?
Pouze takové místo, které souborový systém vyhrazuje metadatům
Termíny
NVRAM = Non-volatile RAM. Společný název pro EEPROM a FLASH paměti (a podobné). Moc se ale nepoužívá.
Permanentní datové úložiště = Nějaká non-volatile paměť ve stroji.
Plotna = Kruhový zmagnetizovaný kus plechu. Součást HDD. Na plotnu se ukládají data.
Stopa (Track) = "Kružnice" dat na plotně HDD.
Sektor = Úsek stopy HDD.
Hlava HDD = "Ručička" určité plotny HDD. Pohybuje se po stopách. Hlava vykonává samotné čtení/zápis na plotnu.
Cylindr = Množina stop se stejným číslem napříč všemi plotnami.
C/H/S adresování = Cylindr/Hlava/Sektor adresování na HDD.
LDA adresování = Adresování na CD/DVD/BlueRay
Offset = Relativní "adresa" v rámci jednoho sektoru.
Base adress = Absolutní adresa začátku (prvního bytu, např.) nějakého kusu paměti (třeba sektoru).
Hlavička (Header) = Část souboru vyhrazená pro jeho metadata.
Magic signature (Magic constant) = Pár písmenek na začátku hlavičky souboru, podle kterých by mělo být identifikovatelné, který formát souboru to je. Ideální by bylo, kdyby všechno formáty měly vlastní magic constant, ale to nejde úplně zařídit, a tak nastávají konflikty.