V BX jsem viděl spoustu příspěvků. Věřím, že dnes je to „registr pro obecné účely“. Jsem zmatený, proč to lidé nazývají Base Address Register,
- Proč se tomu říká Base Base Register, historicky.
- Je něco z toho, co je ještě dnes relevantní ?
- Existuje konvence, která by vyhradila jeho použití pro základní adresování?
Vidíte to takhle se tomu říká .
Komentáře
- Přemýšlím o tom, toto není ‚ Přesně RC otázka, protože ‚ necílí na nic o starém počítači – zejména ne proto, že by chtěla relevanci dnes . Tato otázka by se lépe hodila na hlavním webu SE – a rychlé vyhledávání ukazuje, že tam byly hodně žádány variace.
- Myslím, že klíčem je, že registry na x86 jsou pouze “ více či méně obecný účel „, můžete použít kterýkoli z nich v základních operacích, ale existují / byly situace, kdy jste byli omezeni na to, které registry můžete u se.
- Dalším klíčovým bodem je, že porovnání historického a moderního využití je zavádějící, pokud jde o x86 (zde předpokládám, že komentář k „Registru pro obecné účely“ se opravdu týká spíše EBX / RBX než BX). Aktuální x86 je zpětně kompatibilní s 8086, ale moderní programovací jazyk x86 v dnešním programování je ve srovnání s programováním 8086 (nebo dokonce 386) velmi, velmi odlišný; takže použití BX nemusí nutně vypovídat o použití EBX / RBX.
Odpověď
BX byl vždy jedním z obecných registrů a vždy se mu říkalo základní registr (viz například 8086 Primer , strana 19). Jedná se o základní registr, protože jej lze použít v různých režimech adresování: uložení adresy v BX a offset v SI nebo DI (respektive zdrojové a cílové rejstříky indexů), umožňuje přístup do paměti na BX + SI nebo BX + DI ( ibid , strana 31) nebo BX + SI + okamžité , nebo dokonce BX + okamžité . Slouží také jako základna pro XLAT
.
BP je podobný a podporuje všechny výše uvedené režimy adresování. Rozdíl mezi BX a BP spočívá v tom, že BX je výchozí pro datový segment (DS), zatímco BP je výchozí pro segment zásobníku (SS). (BX a BP mají také své vlastní specifické pokyny – eg XLAT
používá BX, ENTER
a LEAVE
použít BP.)
Tyto režimy adresování existují dodnes, takže jejich použití je stále relevantní, ale indexované a nepřímé adresování jsou k dispozici s libovolným obecným registrem, ukazatelem nebo indexem počínaje 32bitovým x86 . Zatímco BX a BP jsou „speciální“ na 16bitových x86, protože jsou jedinými registry, u nichž je možné nepřímé nebo indexované adresování, u 32 nebo 64bitových x86 to již neplatí, takže EBX, EBP, RBX a RBP nejsou tak speciální. (BP, EBP a RBP jsou stále poněkud zvláštní, protože jako základní registr v 16- a 32bitovém režimu vybírají SS a nelze je použít jako ukazatele bez offsetu, tj. existuje místo toho nebude použit žádný operační kód pro MOV AX, [BP]
a MOV AX, [BP+0]
.)
Neexistuje žádná konvence, o které vím konkrétního vyhrazení použití BX pro základní adresování; pokud ji potřebujete použít pro základní adresování, nastavíte ji vhodně a použijete ji. Pokud používaná konvence volání vyžaduje zachování BX, musíte to vzít v úvahu (jako volající nebo volaný v závislosti na konvenci a kódu, který píšete).
Komentáře
- +2 pro přidání XLAT / ENTER / LEAVE.
Odpověď
(Toto je kromě odpovědi Stephena Kittsa)
Proč se historicky nazývá registr základní adresy.
No, není to. Pokud je to všechno, pak by to byl „Base Index“ (nebo lépe Index Base), protože to bylo v původním 16bitovém adresování jediný registr, který by mohl být přidán jako „Base“ ve všech indexovaných adresách. Indexováno pomocí SI
nebo DI
. (* 1)
Toto adresování bylo symetrické s BP
jako základním ukazatelem. Základní myšlenkou bylo, že na pole lze poukázat pomocí BX a adresovat ho pomocí SI
nebo DI
bez dalších okolků – nebo BP, pokud je v stack (* 2)
Kromě toho je to jeden z původních obecných dvoubajtových registrů.
Je něco z toho stále relevantní?
Ne tak docela. Alespoň ne v 32/64 bitovém režimu.REX
adresování umožňuje použití kteréhokoli z „klasických“ registrů jako (indexových) základen v 32bitovém režimu – kromě BP
/ SP
(* 3). V 64bitovém režimu lze použít 12 ze 16 registrů stejným způsobem (ne BP
/ SP
/ R12
/ R13
(* 4)).
Nyní, když už jsme řekli, že přijde „dlouhý“ režim s 16bitovými segmenty kódu chráněného režimu . Zde se používá klasické (16bitové) kódování společně s velikostí registru 32/64 bitů. BX
si zachovává svoji výhodu kódování, protože SIB
není potřeba. Nakolik je tento poměrně zapomenutý režim relevantní, je na diskusi.
Existuje konvence, která vyhrazuje jeho použití pro základní adresování?
Ve skutečnosti ne. Použijte podle potřeby. Koneckonců, toto je Assembly – neexistuje žádná konvence, kterou nechcete :))
Jediný problém, který je třeba mít na paměti, je zachování pro vašeho volajícího (pokud to není výslovně provedeno)
Vidíte, jak se tomu říká tady.
Chyb … umožňuje řekněte, že se nemýlí, ale doporučil bych hledat podrobnější popis, abyste se dozvěděli více o x86 (Check Wiki (books) or OSDEV-Wiki ). Nebo pokud jde o klasické (16bitové) programování x86, pak si můžete přečíst pouze jednu knihu: Steve Morse „ 8086 Primer . 32/64 bit je stejně odlišný a je třeba se je naučit, aniž by tyto klasické předpoklady byly opravdu užitečné, místo batohu speciálních případů ve zvláštních případech.
* 1 – Pokud chcete přiřadit mnemotechniku názvy čtyř základních dvoubajtových registrů, může to být
- AX = A ccumulator . Používá se pro A rithmetic (nebo A vždy nejkratší kódování)
- BX = B ase. Používá se jako ukazatel na data (struktury)
- CX = C ounter. Používá se v režimech shift / rotate, string ops a loop.
- DX = D ata. Používá se v aritmetice a I / O.
* 2 – Pak opět v případě „standardního“ programování BP
drží rám zásobníku, takže index je zde vždy indexem do tohoto rámce, pokud není BP dočasně přesunut.
* 3 – SP
lze také použít s SIB
kódování.
* 4 – SP
/ R12
opět s SIB
kódování.
Komentáře
-
REX addressing allows [using any register in 32-bit mode]
– mysleli jste SIB zde? - @ilkkachu Nop. Alespoň pokud si pamatuji. REX umožňuje použít režim r / m se všemi registry. SIB je potřeba pouze pro SP a R12. A samozřejmě, pokud chcete použít škálování … nebo jsem to pokazil? Musím to znovu zkontrolovat.
- Mm. Vím, že ‚ je možné použít všechny registry jako ukazatele v 32bitovém režimu, takže ‚ nemůže být REX. Ve skutečnosti se zdá, že v 32bitovém režimu stačí pouze bajt modr / m k použití jediného registru jako adresy, v tomto případě není potřeba žádný SIB (kromě ESP). wiki.osdev.org/…
- @ilkkachu Jup, ale vy ‚ také máte pravdu, pro použití registru jako základny s jiným jako indexem je zapotřebí SIB. Dovolte mi to ještě jednou zkontrolovat a opravit svou odpověď. ok?
odpověď
BX je nejstarší indexovací registr. Typicky k prvku ve struktuře by měl přístup [BX + constant]
; proto jeho název (případně název pochází z [BX + SI]
; na levé straně lze použít pouze BX nebo BP a na pravé straně lze použít pouze SI a DI).
Nemohl jsem najít konkrétní věc na ebx / rbx, kromě toho, že je to nejnižší registr, který není zahalen specifickou instrukcí (mul / div / shl / shr), takže je dobré umístit ukazatel.
Na druhou stranu je [esp + offset] delší instrukce než [ebp + offset], takže eliminace ukazatele rámce nevytváří vždy kratší kód.
Komentáře
- Jste si jisti, že 32bitové operační kódy jsou kratší? V 16bitovém režimu existují explicitní kódování pro kombinace BX / BP, SI / DI a 8 nebo 16bitové posunutí a další varianty nelze kódovat; v 32bitovém režimu se používá kódování obecného registru (EAX / ECX / EDX / EBX / ESP / EBP / ESI / EDI), kromě toho, že pro označení bajtu SIB se používá 100b (obvykle ESP) a 101b (obvykle EBP ) bez posunutí se používá k označení 32bitového posunutí.
MOV EAX, [EBX+9]
trvá 3 bajty, stejně jakoMOV EAX, [ECX+9]
; s dalším registrem potřebujete 4 bajty. - @StephenKitt: Stojím opravený. Jediný, kdo je ve skutečnosti delší, je [esp + x]