
Oggi ho intenzione di parlare di ciò che
continua all’interno dei processori Intel che
guida molti se non tutti i nostri server
computer portatili e desktop e mi verrà insegnato
di entrare nei dettagli un po ‘
quindi spero che mi perdoni se ottengo
nelle erbacce con un po ‘di montaggio sul
schermo ma prima di andare troppo lontano su I
avere una ammissione il mio discorso si chiama x86
per divertimento e profitto
e la mia intenzione originariamente doveva venire
con alcuni indicatori davvero forti
su come potresti ottimizzare il tuo codice
come puoi profilare il tuo codice come
capire gli interni del
la macchina può darti un’idea di
migliorando il tuo codice ma c’è così tanto
per coprire ed è così interessante, solo
volevo coprire le cose che penso
sono interessanti e si spera lungo il
modo noi prenderemo un po ‘insolito
indicatori di comportamento che possiamo cercare
e qualche oggetto di ottimizzazione
opportunità ma principalmente questa roba è
solo molto interessante e se niente
altrimenti voglio che tu vada via dalla fine
di questo discorso e avere un nuovo
apprezzamento per ciò che sulla terra Intel
e gli ingegneri AMD sono stati in grado di fare
dietro la facciata x86 che ci danno
e in effetti hanno una sorta di simpatia
per quelle persone tra noi che scrivono
compilatori e squadre investigative comuni e che stanno cercando di
una specie di reverse engineer e take
vantaggio di tutto questo fantastico
potere di fronte a noi in modo da Intel sono
notoriamente a denti stretti su ciò che accade
oltre il set di istruzioni x86
loro hanno circa sette o otto piedi
un sacco di manuali che puoi ottenere
avere tutti i modi di attuare in dettaglio
sul singolo op codifica il byte
codifica le modalità di gestione del sistema
funziona e tutte quelle cose ma non lo fanno
in realtà ti dico come funziona dentro
principalmente perché credo che non vogliono
fare l’occhiolino agli altri
abbastanza giusti anche loro non vogliono che lo facciamo
trarre troppa vantaggio dalla parte interna
di un chip in cui possono cambiare da
revisione del processore alla revisione del processore
ma per fortuna ci sono alcune persone fuori
là chi è abbastanza pazzo da farlo
il loro hobby o passatempo per provare e
decodificare il più possibile
su cosa succede sotto e questo
parlare non sarebbe stato possibile senza a
sacco di
aiuto da un ragazzo potenzialmente chiamato
Agron of fog che è all’Università di
La Danimarca penso e l’ ha fatta sua
il lavoro della vita per sedersi e scrivere test
caso dopo caso di test dopo caso di test e
utilizzare tutta la gestione interna
contatori che si trovano all’interno del chip e
in qualche modo cercare di ricavare ciò che sta accadendo
sotto il cofano così tanto viene questo
da quello che ha detto e da altre persone
chi ha esaminato questo e fatto
esperimenti e alcuni dei miei
anche esperimenti, ma soprattutto io sono
in piedi sulle spalle di questi altri
ragazzi sono venuti prima di me, quindi questo è
su tutti i dettagli di Intel
pronto a darvi su ciò che accade
all’interno di questo diagramma qui siamo
parlerò della metà superiore e
la metà inferiore della metà superiore ecco la
per ordinare una istruzione dopo
un’altra parte del processore e il
la parte inferiore è dove l’ interessante
succede qualcosa dove tutto esce
di ordine e di cui parleremo
la pipeline quello che predice il ramo
è ciò che registro è rinominato e perché
è importante come quello fuori ordine
l’esecuzione avviene e un pochino sopra
caching Sono io possa aver perso venduti che
un po ‘nell’astratto di questo
parlare ho detto che sarei andato
nel caching pure ma di nuovo quello è
come probabilmente altre ore parlano e sono
proprio così andremo a pascolare
un po ‘forse se io se loro
Invitami a tornare l’anno prossimo, possiamo parlare
a questo allora quindi ci sarà
qualche assemblea sullo schermo come ho detto
e prima di andare troppo lontano io solo
dare una rapida panoramica dell’assemblaggio
struttura in modo che stiamo parlando
lo stesso tipo di cosa ce ne sono due
modi concorrenti di mostrare assembly Intel
c’è il formato AT & T e poi c’è
il formato Intel ho scelto Intel
uno per queste diapositive perché è giusto
ha più senso per me venendo da
I processori ARM risalgono a quando e così è
dove la destinazione è sulla sinistra
lato della mano delle due cose così an
l’istruzione generalmente sembra qualcosa a
un po ‘come op dove up è come caricare o aggiungere
o sottrarre o o esclusivo o o spostamento
destinazione e fonte e quelli
destinazione e quelle fonti possono essere uno
di tre cose possono essere un registro
uno dei rack o RBX o RCX come me
scritto qui ce ne sono otto
registri architettonici che provenivano da
l’era a 32 bit quando AMD ha inventato il
estensioni della versione a 64 bit di
il
valutatori hanno aggiunto in altri otto
registra quali erano molto di più
piuttosto chiamato sensibilmente attraverso i nostri 15 piuttosto
nuovi strani nomi esoterici ci sono
anche queste istruzioni multimediali che
sono cresciuti dalle revisioni del
Istruzioni MMX impostate da lontano quando
questi non sono registri generici
di solito sono in possesso di interi da impatto o
valori imposti a virgola mobile e loro
può essere utilizzato in parallelo per simili
moltiplica e cambia e cose ma
non possono essere usati generalmente per simili
indicizzazione a differenza anche degli altri registri
puoi parlare di sottosezioni di
registri così come ho detto il 64-bit
registra RA X ha un 32 bit
controparte EAX e un conteggio di 16 bit circa
ax e poi un H e al quale si riferiscono
il secondo dal basso e dal basso
otto bit rispettivamente che tutti
che rimandano alla eredità del
8088 che ancora pervade ancora oggi
macchine desktop e server per il massimo
parte il flusso di istruzioni del tuo
IBM 8e originale funzionerà felicemente
non molestato relativamente indolubile su un
sistema operativo appropriato su un moderno
chip Intel che ha un numero di
effetti collaterali interessanti il fatto che
abbiamo questo oltre 30 anni indietro
compatibilità nel flusso di istruzioni
ne parleremo un po ‘più tardi
come ho detto, può essere una delle tre cose
potrebbe essere un registro può essere un
memory operando da chiunque venga
come la Cisco quindi il mondo a rischio come me
è stato assolutamente scaglionato a
rendi conto che su x86 un operando di memoria
può essere un indirizzo di memoria assoluto mem
più un registro più un altro registro
tempi uno a quattro o otto e questo è un
un singolo operando è un tipo di parte
di un’istruzione è carina
serie complicata di indicizzazione o può
anzi essere una costante così quei tre
le cose sono memoria di registro o costante
quindi ho un esempio in basso
qui questa è un’istruzione
è un array di puntatore word ADD D RB X
più 4 volte ID X virgola DX e che cosa
in realtà è viene letto dall’indice array
il registro B più 4 volte il D
registrati aggiungi da register a quel valore
e poi riscrivilo tutto è uno solo
l’istruzione è piuttosto complicata
ed è qui che il C
in sis viene da per metterlo in
contesto e per darci un esempio come noi
scorrono lungo il gasdotto Ho un molto
semplice esempio qui che è a
element-wise mi ha dato il valore massimo
di ciascun elemento sul lato sinistro
abbiamo il codice C e sul
lato destro abbiamo uno dei
molte potenziali versioni compilate di questo
codice e sto andando attraverso il
istruzione per istruzione proprio così
possiamo essere sulla stessa pagina
cosa sta succedendo qui, quindi abbiamo un
65.000 array di voci li esaminiamo ciascuno
uno individualmente se y è maggiore di
l’ elemento x quindi scriviamo la Y
elemento nell’elemento X e lo siamo
fatto ovviamente ci sono molto meglio
modi per farlo davvero
codice del mondo reale ma questo è come un
esempio relativamente semplicistico, quindi facciamolo
prendere la prima istruzione lì che
visto EI x EI x questa è una rotatoria
modo di impostare il registro EAX a zero
abbiamo i compilatori hanno deciso che il
Il registro EAX sarà dove si trova
andando a mantenere il contatore del ciclo e perché
è vero per mezzo della sega ascia e ascia si può chiedere bene
è abbastanza facile provare a te stesso
che se prendi qualsiasi numero e
esclusivo o con se stesso finisci
con 0 quindi perché il compilatore ha fatto questo
beh la risposta è l’opcode che
traduci in quello zouri un XCX
sono lunghi 2 byte per spostare l’equivalente
valore con un valore costante di 0
richiedono più byte quindi il compilatore ha
scelto una rappresentazione più piccola del
stesso funzionalmente la stessa istruzione
al fine di ridurre al minimo la quantità di codice
cache che è necessario noterete anche
se guardi un po ‘più in basso
che più avanti usa la nostra ascia ma è così
EAX in ascesa ci sono diversi
regole complicate su quali parti di
i registri vengono aggiornati con quali tipi
di istruzioni ma quando AMD si avvicinò
con le estensioni a 64 bit per Intel
set di istruzioni hanno deciso che se tu
dovevo scrivere al registro a 32 bit
cancella automaticamente i primi 32 bit
che ha un lato davvero conveniente
effetto qui di noi utilizzando un più piccolo
codifica di Zoar eax EAX che è solo 2
byte lunghi ma che cancellano l’intero 64
i bit qui se fosse tutto rax venire un rax
richiederebbe un paio di byte opcode in più
così passando alla prossima istruzione noi
avere una lettura questo è uno di quegli indici
legge che non è così complicato come
quello che ha x uno due quattro o
otto che abbiamo visto nella prima diapositiva
stiamo andando a leggere qui dal nostro
si plus r axe e per convenzione il a
un bi è che il nostro si è il secondo
parametro a questa funzione che
corrisponde al puntatore del filo
array in modo che andremo a letto che fuori
calcolando l’indirizzo di questo
elemento particolare aggiungendo l’elemento
indicale e leggilo in questo X mm
zero registrati questo è solo uno di lettura
numero doppio di precisione fuori i prossimi due
le istruzioni qui sono un confronto che
sta confrontando questo valore direttamente con
l’indirizzo di memoria della X di I così noi
non ho dovuto leggere la X di I valore
per fare il confronto possiamo
basta avere un confronto che agisce direttamente
in memoria e se il valore è inferiore
stiamo saltando sull’etichetta di qui che
salta l’istruzione successiva questo è il
equivalente al fallimento della condizione if
e andare avanti e non fare il
aggiornamento che sta per accadere
questa parte quindi è l’aggiornamento che siamo
supponendo che YI fosse maggiore di X di
Io sto solo leggendo scrivendo questo
valore di x mmm 0 nell’indirizzo del
di XI e poi saltiamo al
prossimo elemento dell’array e lo farai
notare qui il compilatore è deciso
piuttosto che usare quello x 1 x 2 x 4
Multiplet Maite lì x 8 trucco di indicizzazione
è solo moltiplicato il contatore del ciclo di
8 in tutto e aggiunge 8 ogni volta
stiamo contando in indirizzi di memoria
invece di valori I effettivi e
in modo proporzionato saremo
confrontando la fine dell’array qui con
otto volte i 65.000 in cui vado
lì e poi se non abbiamo raggiunto il
Alla fine torniamo all’inizio
altrimenti abbiamo finito, quindi spero che sia così
avuto modo ottenuto noi sulla stessa pagina quando si
arriva all’assemblaggio quindi la pipeline Intel
è una bestia molto lunga e complicata e
Ho intenzione di parlare di gruppi di
cose che vanno avanti ma che
prima di tutto qual è il gasdotto I
penso che probabilmente la maggior parte di noi lo sa
i processi moderni sono condutture
perché bene non è probabilmente mai stato il
caso che un’istruzione potrebbe completare
in un solo ciclo anche indietro nel vecchio
vecchi tempi di molto
istruzioni più semplici molto più lente
l’orologio accelera e quindi c’è sempre
stato una partizione di lavoro e nel
processi originali l’originale a 8 bit
processori certamente con cui ho lavorato
il 6502 e lo z80 ogni istruzione
prenderebbe cinque o più cicli a
completare e l’istruzione sarebbe
essere recuperare il byte che è possibile causare il
opcode fetch gli operandi eseguono il processo
Scrivi i risultati e poi lo faremo
passare alla prossima istruzione così
sarebbero stati presi quattro o cinque cicli ciascuno
vai allora la gente si rende conto che mentre
stavamo decodificando una istruzione noi
potrebbe essere andare a prendere il prossimo e mentre
stiamo eseguendo le istruzioni che potremmo
decodifica il precedente nel recupero
il prossimo ancora così facendo pipelining noi
può aumentare il rendimento in a
stile di linea di produzione che è grande così
ora ogni orologio segna una nuova istruzione
entra nella parte anteriore della pipeline e
un’istruzione lascia la fine del
il pipelining è completato quindi ogni orologio
zecche qualcosa di utile succede a noi
non sono cambiati quanto tempo ci vuole per
eseguire una singola istruzione è ancora
quattro o cinque cicli ma ogni segno di spunta siamo
ottenere una cosa in più e questo è
molto l’ approccio alla produzione
linea prende quando si guarda come auto
costruendo se tu fossi qui per parlare di jezus
ieri e stava mostrando tutto
il genere di cose da pipelining e il
lavoro che la Toyota ha fatto per
ottimizzare la loro pipeline in avanti ha fatto
anche io penso a questo, ma il problema
è quello che stai facendo un’auto a una macchina
non dipende da una macchina precedente che
è stato fatto, che non è vero per
istruzioni il flusso di istruzioni
ha necessariamente istruzione interiore
dipendenze se stai facendo un multiplo
e il moltiplicarsi richiede cinque o sei
cicli quindi si desidera utilizzare il risultato
di quello si moltiplica nella prossima istruzione
bene se la tua pipeline sei un po ‘fuori
di fortuna fino al completamento del multiplo
e devi quindi puoi iniziare il
prossima istruzione quindi cosa tipicamente
succede che il gasdotto si fermerebbe a
quel punto e la prossima istruzione che
era necessario il risultato del moltiplicare
aspettare la conclusione moltiplicata
che tipo di vergogna stiamo usando
la nostra larghezza di banda del gasdotto lì o perdere
larghezza di banda più sorta di più
è problematico il fatto che il nostro
flusso di istruzioni in arrivo non lo è
un flusso lineare
all’interno di quel flusso o un ramo che
può essere condizionatamente e così ogni volta che
il codice salta intorno e inizia ad aver bisogno
esecuzione da una parte diversa del
programma che, fondamentalmente, devono ricominciare da capo
che arriviamo al punto in cui il
ramo succede se il ramo è preso
ci va, purtroppo, tutto a posto
il lavoro che sta venendo giù il
la linea di produzione è sbagliata, dobbiamo
iniziare di nuovo e così si va indietro al
iniziando partiamo dall’inizio di
la linea di produzione ma al nuovo
indirizzo in modo che cosa possiamo fare al riguardo
bene possiamo fare un’ipotesi che è il
cosa più semplice che ne dici se in qualche modo noi
potrebbe guardare al futuro e decidere
bene ciò che è davvero così che stiamo facendo
ciò che effettivamente è la sequenza di
le istruzioni che stanno arrivando sono
non solo indirizzo uno seguito da indirizzo
a un seguito dall’indirizzo tre andiamo
avere una sorta di logica di predizione bene
abbiamo bisogno di una sfera di cristallo per risolverlo
davvero non c’è una buona risposta per questo
ma ce ne sono alcuni veramente buoni
euristica che è esattamente ciò che
quando il predittore del ramo ha così il
predittore di ramo questo succede proprio a
l’inizio della pipeline oops
prima abbiamo persino recuperato un byte di RAM
stiamo indovinando dove quel byte di RAM
deve venire da
dobbiamo prevedere se è un ramo se
c’è un ramo in arrivo dove va
e se è un ramo condizionale di cui abbiamo bisogno
per funzionare bene sarà preso
questa volta o no quindi abbiamo un po ‘
contanti e quel denaro è chiamato il ramo
buffer di destinazione e in quella cache che memorizziamo
ogni istruzione di ramo che abbiamo visto
recentemente abbiamo visto dove quel ramo
l’istruzione va e nel caso di
rami condizionali manteniamo una specie
di stato che ci dice ci dà un
predizione circa se o meno che
il ramo sarà preso la prossima volta
vederlo lo stato più semplice che potremmo mantenere
è letteralmente lo abbiamo ripreso
recentemente così un modo che è fatto è con
un contatore di saturazione a due bit che diciamo
ogni volta che prendiamo un ramo ne muoviamo uno
stage qui a destra
ogni volta che non prendiamo un ramo, noi
sposta uno stadio a sinistra e poi se
siamo nella zona verde qui debolmente
presi o fortemente presi, diciamo bene
supponiamo che lo stiamo prendendo di nuovo e
se siamo in una zona rossa diciamo semplicemente no
Andiamo avanti con il suo ignorare questo
ramo continuiamo a continuare a trasmettere da
memoria in memoria per ordinare è fantastico
questa è una cosa molto semplice da fare ma
non è molto accurato se pensi
su quali sono davvero i rami
come se avessi dei loop, andremo
sullo stesso pezzo di codice multiplo
tempi e quale caso questo probabilmente potrebbe
funziona abbastanza bene, sai ogni volta che lo fai
raggiungere il fondo di un ciclo c’è a
diramati verso l’alto e se lo hai
ottenuto come un centinaio di iterazioni di un ciclo
allora sarà più a destra della
tempo e poi stai per sbaglio
alla fine forse va bene ma se
ne hai altre più complicate
dipendono dalle dipendenze delle filiali e tu sei
praticamente per fortuna questa roba non lo è
abbastanza buono che dobbiamo prendere in un
consiglio della storia di ciò che questo
il ramo ha fatto prima forse è necessario
guarda in che cosa stanno facendo gli altri rami
il sistema e cercare di aggiungere nel
mescolare e vedere se non possiamo indovinare basato su
che quel tipo di impronta digitale di cosa
il programma è all’altezza di una cosa che possiamo
fare è tenere traccia di ciò che accade dato
la storia di un particolare ramo così
per ogni ramo in quel BTB che poco
cache ci terremo in questo
esempio ho messo quattro solo perché è
facili quattro bit di quello che è successo l’ultimo
quattro volte abbiamo visto questo ramo e poi
che andremo a utilizzare che per indicizzare in un
tabella di dato il fatto che abbiamo visto
due rami presi e poi due rami
non preso in questa sequenza che ci dà
un indice tre andiamo a guardare nel
tabella di storia cosa è successo l’ultimo
tempo abbiamo visto questo modello di rami
essere presi oh, abbiamo preso un ramo, facciamolo
prevedere che lo abbiamo fatto e poi
Ovviamente, come veniamo giro nel
l’esecuzione in realtà prende la decisione
riguardo se abbiamo preso il ramo o noi
non ha preso la filiale che aggiorna la nostra
tavolo e nel tempo impariamo dato questo
schema questo è ciò che accade che è bello
ma c’è un problema
questo è solo quattro bit di storia
le quattro volte che abbiamo visto in precedenza
questo progetto non è molto di stato
i programmi sono molto più complicati di
che non scala in tutto il tavolo
di contatori che hai visto sulla mano destra
il lato nella diapositiva precedente è di due bit
per entrata ma sale con due al
N quindi se aggiungiamo otto bit, se vogliamo
fare otto pezzi di storia e prendere in
conto degli otto precedenti rami
di questo potat casi di vedere questo
ramo precedente quindi abbiamo bisogno di 256 lotti di
due bit e quello giusto
anche quello che vogliamo avere un cache di
molti rami Biddy che non sono
andando a sporgere molto bene
ci sono alcuni circuiti in certo
alcuni dei vecchi processori Intel che
avere un tipo di ipotesi a parte
per il comportamento del circuito in cui tengono traccia
del numero di volte che il ramo è
incontrato e preso ogni volta
tranne uno che tipo di mucca copre il
caso di avere qualcosa che va
attraverso come 50 volte e non ottiene
preso 50 volte non viene preso 50
volte non viene preso bene così
probabilmente un loop di 50 che stiamo andando
per vedere di volta in volta ma um è
difficile determinare se o non
qualcosa è davvero un ciclo o se o
non è solo una condizione che è spesso
vero quindi c’è solo un limite limitato
chilometraggio e prendendo quel tipo di approccio
quello che Intel ha fatto nel loro più
la generazione recente di hardware è da prendere
una visione globale della previsione del ramo
problema prendono 32 bit di globale
storia che non è un particolare
cronologia del modello del ramo ma qualsiasi ramo
qualsiasi ramo condizionale che abbiamo visto
recentemente le 32 filiali più recenti
cosa faremo in questi casi e
invece di avere 4 GB di valore
tabella di previsione dei rami per quelli 32
bit che abbiamo hash quello in un più piccolo ma
tabella di pattern condivisa in modo che possiamo avere
piuttosto un grande tavolo di questi modelli ma
dobbiamo accettare che ci stiano andando
per essere collisioni usiamo ancora un per
tabella delle filiali per la destinazione di qualsiasi
un ramo particolare che cosa fa
sembra che assomigli a questo
quindi ora abbiamo 32 bit di cosa
la terra abbiamo fatto di recente in termini di
ramificando prendiamo che prendiamo il
indirizzo di filiale di questo particolare ramo
stiamo cercando di prevedere che li fumeremo
insieme a questo hash qui e poi a noi
andare in questo tavolo ci viene dato questo tipo
di stato del programma questo è quello che abbiamo fatto
prima e questo è veramente figo tranne
che questa tabella di storia globale non ha
idea se sia o no davvero questo
ramo che stiamo guardando a due
rami che hash allo stesso elemento
usiamo semplicemente quello che c’è nel loro ramo
tavolo il tavolo della storia mi scusi e
ciò significa che puoi entrare
situazioni in cui i rami combattono sopra il
stesso slot nel buffer e ci manca miss
prevedere molto del tempo
e ci sono modi per aggirare ciò che come
per quanto posso dire non sono in realtà
succede su chip Intel moderni ma
sicuramente altre altre architetture allora
anche come un altro predittore
di un meta predittore per ramo che
dice solo quanto spesso ho previsto questo
ramo correttamente e ogni volta che scriviamo
ci muoviamo uno a destra e diciamo va bene
faremo quello che la cosa del tavolo delle succursali
dice e ogni volta che ci sbagliamo, noi
spostalo a sinistra e poi diciamo bene
fare il contrario di ciò che la tabella delle filiali
la cosa lo fa se hai due rami
che hanno un comportamento opposto a cui atterrare
lo stesso slot almeno possiamo gestire
quella situazione ma come dico non c’è
forte indicazione che Intel sta facendo
questo dicono che non sono anche noi
non so quanto sia grande questa tabella di storia
sui ponti sabbiosi quindi la tua ipotesi è come
buono come il nostro in realtà ma supponendo che
si sa sono questi solo due bit di ciascun Sono
indovinando loro usano parecchi pezzi di
storia ma prima di tutto fa questo
in realtà contano prima di andare troppo lontano
giù questa cosa arretrata non abbiamo nemmeno
entrato nella prima fase del gasdotto
giusto ancora ci stiamo ancora provando
allenati dove diamine stiamo andando
ottenere le istruzioni da è
importante bene ecco un po ‘ di Python
codice Python è ovviamente interpretato
linguaggio ed è pieno di interni
rami all’interno del proprio interprete e
quindi sarebbe interessante vedere
se possiamo o meno vedere anche il
risultati del predittore di ramo a questo
livello e così questo esempio sta per
correre su un array e sta per somma
il totale dell’array ed è anche
andando a contare il numero di elementi
che erano al di sotto della soglia di 128 in
questo caso e riassumerà quelli
ragazzi e poi alla fine torniamo come
la media dell’intero array e il
media di quelli che erano sotto 128
se si alimenta una grande vecchia gamma di valori
in questo ognuno tra 0 e 256 questo è
cosa succede se quell’insieme di valori è
completamente casuale tra 1 0 e 255
256 scusa ci vogliono 129 secondi per
elemento ma se si ordina lo stesso input
valore quindi lo stesso set di input prima di passare
esso nella loro prende soltanto 94 906
11 e 98 mi scusi
Penso che dovrei bere qualcosa con questo 94
è un nuovo secondo un elemento che è un
accelerazione dell’8% che non è male ora come
posso essere sicuro che la sua previsione di ramo
lo sta aiutando bene perché dovrebbe succursale
aiuto di previsione qui dovrei dire prima
bene nel caso ordinato ovviamente il
prima metà della matrice questo se
la dichiarazione sarà vera andrà sempre
nel numb troncato e il totale del clip
più è uguale a uno quindi da qualche altra parte
ramo è uno dei tanti rami
all’interno dell’interprete sarà sempre
non preso in quanto non salta il se
dichiarazione quindi corriamo attraverso il primo
metà dell’array e noi colpiamo il piede
agganciare il primo valore che è 128 e a
quel punto la previsione è sbagliata
speriamo però entro il prossimo 2 2 o
3 iterazioni lo avremmo imparato
in realtà questo è ora il nuovo il nuovo il
il nuovo ordine mondiale è quello che saremo
prendendo questo ramo ogni volta e noi
quindi prevedere correttamente da quel momento in poi
quindi sembra una previsione di ramo
ottenere la previsione del ramo proprio qui
sarebbe utile mentre nel caso
caso ovviamente il predittore del ramo è
sta andando a cercare di dedurre uno schema
per questo da questa affermazione se siamo
in effetti nessun modello esiste affatto lì
sono una varietà di strumenti che puoi eseguire
e ho corso uno chiamato perf che sono io
consiglio vivamente per questo tipo di
investigazione e se corri con loro
senza i dati ordinati puoi vederlo
lo stesso numero di istruzioni è
preso lo stesso numero di CPU in pensione
istruzioni che passano attraverso il sistema
lo stesso numero di rami è
incontrato incontrato ma il ramo
il tasso di previsione è molto diverso
tra i due quindi non è nessun altro
artefatto per quanto posso dire anche se
è ancora sorprendente per me che in un
linguaggio interpretato può ancora avere importanza
quello che puoi fare su questo non lo so
in senso pratico per questo particolare
esempio di giocattolo comunque ok
quindi ho fatto un caso ragionevole sul perché a
predizione delle diramazioni è utile ciò che
succede una volta che abbiamo previsto dove
il flusso del programma sta andando bene i risultati
del predittore di ramo sono un flusso di
l’indirizzo di istruzioni è come dove
vogliamo essere da prendere e quello
passa al primo stadio che è
questa fase di recupero e pre decodifica
il futuro è responsabile della lettura
il flusso di istruzioni è responsabile
per fare le ricerche TLB il
traduzione da virtuale a indirizzo fisico
e per lo streaming in blocchi di
istruzioni le istruzioni sembrano
qualcosa come questo
il fetcher li legge in sedici byte
pezzi e ha una cosa interessante
fare prima su così in giù sul
pipeline che vogliamo sbloccare tanto
parallelismo possibile e questo significa
che vogliamo fare in realtà più di
un’istruzione alla volta se questo è a
tutto fattibile ma a causa del lungo e
storia torturata della x86
architettura stiamo tipo di sinistra con
questo strano formato di codici op che no
essere razionale sarebbe venuto con
quindi se si guardano le istruzioni RISC
al giorno d’oggi sono di solito di dimensioni fisse
molto facile vedere dove ogni istruzione
è ma in una sequenza intel non c’è
modo ovvio per determinare dove
i byte sono ci dispiace dove il
le istruzioni sono all’interno di quel flusso di byte
questo è ciò che fa il fetcher
e si affaccia per l’inizio del
ogni istruzione che è sorprendente
risultato se ci pensi in 1
o 2 cicli di clock
è in qualche modo scansionare questa lista di
istruzioni decodificate dove l’inizio
di ogni istruzione forse e in qualche modo
fatto ciò in parallelo perché
necessariamente l’inizio di uno
l’istruzione segue dalla fine di
l’ istruzione precedente c’è a
dipendenza da ciascuno portato avanti
quindi l’unico modo in cui posso pensare di essere
fare è in qualche modo come la decodifica parallela
tutti i 16 possibili posti nel
flusso di istruzioni in cui le istruzioni
potrebbe essere e quindi in qualche modo filtrare
quelli che non hanno senso ma
qualunque cosa sia, è un risultato incredibile
e così questa istruzione scorre qui
questa sequenza di byte è in realtà il
prime poche istruzioni dell’esempio I
ti ho mostrato prima ci sono quei due
byte o EAX EAX e puoi vedere che abbiamo
tirato fuori quattro istruzioni qui e
allora abbiamo la F 200 F che io
non ho messo qui così al
inizio della prossima istruzione nel
flusso che sarà in qualche modo dipendente da esso
all’inizio del prossimo recupero
il prossimo ciclo
Sono costantemente là fuori e ho
Mi dispiace, quindi abbiamo i nostri quattro
oh si scusa a quel punto qui il
il pre decoder non sa cosa questi
le istruzioni sanno solo dove sono
si trovano nella sequenza di byte che c’è
questo è tutto quello che possono fare e loro sono dati
la quantità di tempo che devono fare
questo ma quei byte poi fluiscono come a
sequenza di byte e offset dove il
le istruzioni possono iniziare nello stream
sulla fase di decodifica che è dove
finalmente gli ingegneri Intel hanno una sorta di
ammesso la sconfitta di questo davvero
complicata istruzione bizantina
sequenza e hanno deciso che vogliono
qualcosa di più puro dentro così a questo
puntare le costruzioni SIS che arrivano
attraverso sono convertiti in una sorta di
rischio interno ora Intel non pubblicamente
scusami fino a quando non pubblichi il formato
di questo rischio interno ce ne sono alcuni
sorta di letteratura su dove il
le unità di esecuzione usano i vari tipi di
micro operazioni quindi in micro operazioni
è ciò che chiamano questo questo rischio
impostare e all’interno di tali micro operazioni
le istruzioni più complicate come
l’istruzione di lettura-modifica-scrittura che avevo
nella prima diapositiva il carico da a
aggiungere complicati indirizzi di memoria e
memorizzarlo di nuovo in realtà devolvere nella
tre istruzioni che qualsiasi normale
persona avrebbe scritto in un RISC
mondo è una cosa davvero importante
fare perché più avanti lungo la linea siamo
andando a essere in grado di rompere quelle parti di
le istruzioni e programmarle
in modo diverso che se parti del chip
sono occupati come se il moltiplicatore fosse occupato
possiamo ancora fare la parte di carico di un carico
istruzione che il moderno ha a
componente moltiplicatore ad esso possiamo
potenzialmente avere un se è sì mi dispiace
questo è probabilmente un buon esempio
scusa per aver infranto le istruzioni
pezzi aiuta perché possiamo pianificare
le singole parti in giro e abbiamo
molto più fedeltà in seguito per
cose paralizzanti che non lo farebbero
altrimenti essere paralizzato se abbiamo appena
ingenuamente li teneva come istruzioni atomiche
che abbiamo scritto per iniziare con i decoder
qui può gestire fino a quattro istruzioni
in un unico ciclo che è impressionante così
quelle quattro istruzioni che ti ho mostrato
la diapositiva precedente verrà visualizzata
nella fase di decodifica e lo saranno
trasformato in micro operazioni in uno
ciclare quelli
c’è una certa complessità con il
diversi decodificatori il primo decodificatore per
esempio è in grado di decodificare
assolutamente qualsiasi tipo di istruzione e
generando un numero qualsiasi di micro
operazioni mentre gli altri tre
decoder che ci sono in
parallelo può solo fare il più semplice
istruzione quindi c’è un qualche tipo di
chilometraggio in programma con molta attenzione
le tue istruzioni in un particolare
modello per consentire loro di scorrere attraverso come
il più velocemente possibile sui nuovi processi
questo è meno importante a causa del
micro cache di cui parlerò in a
secondo, ma vedrai se mai andrai
nelle profondità profonde di simili GCC
programmatore di istruzioni interne che prova
è meglio spostare le cose per adattarle
questo tipo di schema e davvero in realtà
è una specie di nota a parte se tu se tu
aprire uno dei posti migliori per ordinare di
vedere la documentazione per questo per il
reverse engineering di ciò che accade
dentro è guardare dentro le viscere di
il compilatore come ce ne sono alcuni
automi all’interno del compilatore che ha provato
di prevedere quello che il processore fa
internamente e programmare le istruzioni a
adattarsi con il flusso previsto così noi
hanno questi quattro decodificatori e li emettono
queste micro operazioni ad altre cose
prendere parte a questo punto abbiamo micro
fusione che è il nome per prendere due
micro operazioni e tipo di trattamento
li come uno anche se abbiamo attentamente
li devoluto in diversi pezzi che
occupa molta banda se tu
immagina di avere un flusso di
le istruzioni che arrivano sono una specie di
espandendo il numero di operazioni
quindi abbiamo una sorta di fan di cose
andando fuori di testa cosa succedendo e quello
ovviamente consuma risorse sul chip
quindi per le operazioni molto comuni come
negozi che richiedono un indirizzo
calcolo così come il negozio reale
beh non hanno più bisogno di temporanei
spazio ci sono due pezzi separati di
lavoro uno è quello di calcolare l’ indirizzo e
uno di loro è quello di fare il negozio ma
Non sarebbe bello solo per ordinare di
trattali come un’unità atomica come loro
scorrere lungo la conduttura e ma giusto
pianificare questi due bit in modo diverso
questo è ciò che sta facendo la micro fusione
due miei raccolti e tipo di loro raggruppamento
insieme come una specie di cianfrusaglie
fare insieme e poi ne abbiamo di più
importante fusione macro che è dove
il contrario accade piuttosto che
più micro operazioni
generato da un singolo input
istruzione prendiamo due input
istruzioni e possiamo bere generare
solo una micro operazione un esempio di
questo è il confronto seguito da un ramo
è così comune che vorremmo
come confrontare il nostro contatore di loop con alcuni
valore
e quindi ramo se non uguale o
decrementa un valore e nel ramo se
non è zero quel tipo di cose che
la maggior parte delle istruzioni dell’insieme di istruzioni
i set hanno effettivamente un decremento e salti
se non tipo zero di sentirsi x86
dozzina ma a questo punto se ne hai due
istruzioni una dopo l’ altra che hanno
questo modello sarà trasformato in a
singola operazione micro così abbiamo tipo
guadagnare un po ‘di questo
fan-out che stavamo ottenendo da da
più in basso nel Sandy Bridge e
sopra c’è qualcosa chiamato micro
contanti di operazione a questo punto anche così
abbiamo già l’orologio ha già
spuntato come sei o sette volte per arrivare
questo punto e quindi un sacco di cose
prezioso lavoro è stato fatto sarà
utile per aggrapparsi a quell’intermedio
risultati soprattutto se le volte che stiamo andando
per rivisitare questo codice in breve
ordine
così la cache di micro-operazione memorizza il
risultati delle operazioni decodificate a
questo punto ci sono circa 1.500 voci
ed è una sorta di cache molto complicata
che non è mappato a un normale come Urim
memoria cache nel modo in cui tu
probabilmente penserei ma se solo tu
pensala come qualcosa che può
tenere un loop piuttosto piccolo in è utile per
ma la ragione per cui questo è utile è
che quando facciamo un ramo più tardi, se noi
scopri che abbiamo sbagliato
lungo la pipeline ma il
la destinazione di quel ramo è all’interno del
cache dei microbi non dobbiamo andare tutti
la strada verso la parte anteriore della pipeline noi
può fare un cortocircuito e iniziare da
la cache di micro rob e solo da allora
in poi dobbiamo iniziare
istruzioni di ritrattamento che riduce
la latenza di un ramo imprevedibile così
anche se abbiamo investito tutto questo tempo
prima cercando di capire in che direzione il
il ramo sta andando se ci sbagliamo il
la cache delle micro-operazioni può salvarci un po ‘
di tempo recuperando da quello che ho
ha detto che la mia Intel non me ne frega molto
esempi di ciò che la loro micro operazione
per uno sembra così ho un po ‘su
il lato sinistro qui dato un esempio
del codice di nuovo e sulla mano destra
lato ho inventato il mio tipo di formato
per quello che potrebbero fare queste micro operazioni
Assomiglia a
quando la convention che ho qui è
quella linea di testo è un micro
operazione così le cose che voglio
sono alcuni punti in questo flusso
che confronta le istruzioni che confronta
con la memoria è alle micro operazioni
c’è una sorta di valore temporaneo e
temporaneo senza nome che viene letto e
allora il confronto avviene come un secondo
micro operazione separata e poi lì
in fondo al ciclo quello che abbiamo
perso in quell’unica micro operazione in più
tipo di artiglio qui perché il
compare seguito dalle mappe di salto in a
singola micro operazione che è la
fusione macro ma anche questo non è proprio
quello che è successo così a questo punto questo
modello mentale di cui potremmo avere
mettere il codice side-by-side non lo è
ciò che il processore sta vedendo in questo
punto perché ciò che il processo è davvero
vedere ovviamente è una sequenza di
istruzioni che fluiscono linearmente verso il basso
il programma previsto ordina il ramo
il predittore ha fatto la sua magia noi abbiamo il
fetcher è solo prendere qualunque cosa sia stata
detto di andare a prendere e questo è ciò che scorre
giù così ho cercato di catturare
questo su questo scivolo qui dove sul
proprio sul lato sinistro che ho tipo
metti l’indirizzo per darti un’idea
e per mettere in evidenza ciò che intendo
qui prendi questo confronto qui
è uno dei paragoni attorno al se
X è maggiore di Y e in questo caso
Ho arbitrariamente deciso che il
predittore di ramo ha previsto che questo
particolare sta per essere presa in modo
piuttosto che il prossimo essere dell’istruzione
i Nordics 14 che sarebbero i prossimi
indirizzo delle istruzioni ho detto hey noi
penso che questo andrà a 19 andare a
19 ora e così è la prossima cosa
che sta per essere in dirittura d’arrivo
Allo stesso modo qui è il ciclo al
in basso dove abbiamo fatto il confronto e
se non è uguale e ovviamente per il vasto
maggior parte dei casi che sarà
preso come per tutti tranne uno
iterazione che sta per essere il caso
quindi speriamo che il predittore sia indovinato
che così ancora una volta la prossima istruzione lo farà
essere di nuovo all’inizio del ciclo e poi
quaggiù solo per il confronto
questo è stato previsto non è stato preso così
piuttosto che essere l’indirizzo esadecimale di
il prossimo è il prossimo
indirizzo lineare in memoria all’esagono 14 ora
ovviamente questo onore di sottolineare cosa
succede quando il ramo arriva davvero
essere eseguito e questa è la succursale
devo dire bene da che parte è fatto davvero
andare e avevo ragione e se non ho ragione
cosa faccio bene abbiamo già detto
di
stiamo andando a lavare la pipeline ma
come succede questo parleremo
quello in un secondo
okay, quindi abbiamo decodificato il nostro flusso di
le istruzioni siamo circa le sei e sette
il ciclo di clock dipende dal modello
giù quelli lungo il gasdotto e noi
colpire questa cosa chiamata il renamer il
il tipo di rinominatore prende un’altra vista di rischio
e in qualche modo trasforma l’ istruzione x86
impostato per adattarsi così solo l’x86
questi otto o sedici in modalità 64 bit
registri che possiamo parlare
ignorando i registri xmm per ora ma
se guardi qualsiasi chip di rischio ci sono
centinaia se non migliaia di disponibili
registra perché è così bene se vuoi
per separare le nostre istruzioni indipendenti
scorre e ha parallelismo inter
parallelismo delle istruzioni che devi essere
non calpestare i tuoi registri allo stesso modo
tempo se usi lo stesso registro due volte
bene devi aspettare per il precedente
utilizzo da finire prima di poterlo riutilizzare
fare qualcos’altro era il
caso in cui i registri hanno preso un sacco di
immobiliare se guardi come vecchio
schemi circuitali o altri vecchi
muore di come il 6502 per esempio
c’è un grande progetto in cui le persone
hanno preso la cima di 6502 se
scansionandoli ad alta risoluzione
telecamere e in modo letterale come supporto
fuori dove ogni singolo transistor è ma
possono disegnare qualsiasi tipo di diagramma di
dove tutto è puoi vedere che il
i registri sono in realtà un sostanziale
blob of the the color che non è più
il caso rispetto a come le cache
che sono lì e tutto il
logica complicata i registri sono a
piccola proporzione, quindi potendo essere solo in grado
per codificare 16 nel formato anche con tutti
le estensioni che ci sono sono gentili
di una limitazione per questo così il renamer
fa analisi di dipendenza al volo e
trasforma il tuo codice in single static
modalità di assegnazione scusa forma e poi
costituisce un temporaneo intermedio intimo
valori e li mappa in una sorta di a
suite di un centinaio di istruzioni
come mi dispiace scusami un centinaio o più
registra così non abbiamo bisogno che non siamo
più a lungo rispetto ai sedici registri
quello è venuto
in possiamo usare questi valori intermedi
tutto e questi intermedio
esempio è piuttosto la cosa migliore
fai qui così qui sul lato sinistro
Ho un esempio leggermente diverso
abbiamo una routine che richiede due
valori e incrementi di due diversi
Globale e abbastanza ragionevolmente qui è un
pezzo di codice che il compilatore potrebbe avere
output che viene letto globale a in
EAX aggiunge X al primo parametro e
memorizzarlo e poi lo stesso di nuovo per
B nota che sta usando nuovamente EAX due volte
piuttosto ragionevole, ma se quella lettura prende un
molto tempo e penso che lo sappiamo tutti
accedere alla memoria di solito è piuttosto lento
allora bene è chiaro e ovvio
queste due istruzioni dopo di ciò che
dipende dal valore che non può essere eseguito
bene, ma abbiamo usato EAX nel prossimo
blocco di codice cosa succede se globale B
è già nella cache un pasticcio se
dovevamo farlo se avessimo usato un altro
registrati qui forse questo potrebbe essere stato
in programma ma abbiamo usato Dax che non possiamo fare
sarà calpestato da
qualunque sia questo flusso di istruzioni
facendo così il renamer dà un’occhiata a
questo lo inserisce nel modulo SSA e viene visualizzato
con qualcosa che sembra un po ‘
come questo di nuovo non c’è tipo di
formato documentato per questo quindi ho gentile
di usato come suffisso su ciascun registro a
sorta di indicare il nuovo nome che ciascuno
registro ha quindi piuttosto che EI X sul
lato sinistro abbiamo EE X sub 1 e
quindi aggiungiamo EI X 1 a EDI 1 e scriviamo
il risultato a un nuovo temporaneo
registro intermedio chiamato EDI 2 e
questa è la cosa che scriviamo di nuovo
di nuovo e poi in modo critico in questo
secondo blob, abbiamo determinato questo
il valore di EI X è completamente indipendente
del valore precedente di EI X potremmo
come pure abbiamo usato un altro registro noi
avremmo potuto fare non potremmo avere
codificati o l’ABI ci ha costretti a utilizzare un
particolare registro architettonico nominato
e ma a questo livello all’interno del chip noi
possiamo crearne uno nuovo , possiamo solo dire hey
chiamiamo questo EI X sub due e ora il
Orb scusa e ora quei due pezzi di
i codici sono indipendenti l’ uno dall’altro e
può correre insieme in parallelo o in grado di
vai di fronte all’altro e sblocchiamo
parallelismo che altrimenti lo farebbe
sono stato
impedito il modo in cui è realizzato è
guarda il renamer tiene traccia di quale di
questi registri temporanei intermedi
contiene la versione corrente di qualsiasi di
l’architettura nominata la registra
è la tabella alias di registro e mappa
in un buffer di riordino che è
come una base graffiata temporanea di tutti
di queste micro operazioni che hanno ancora
da eseguire o aver eseguito ma
non ho ancora finito o completato
mappe nel file di registro permanente
che è come il luogo canonico dove
la vera EAX e il vero edx live
interessante fino in fondo
Sandy Bridge tutto ciò che è complicato
una sorta di logica interna in cui tutto questo
queste varie cose vengono mescolate
intorno e previsto o qualunque cosa non fosse
il collo di bottiglia il fondo effettivo che
era questo PRF leggere qui quindi se se lo hai
modificato un registro recentemente sta andando
vivere in uno di questi temporanei
variabili che sono dentro questo questo
Oltre 100 serie di risultati intermedi
ma se non hai modificato un registro
la ragione di recente è nel reale
registrare il file nel permanente
registrare file e in questa fase come noi
lasciare il rinominatore qualsiasi istruzione
ha bisogno del vero EAX e della vera EAX
non è già nel vero debuff
dobbiamo leggere dal permanente
registra il file e inseriscilo ma
ci sono solo tre porte di lettura sul
registra file che significa che in qualsiasi momento
avevi bisogno di più di tre registri
che non era stato modificato di recente da te
richiederebbe più cicli di clock per leggere
loro e ora sembra molto
tre registri ogni singolo ciclo di clock
tranne che ormai abbiamo devoluto il nostro
istruzioni nel flusso di micro operazioni
ogni micro op ha fino a tre operandi
e stiamo cercando di farne quattro a
una volta così possiamo facilmente escogitare 12 e
questo significa che ne prenderemo quattro
tic tac dell’orologio solo per passare al successivo
stage così per fortuna su Sandy Bridge e
sopra hanno riparato questo e tu no
vedo più questo come un problema
Supponendo che voi ragazzi siete su dei sandwiches
corsi
l’altra cosa che renamer è intelligente
abbastanza da fare è capire questi divertenti
piccole cose come questa o XCX siamo noi
fatto prima in modo così ingenuo se eri solo
monitoraggio come il valore di ciascuno o
piuttosto se fosse o meno un registro
dipende da una precedente incarnazione di
che fa registrare il presente è tutto EI sguardi XCX
come dipende dal precedente
valore di EI X e non è rinominato
è abbastanza intelligente da sapere che questo significa
dammi una nuova EI x inserisci il valore 0 in essa
e andare avanti con la tua vita e in effetti
nella cosa più nuova
i chip più recenti come Ivy Bridge e
più recente a quel punto la micro operazione
in realtà cade fuori dal gasdotto che non facciamo
è necessario fare altro lavoro il lavoro è
fatto solo assegnando un nuovo spazio vuoto
che ha un valore zero in esso per alcuni di
le istruzioni e quelle che piacciono
confronta non con te stesso che per il
registri xmm imposta tutto su quelli
può anche accadere sui ponti dell’edera a
questo punto e nel registro si muove così
spesso di nuovo per adattarsi all’ABI dove
stiamo spostando i valori tra i registri
solo per essere sicuro che le cose siano nel
È disponibile il registro EDI pronto per
chiamare una subroutine bene tutto ciò che è la sua
solo un aggiornamento contabile se pensiamo
è il valore più recente di EDI
slot 7 beh questo è quello che ci serve
registra ok è nello slot 7 di tanto in tanto
la nota che la mossa stessa non ha
succede così molte delle istruzioni possono
essere sbucciato un sacco di simili
istruzioni intermedie le mosse e
i turni scusate le mosse e il
l’ORS esclusivo con il sé può effettivamente
scomparire il flusso di istruzioni a
questo punto e aggiorniamo solo le nostre tabelle
quindi il buffer di riordino è temporaneo
zero spazio di questi cento dispari
elaborare i miei raccolti e i loro operandi il
riordinare il buffer mantiene lo stato che conosce
qual è la micro operazione, conosce il
input e nel caso di micro
operazioni che non hanno i loro valori
pronto sa quali sono le altre operazioni
aspettando e snoop i risultati di
completare le istruzioni come a
l’istruzione dipendente completa il suo
trasmesso attraverso un bus interno
e ogni micro operazione che sta aspettando
per quei risultati ora puoi leggerlo
memorizzalo e diventa pronto per eseguire questo è
anche il palco dove quel permanente
registro letto succede
e a questo punto le micro-operazioni
rimanere nel buffer fino all’ultimo
fase della pipeline okay siamo quasi
nel punto in cui ora stiamo andando
entrare nel territorio magico di effettivamente
eseguendo queste istruzioni e per il
prima volta che andremo a uscire
ordina le stazioni di prenotazione proprio come
l’ ultimo passo questo è dove una sorta di
algoritmo di programmazione che di nuovo è molto
molto vagamente descritto nella letteratura
è responsabile di elaborare quale di
le micro operazioni stanno per andare a
quali parti del chip sia effettivamente
eseguito ci sono sei porte di esecuzione
e ogni porta di esecuzione può fare solo un
sottoinsieme di istruzioni c’è un sacco di
si sovrappongono tra loro ma c’è lì
anche come aree uniche che possono solo fare
un particolare tipo di istruzione e
quello sembra oh siamo qui sì così abbiamo
abbiamo davvero intenzione di parlare di cosa
quali parti fanno ciò che ora abbiamo appena fatto
la parte superiore qui che è l’inorder
parte della coda e ora siamo nel
scheduling domain down here ed è
vale la pena parlare di queste porte qui così
abbiamo le sei porte a questo è dispiaciuto
c’è Sandy Bridge ci sono sei porte
le prime tre porte qui che sono
piombo ossimorico zero uno e cinque loro
tutti hanno una ALU attaccata a loro così tu
tutti possono fare le semplici operazioni di spostamento
se non sono già stati rinominati
di esistenza possono fare turni che possono
fai tutto ciò che possono fare in esclusiva o loro possono
fare confronti e cosa significa questo
quello in ogni spunta se ce ne sono tre
semplici operazioni pronte possono tutti
iniziare l’esecuzione significa che lo abbiamo
ora ha iniziato a fare tre cose contemporaneamente
è fantastico se stai facendo carichi o
negozi è possibile fare uso di queste porte su
qui le porte 2 3 e 4 dobbiamo caricare
porte e una porta del negozio in modo da poter vedere
che questo tipo di un po ‘di contesa
lì in termini di numero di questi
le cose stanno succedendo c’è una cosa in più
riguardo ai negozi come ho detto il
le modalità di indicizzazione sono davvero complicate
può avere come questo indirizzo di base più due
si registra con uno di loro
moltiplicato per un valore costante potenza a
costante per quattro motivi non lo faccio completamente
capisci almeno su Sandy Bridge
questa quarta porta la porta del negozio no
avere la logica del circuito per farlo
calcolo dell’indirizzo e così ogni volta che tu
fare un negozio non è solo il caso
hai due caricatori in un negozio così
c’è un
disparità tra loro ogni volta che lo fai
un negozio deve prendere in prestito uno dei carichi
unità solo per fare il calcolo dell’indirizzo
e questo è un esempio di quelli
micro-operazioni fuse dove c’è un negozio
sia il calcolo dell’indirizzo che il
caricare ma prende in prestito due porte a
una volta anche se è solo una reale
slot nel buffer di riordino altre cose
notare qui è che una volta entrati
le istruzioni più complicate come
il punto in virgola mobile si moltiplica e aggiunge
vari shuffle ce ne sono solo uno o
forse due unità che possono farlo funzionare
che limita la quantità di quelli che possiamo
fai subito sì sei unità che è sì noi
hanno sì sei unità sono per lo più
pipeline di se stessi in modo che significa che
ogni unità lo stanno moltiplicando
potrebbe richiedere sei unità per sei cicli di clock
completo ma possiamo iniziare una nuova moltiplicazione
ogni singolo ciclo quindi anche se il
i risultati individuali di uno moltiplicano
non siamo pronti fino al sesto tick possibile
iniziare una nuova ogni ogni ciclo di clock
questo significa che il tasso scende
qui ci sono fino a tre cicli
quello che stavo dicendo con quelle ALU con
il fatto che abbiamo tre unità ALU
significa che ogni singolo clic clic
orologio possiamo iniziare un tre di quei ragazzi
possiamo solo iniziare un punto in virgola mobile
moltiplicare ogni ciclo di clock che è a
peccato in questo caso anche io sono solo
parlare di come lo scalare si moltiplica
questo può succedere se stai iniziando
usare le istruzioni X mmm per fare come
più punti mobili fluttuanti in
parallelo dove ti piace avere quattro o
più imballato nella XMM registra solo
uno di quelli può iniziare ciascuno, ma
sono come quattro multipli indipendenti
o otto a seconda della larghezza del tuo
registri c’è un altro tipo di
componente così come il throughput
problema di quanti ne possiamo iniziare ciascuno
spuntare abbiamo la dipendenza tra
istruzioni così per operazioni logiche e mosse
se inizi una mossa o un’esclusiva o
i risultati già al prossimo tick così
la prossima istruzione dipende da questo
potrebbe iniziare il ciclo successivo per
l’intero si moltiplica in tre quattro
la virgola mobile si moltiplica come ho detto
una specie di cinque ish sei per radici quadrate
1024 per divisione e resto siamo
cercando ovunque tra il 24 e l’ 84
dipende da
i dati effettivi che stai utilizzando e il reale
la cosa fondamentale di questo è che non è così
pipeline possiamo solo emettere
ha solo una divisione intera in corso a
una volta così in netto contrasto con quelli
moltiplicatori che sono in corso in cui siamo
può avere 301 alla volta ma tu ne conosci uno
uno ogni singolo ciclo a divisione o a
resto sta andando a prendere 80 cicli
ottieni il risultato e non possiamo farlo
l’altro divide i resti in modo che tutti
le tue tabelle hash che hai scritto
dove stai usando il modulo con
forse un numero primo di tavolo
dovrebbe prendere in considerazione l’ utilizzo di un altro
complicata funzione di hashing che utilizza
moltiplica i turni di spostamento ORS esclusivi
che possono essere tutti calcolati molto più velocemente
e poi termina con il potere di
due per adattarsi a una tabella di potere per dimensioni
piuttosto che aspettare 80 cicli per
ti dividi, sai di avere un livello più alto
la funzione hash di qualità potrebbe essere migliore
Scambio comunque comincio a finire
di tempo um questo è il mio tuffo veloce data
nella scusa per il motivo per cui non posso avere 4
gigabyte di cache Ram perché ci vuole 3
a 250 cicli per accedere a Ram sul
lato sinistro qui ho un po ‘ di
Ram statico che potresti trovare in
il tuo cache sul lato destro che ho
un po ‘di DRAM ora è abbastanza chiaro
che il lato sinistro è molto di più
complicato rispetto alla parte destra ma
perché è così male sulla sinistra?
lato abbiamo questo è un dispositivo logico puro
un componente discreto possiamo essere a 0 o 1
fuori da questo in ogni momento, ma richiede
potenza costante richiede 6 transistor
e un mucchio di complicate sovrapposizioni
fili che rendono molto molto difficile
per spiegarlo in modo ad alta densità
un chip
Non so come faccia a farlo Intel, ma tu
guarda il dado e c’è questo
belle aree che sono chiaramente il
cache della stessa cosa più e più volte
di nuovo ma in qualche modo sono stati in grado di farlo
fatelo ma è affamato di potere
significa che riscaldarsi è un problema per
per la dissipazione del calore um ma è una logica
dispositivo che è grande sulla mano destra
lato abbiamo qualcosa che è un
componente analogico
questo condensatore quaggiù ne conserva alcuni
numero molto piccolo di elettroni da immagazzinare
se c’è uno zero o uno là
il che significa che non abbiamo bisogno di pagare
alimentandolo quando non stiamo accedendo
possiamo spegnere il sistema e lo farà
essere lì tranne che poi si scarica via
tempo quindi dobbiamo restare occasionalmente
rabbocco che riduce la nostra memoria
larghezza di banda che dobbiamo continuare a utilizzare
solo per continuare a riempirlo, ma di più
importante ogni volta che leggiamo da questo
non è la conversione da analogico a digitale che
richiede tempo quindi il perché dovremmo farlo
questo bene, ovviamente , non abbiamo bisogno di energia
tutto il tempo è fantastico
questi sono molto più semplici che possiamo
esponete questi elementi a una densità molto più alta
ecco perché le tue celle DRAM sono molto
molto più strettamente imballato e tu
può avere i tuoi gigabyte di RAM e
ovviamente l’ altra parte è questa
la DRAM di solito è fisicamente
separato dal chip piuttosto che
essere sulla morte come tale questa propagazione
ritardi ci vuole solo un po ‘di tempo
le sfortunate leggi della fisica sono contrarie
questi elettroni non si muovono da nessuna parte vicino
la velocità della luce e stanno andando a
spostare abbastanza lontano dal chip RAM
per entrare nel processore così è gentile
delle mie scuse per il motivo per cui non possiamo avere un sacco
di cache Ram c’è qualche esempio
orari qui e penso che abbiamo tutti noi
sappi che è meglio tenerlo
le cose in un livello memorizzano nella cache il
cache di livello inferiore che memorizza nella cache lo faremo
esplosione attraverso quest’ultimo paio di bit
ecco quindi l’ultima cosa che succede è
quando l’istruzione ha completato
trasmette il suo risultato che libera qualsiasi
delle micro operazioni che stanno aspettando
per essere programmati diventano pronti per essere eseguiti
se sono nel qual caso lo scheduler
li raccoglierò il prossimo segno di spunta che abbiamo
ho alcune cose complicate da ripristinare
inoltro che ho il tempo di parlare
circa ora e l’ultimo stadio è questo
fase di pensionamento che è dove alcuni di
la magia migliore accade così nel
fase di pensionamento finora abbiamo tipo di
ogni istruzione che è stato volato giù
la pipeline è stata una transazione
è ancora da impegnare anche se possiamo avere
leggi dalla memoria tutti i diritti che abbiamo
fatto ho una sorta di rintanato in una memorizzazione
buffer che non ha ancora fatto perché
è così importante che abbiamo noi
riordinato tutto lungo la strada cosa
succede se ne abbiamo uno che è un ramo
è sbagliato ma cosa succede se ci ha portato
un po ‘per scoprirlo già
ha iniziato a fare parte del lavoro che è stato
l’altro lato di quel ramo di cui abbiamo bisogno
disfare quel lavoro e il modo in cui è
fatto è semplicemente non commettendo il
l’istruzione fondamentalmente sta spazzando via quello
transazione
l’ istruzione è iniziata e non scritta
torna al file di registro permanente no
permettendo al negozio di fluire effettivamente
verso l’ esterno del chip di no
permettendo che l’istruzione si ritiri
analogamente le eccezioni come / zeros significano
potrebbe essere il caso in cui divido il
i valori per una divisione non si sapranno risalire
davanti e così istruttori oltre il
il divario è già finito in
completato ma la divisione per zero deve
capita con il vecchio valore di quelli
operandi e c’è un questo tipo di
questo sta iniziando a diventare esposto a
il modello di programmazione elenca questo insieme
idea di avere questo tipo di
istruzioni transazionali dove così per
esempio ha ben presente questo software
modello di memoria transazionale dove puoi
chiedi di essere informato se se varie parti
della RAM sono accessibili mentre stai lavorando
e abortire e una serie di istruzioni così
che un’operazione atomica dal tuo punto
di vista non richiede un blocco solo
indica il rollback della transazione
Da allora ho scoperto che non lo è
effettivamente fatto da efficacemente come il
è la stessa logica della previsione del ramo
probabilmente fatto a livello di cache ma
si parla nel lago del cielo che è
come due altre revisioni su di loro
esponendo questo livello di istruzione
transazione per noi come programmatori okay
siamo arrivati alla fine, è terribile
molte cose che stanno succedendo sotto il
cappa e non penso di avere tempo per
domande a giudicare dal tempo ma
la ringrazio molto per il vostro tempo in cui
ci sono alcune risorse di esempio
lassù grazie
continua all’interno dei processori Intel che
guida molti se non tutti i nostri server
computer portatili e desktop e mi verrà insegnato
di entrare nei dettagli un po ‘
quindi spero che mi perdoni se ottengo
nelle erbacce con un po ‘di montaggio sul
schermo ma prima di andare troppo lontano su I
avere una ammissione il mio discorso si chiama x86
per divertimento e profitto
e la mia intenzione originariamente doveva venire
con alcuni indicatori davvero forti
su come potresti ottimizzare il tuo codice
come puoi profilare il tuo codice come
capire gli interni del
la macchina può darti un’idea di
migliorando il tuo codice ma c’è così tanto
per coprire ed è così interessante, solo
volevo coprire le cose che penso
sono interessanti e si spera lungo il
modo noi prenderemo un po ‘insolito
indicatori di comportamento che possiamo cercare
e qualche oggetto di ottimizzazione
opportunità ma principalmente questa roba è
solo molto interessante e se niente
altrimenti voglio che tu vada via dalla fine
di questo discorso e avere un nuovo
apprezzamento per ciò che sulla terra Intel
e gli ingegneri AMD sono stati in grado di fare
dietro la facciata x86 che ci danno
e in effetti hanno una sorta di simpatia
per quelle persone tra noi che scrivono
compilatori e squadre investigative comuni e che stanno cercando di
una specie di reverse engineer e take
vantaggio di tutto questo fantastico
potere di fronte a noi in modo da Intel sono
notoriamente a denti stretti su ciò che accade
oltre il set di istruzioni x86
loro hanno circa sette o otto piedi
un sacco di manuali che puoi ottenere
avere tutti i modi di attuare in dettaglio
sul singolo op codifica il byte
codifica le modalità di gestione del sistema
funziona e tutte quelle cose ma non lo fanno
in realtà ti dico come funziona dentro
principalmente perché credo che non vogliono
fare l’occhiolino agli altri
abbastanza giusti anche loro non vogliono che lo facciamo
trarre troppa vantaggio dalla parte interna
di un chip in cui possono cambiare da
revisione del processore alla revisione del processore
ma per fortuna ci sono alcune persone fuori
là chi è abbastanza pazzo da farlo
il loro hobby o passatempo per provare e
decodificare il più possibile
su cosa succede sotto e questo
parlare non sarebbe stato possibile senza a
sacco di
aiuto da un ragazzo potenzialmente chiamato
Agron of fog che è all’Università di
La Danimarca penso e l’ ha fatta sua
il lavoro della vita per sedersi e scrivere test
caso dopo caso di test dopo caso di test e
utilizzare tutta la gestione interna
contatori che si trovano all’interno del chip e
in qualche modo cercare di ricavare ciò che sta accadendo
sotto il cofano così tanto viene questo
da quello che ha detto e da altre persone
chi ha esaminato questo e fatto
esperimenti e alcuni dei miei
anche esperimenti, ma soprattutto io sono
in piedi sulle spalle di questi altri
ragazzi sono venuti prima di me, quindi questo è
su tutti i dettagli di Intel
pronto a darvi su ciò che accade
all’interno di questo diagramma qui siamo
parlerò della metà superiore e
la metà inferiore della metà superiore ecco la
per ordinare una istruzione dopo
un’altra parte del processore e il
la parte inferiore è dove l’ interessante
succede qualcosa dove tutto esce
di ordine e di cui parleremo
la pipeline quello che predice il ramo
è ciò che registro è rinominato e perché
è importante come quello fuori ordine
l’esecuzione avviene e un pochino sopra
caching Sono io possa aver perso venduti che
un po ‘nell’astratto di questo
parlare ho detto che sarei andato
nel caching pure ma di nuovo quello è
come probabilmente altre ore parlano e sono
proprio così andremo a pascolare
un po ‘forse se io se loro
Invitami a tornare l’anno prossimo, possiamo parlare
a questo allora quindi ci sarà
qualche assemblea sullo schermo come ho detto
e prima di andare troppo lontano io solo
dare una rapida panoramica dell’assemblaggio
struttura in modo che stiamo parlando
lo stesso tipo di cosa ce ne sono due
modi concorrenti di mostrare assembly Intel
c’è il formato AT & T e poi c’è
il formato Intel ho scelto Intel
uno per queste diapositive perché è giusto
ha più senso per me venendo da
I processori ARM risalgono a quando e così è
dove la destinazione è sulla sinistra
lato della mano delle due cose così an
l’istruzione generalmente sembra qualcosa a
un po ‘come op dove up è come caricare o aggiungere
o sottrarre o o esclusivo o o spostamento
destinazione e fonte e quelli
destinazione e quelle fonti possono essere uno
di tre cose possono essere un registro
uno dei rack o RBX o RCX come me
scritto qui ce ne sono otto
registri architettonici che provenivano da
l’era a 32 bit quando AMD ha inventato il
estensioni della versione a 64 bit di
il
valutatori hanno aggiunto in altri otto
registra quali erano molto di più
piuttosto chiamato sensibilmente attraverso i nostri 15 piuttosto
nuovi strani nomi esoterici ci sono
anche queste istruzioni multimediali che
sono cresciuti dalle revisioni del
Istruzioni MMX impostate da lontano quando
questi non sono registri generici
di solito sono in possesso di interi da impatto o
valori imposti a virgola mobile e loro
può essere utilizzato in parallelo per simili
moltiplica e cambia e cose ma
non possono essere usati generalmente per simili
indicizzazione a differenza anche degli altri registri
puoi parlare di sottosezioni di
registri così come ho detto il 64-bit
registra RA X ha un 32 bit
controparte EAX e un conteggio di 16 bit circa
ax e poi un H e al quale si riferiscono
il secondo dal basso e dal basso
otto bit rispettivamente che tutti
che rimandano alla eredità del
8088 che ancora pervade ancora oggi
macchine desktop e server per il massimo
parte il flusso di istruzioni del tuo
IBM 8e originale funzionerà felicemente
non molestato relativamente indolubile su un
sistema operativo appropriato su un moderno
chip Intel che ha un numero di
effetti collaterali interessanti il fatto che
abbiamo questo oltre 30 anni indietro
compatibilità nel flusso di istruzioni
ne parleremo un po ‘più tardi
come ho detto, può essere una delle tre cose
potrebbe essere un registro può essere un
memory operando da chiunque venga
come la Cisco quindi il mondo a rischio come me
è stato assolutamente scaglionato a
rendi conto che su x86 un operando di memoria
può essere un indirizzo di memoria assoluto mem
più un registro più un altro registro
tempi uno a quattro o otto e questo è un
un singolo operando è un tipo di parte
di un’istruzione è carina
serie complicata di indicizzazione o può
anzi essere una costante così quei tre
le cose sono memoria di registro o costante
quindi ho un esempio in basso
qui questa è un’istruzione
è un array di puntatore word ADD D RB X
più 4 volte ID X virgola DX e che cosa
in realtà è viene letto dall’indice array
il registro B più 4 volte il D
registrati aggiungi da register a quel valore
e poi riscrivilo tutto è uno solo
l’istruzione è piuttosto complicata
ed è qui che il C
in sis viene da per metterlo in
contesto e per darci un esempio come noi
scorrono lungo il gasdotto Ho un molto
semplice esempio qui che è a
element-wise mi ha dato il valore massimo
di ciascun elemento sul lato sinistro
abbiamo il codice C e sul
lato destro abbiamo uno dei
molte potenziali versioni compilate di questo
codice e sto andando attraverso il
istruzione per istruzione proprio così
possiamo essere sulla stessa pagina
cosa sta succedendo qui, quindi abbiamo un
65.000 array di voci li esaminiamo ciascuno
uno individualmente se y è maggiore di
l’ elemento x quindi scriviamo la Y
elemento nell’elemento X e lo siamo
fatto ovviamente ci sono molto meglio
modi per farlo davvero
codice del mondo reale ma questo è come un
esempio relativamente semplicistico, quindi facciamolo
prendere la prima istruzione lì che
visto EI x EI x questa è una rotatoria
modo di impostare il registro EAX a zero
abbiamo i compilatori hanno deciso che il
Il registro EAX sarà dove si trova
andando a mantenere il contatore del ciclo e perché
è vero per mezzo della sega ascia e ascia si può chiedere bene
è abbastanza facile provare a te stesso
che se prendi qualsiasi numero e
esclusivo o con se stesso finisci
con 0 quindi perché il compilatore ha fatto questo
beh la risposta è l’opcode che
traduci in quello zouri un XCX
sono lunghi 2 byte per spostare l’equivalente
valore con un valore costante di 0
richiedono più byte quindi il compilatore ha
scelto una rappresentazione più piccola del
stesso funzionalmente la stessa istruzione
al fine di ridurre al minimo la quantità di codice
cache che è necessario noterete anche
se guardi un po ‘più in basso
che più avanti usa la nostra ascia ma è così
EAX in ascesa ci sono diversi
regole complicate su quali parti di
i registri vengono aggiornati con quali tipi
di istruzioni ma quando AMD si avvicinò
con le estensioni a 64 bit per Intel
set di istruzioni hanno deciso che se tu
dovevo scrivere al registro a 32 bit
cancella automaticamente i primi 32 bit
che ha un lato davvero conveniente
effetto qui di noi utilizzando un più piccolo
codifica di Zoar eax EAX che è solo 2
byte lunghi ma che cancellano l’intero 64
i bit qui se fosse tutto rax venire un rax
richiederebbe un paio di byte opcode in più
così passando alla prossima istruzione noi
avere una lettura questo è uno di quegli indici
legge che non è così complicato come
quello che ha x uno due quattro o
otto che abbiamo visto nella prima diapositiva
stiamo andando a leggere qui dal nostro
si plus r axe e per convenzione il a
un bi è che il nostro si è il secondo
parametro a questa funzione che
corrisponde al puntatore del filo
array in modo che andremo a letto che fuori
calcolando l’indirizzo di questo
elemento particolare aggiungendo l’elemento
indicale e leggilo in questo X mm
zero registrati questo è solo uno di lettura
numero doppio di precisione fuori i prossimi due
le istruzioni qui sono un confronto che
sta confrontando questo valore direttamente con
l’indirizzo di memoria della X di I così noi
non ho dovuto leggere la X di I valore
per fare il confronto possiamo
basta avere un confronto che agisce direttamente
in memoria e se il valore è inferiore
stiamo saltando sull’etichetta di qui che
salta l’istruzione successiva questo è il
equivalente al fallimento della condizione if
e andare avanti e non fare il
aggiornamento che sta per accadere
questa parte quindi è l’aggiornamento che siamo
supponendo che YI fosse maggiore di X di
Io sto solo leggendo scrivendo questo
valore di x mmm 0 nell’indirizzo del
di XI e poi saltiamo al
prossimo elemento dell’array e lo farai
notare qui il compilatore è deciso
piuttosto che usare quello x 1 x 2 x 4
Multiplet Maite lì x 8 trucco di indicizzazione
è solo moltiplicato il contatore del ciclo di
8 in tutto e aggiunge 8 ogni volta
stiamo contando in indirizzi di memoria
invece di valori I effettivi e
in modo proporzionato saremo
confrontando la fine dell’array qui con
otto volte i 65.000 in cui vado
lì e poi se non abbiamo raggiunto il
Alla fine torniamo all’inizio
altrimenti abbiamo finito, quindi spero che sia così
avuto modo ottenuto noi sulla stessa pagina quando si
arriva all’assemblaggio quindi la pipeline Intel
è una bestia molto lunga e complicata e
Ho intenzione di parlare di gruppi di
cose che vanno avanti ma che
prima di tutto qual è il gasdotto I
penso che probabilmente la maggior parte di noi lo sa
i processi moderni sono condutture
perché bene non è probabilmente mai stato il
caso che un’istruzione potrebbe completare
in un solo ciclo anche indietro nel vecchio
vecchi tempi di molto
istruzioni più semplici molto più lente
l’orologio accelera e quindi c’è sempre
stato una partizione di lavoro e nel
processi originali l’originale a 8 bit
processori certamente con cui ho lavorato
il 6502 e lo z80 ogni istruzione
prenderebbe cinque o più cicli a
completare e l’istruzione sarebbe
essere recuperare il byte che è possibile causare il
opcode fetch gli operandi eseguono il processo
Scrivi i risultati e poi lo faremo
passare alla prossima istruzione così
sarebbero stati presi quattro o cinque cicli ciascuno
vai allora la gente si rende conto che mentre
stavamo decodificando una istruzione noi
potrebbe essere andare a prendere il prossimo e mentre
stiamo eseguendo le istruzioni che potremmo
decodifica il precedente nel recupero
il prossimo ancora così facendo pipelining noi
può aumentare il rendimento in a
stile di linea di produzione che è grande così
ora ogni orologio segna una nuova istruzione
entra nella parte anteriore della pipeline e
un’istruzione lascia la fine del
il pipelining è completato quindi ogni orologio
zecche qualcosa di utile succede a noi
non sono cambiati quanto tempo ci vuole per
eseguire una singola istruzione è ancora
quattro o cinque cicli ma ogni segno di spunta siamo
ottenere una cosa in più e questo è
molto l’ approccio alla produzione
linea prende quando si guarda come auto
costruendo se tu fossi qui per parlare di jezus
ieri e stava mostrando tutto
il genere di cose da pipelining e il
lavoro che la Toyota ha fatto per
ottimizzare la loro pipeline in avanti ha fatto
anche io penso a questo, ma il problema
è quello che stai facendo un’auto a una macchina
non dipende da una macchina precedente che
è stato fatto, che non è vero per
istruzioni il flusso di istruzioni
ha necessariamente istruzione interiore
dipendenze se stai facendo un multiplo
e il moltiplicarsi richiede cinque o sei
cicli quindi si desidera utilizzare il risultato
di quello si moltiplica nella prossima istruzione
bene se la tua pipeline sei un po ‘fuori
di fortuna fino al completamento del multiplo
e devi quindi puoi iniziare il
prossima istruzione quindi cosa tipicamente
succede che il gasdotto si fermerebbe a
quel punto e la prossima istruzione che
era necessario il risultato del moltiplicare
aspettare la conclusione moltiplicata
che tipo di vergogna stiamo usando
la nostra larghezza di banda del gasdotto lì o perdere
larghezza di banda più sorta di più
è problematico il fatto che il nostro
flusso di istruzioni in arrivo non lo è
un flusso lineare
all’interno di quel flusso o un ramo che
può essere condizionatamente e così ogni volta che
il codice salta intorno e inizia ad aver bisogno
esecuzione da una parte diversa del
programma che, fondamentalmente, devono ricominciare da capo
che arriviamo al punto in cui il
ramo succede se il ramo è preso
ci va, purtroppo, tutto a posto
il lavoro che sta venendo giù il
la linea di produzione è sbagliata, dobbiamo
iniziare di nuovo e così si va indietro al
iniziando partiamo dall’inizio di
la linea di produzione ma al nuovo
indirizzo in modo che cosa possiamo fare al riguardo
bene possiamo fare un’ipotesi che è il
cosa più semplice che ne dici se in qualche modo noi
potrebbe guardare al futuro e decidere
bene ciò che è davvero così che stiamo facendo
ciò che effettivamente è la sequenza di
le istruzioni che stanno arrivando sono
non solo indirizzo uno seguito da indirizzo
a un seguito dall’indirizzo tre andiamo
avere una sorta di logica di predizione bene
abbiamo bisogno di una sfera di cristallo per risolverlo
davvero non c’è una buona risposta per questo
ma ce ne sono alcuni veramente buoni
euristica che è esattamente ciò che
quando il predittore del ramo ha così il
predittore di ramo questo succede proprio a
l’inizio della pipeline oops
prima abbiamo persino recuperato un byte di RAM
stiamo indovinando dove quel byte di RAM
deve venire da
dobbiamo prevedere se è un ramo se
c’è un ramo in arrivo dove va
e se è un ramo condizionale di cui abbiamo bisogno
per funzionare bene sarà preso
questa volta o no quindi abbiamo un po ‘
contanti e quel denaro è chiamato il ramo
buffer di destinazione e in quella cache che memorizziamo
ogni istruzione di ramo che abbiamo visto
recentemente abbiamo visto dove quel ramo
l’istruzione va e nel caso di
rami condizionali manteniamo una specie
di stato che ci dice ci dà un
predizione circa se o meno che
il ramo sarà preso la prossima volta
vederlo lo stato più semplice che potremmo mantenere
è letteralmente lo abbiamo ripreso
recentemente così un modo che è fatto è con
un contatore di saturazione a due bit che diciamo
ogni volta che prendiamo un ramo ne muoviamo uno
stage qui a destra
ogni volta che non prendiamo un ramo, noi
sposta uno stadio a sinistra e poi se
siamo nella zona verde qui debolmente
presi o fortemente presi, diciamo bene
supponiamo che lo stiamo prendendo di nuovo e
se siamo in una zona rossa diciamo semplicemente no
Andiamo avanti con il suo ignorare questo
ramo continuiamo a continuare a trasmettere da
memoria in memoria per ordinare è fantastico
questa è una cosa molto semplice da fare ma
non è molto accurato se pensi
su quali sono davvero i rami
come se avessi dei loop, andremo
sullo stesso pezzo di codice multiplo
tempi e quale caso questo probabilmente potrebbe
funziona abbastanza bene, sai ogni volta che lo fai
raggiungere il fondo di un ciclo c’è a
diramati verso l’alto e se lo hai
ottenuto come un centinaio di iterazioni di un ciclo
allora sarà più a destra della
tempo e poi stai per sbaglio
alla fine forse va bene ma se
ne hai altre più complicate
dipendono dalle dipendenze delle filiali e tu sei
praticamente per fortuna questa roba non lo è
abbastanza buono che dobbiamo prendere in un
consiglio della storia di ciò che questo
il ramo ha fatto prima forse è necessario
guarda in che cosa stanno facendo gli altri rami
il sistema e cercare di aggiungere nel
mescolare e vedere se non possiamo indovinare basato su
che quel tipo di impronta digitale di cosa
il programma è all’altezza di una cosa che possiamo
fare è tenere traccia di ciò che accade dato
la storia di un particolare ramo così
per ogni ramo in quel BTB che poco
cache ci terremo in questo
esempio ho messo quattro solo perché è
facili quattro bit di quello che è successo l’ultimo
quattro volte abbiamo visto questo ramo e poi
che andremo a utilizzare che per indicizzare in un
tabella di dato il fatto che abbiamo visto
due rami presi e poi due rami
non preso in questa sequenza che ci dà
un indice tre andiamo a guardare nel
tabella di storia cosa è successo l’ultimo
tempo abbiamo visto questo modello di rami
essere presi oh, abbiamo preso un ramo, facciamolo
prevedere che lo abbiamo fatto e poi
Ovviamente, come veniamo giro nel
l’esecuzione in realtà prende la decisione
riguardo se abbiamo preso il ramo o noi
non ha preso la filiale che aggiorna la nostra
tavolo e nel tempo impariamo dato questo
schema questo è ciò che accade che è bello
ma c’è un problema
questo è solo quattro bit di storia
le quattro volte che abbiamo visto in precedenza
questo progetto non è molto di stato
i programmi sono molto più complicati di
che non scala in tutto il tavolo
di contatori che hai visto sulla mano destra
il lato nella diapositiva precedente è di due bit
per entrata ma sale con due al
N quindi se aggiungiamo otto bit, se vogliamo
fare otto pezzi di storia e prendere in
conto degli otto precedenti rami
di questo potat casi di vedere questo
ramo precedente quindi abbiamo bisogno di 256 lotti di
due bit e quello giusto
anche quello che vogliamo avere un cache di
molti rami Biddy che non sono
andando a sporgere molto bene
ci sono alcuni circuiti in certo
alcuni dei vecchi processori Intel che
avere un tipo di ipotesi a parte
per il comportamento del circuito in cui tengono traccia
del numero di volte che il ramo è
incontrato e preso ogni volta
tranne uno che tipo di mucca copre il
caso di avere qualcosa che va
attraverso come 50 volte e non ottiene
preso 50 volte non viene preso 50
volte non viene preso bene così
probabilmente un loop di 50 che stiamo andando
per vedere di volta in volta ma um è
difficile determinare se o non
qualcosa è davvero un ciclo o se o
non è solo una condizione che è spesso
vero quindi c’è solo un limite limitato
chilometraggio e prendendo quel tipo di approccio
quello che Intel ha fatto nel loro più
la generazione recente di hardware è da prendere
una visione globale della previsione del ramo
problema prendono 32 bit di globale
storia che non è un particolare
cronologia del modello del ramo ma qualsiasi ramo
qualsiasi ramo condizionale che abbiamo visto
recentemente le 32 filiali più recenti
cosa faremo in questi casi e
invece di avere 4 GB di valore
tabella di previsione dei rami per quelli 32
bit che abbiamo hash quello in un più piccolo ma
tabella di pattern condivisa in modo che possiamo avere
piuttosto un grande tavolo di questi modelli ma
dobbiamo accettare che ci stiano andando
per essere collisioni usiamo ancora un per
tabella delle filiali per la destinazione di qualsiasi
un ramo particolare che cosa fa
sembra che assomigli a questo
quindi ora abbiamo 32 bit di cosa
la terra abbiamo fatto di recente in termini di
ramificando prendiamo che prendiamo il
indirizzo di filiale di questo particolare ramo
stiamo cercando di prevedere che li fumeremo
insieme a questo hash qui e poi a noi
andare in questo tavolo ci viene dato questo tipo
di stato del programma questo è quello che abbiamo fatto
prima e questo è veramente figo tranne
che questa tabella di storia globale non ha
idea se sia o no davvero questo
ramo che stiamo guardando a due
rami che hash allo stesso elemento
usiamo semplicemente quello che c’è nel loro ramo
tavolo il tavolo della storia mi scusi e
ciò significa che puoi entrare
situazioni in cui i rami combattono sopra il
stesso slot nel buffer e ci manca miss
prevedere molto del tempo
e ci sono modi per aggirare ciò che come
per quanto posso dire non sono in realtà
succede su chip Intel moderni ma
sicuramente altre altre architetture allora
anche come un altro predittore
di un meta predittore per ramo che
dice solo quanto spesso ho previsto questo
ramo correttamente e ogni volta che scriviamo
ci muoviamo uno a destra e diciamo va bene
faremo quello che la cosa del tavolo delle succursali
dice e ogni volta che ci sbagliamo, noi
spostalo a sinistra e poi diciamo bene
fare il contrario di ciò che la tabella delle filiali
la cosa lo fa se hai due rami
che hanno un comportamento opposto a cui atterrare
lo stesso slot almeno possiamo gestire
quella situazione ma come dico non c’è
forte indicazione che Intel sta facendo
questo dicono che non sono anche noi
non so quanto sia grande questa tabella di storia
sui ponti sabbiosi quindi la tua ipotesi è come
buono come il nostro in realtà ma supponendo che
si sa sono questi solo due bit di ciascun Sono
indovinando loro usano parecchi pezzi di
storia ma prima di tutto fa questo
in realtà contano prima di andare troppo lontano
giù questa cosa arretrata non abbiamo nemmeno
entrato nella prima fase del gasdotto
giusto ancora ci stiamo ancora provando
allenati dove diamine stiamo andando
ottenere le istruzioni da è
importante bene ecco un po ‘ di Python
codice Python è ovviamente interpretato
linguaggio ed è pieno di interni
rami all’interno del proprio interprete e
quindi sarebbe interessante vedere
se possiamo o meno vedere anche il
risultati del predittore di ramo a questo
livello e così questo esempio sta per
correre su un array e sta per somma
il totale dell’array ed è anche
andando a contare il numero di elementi
che erano al di sotto della soglia di 128 in
questo caso e riassumerà quelli
ragazzi e poi alla fine torniamo come
la media dell’intero array e il
media di quelli che erano sotto 128
se si alimenta una grande vecchia gamma di valori
in questo ognuno tra 0 e 256 questo è
cosa succede se quell’insieme di valori è
completamente casuale tra 1 0 e 255
256 scusa ci vogliono 129 secondi per
elemento ma se si ordina lo stesso input
valore quindi lo stesso set di input prima di passare
esso nella loro prende soltanto 94 906
11 e 98 mi scusi
Penso che dovrei bere qualcosa con questo 94
è un nuovo secondo un elemento che è un
accelerazione dell’8% che non è male ora come
posso essere sicuro che la sua previsione di ramo
lo sta aiutando bene perché dovrebbe succursale
aiuto di previsione qui dovrei dire prima
bene nel caso ordinato ovviamente il
prima metà della matrice questo se
la dichiarazione sarà vera andrà sempre
nel numb troncato e il totale del clip
più è uguale a uno quindi da qualche altra parte
ramo è uno dei tanti rami
all’interno dell’interprete sarà sempre
non preso in quanto non salta il se
dichiarazione quindi corriamo attraverso il primo
metà dell’array e noi colpiamo il piede
agganciare il primo valore che è 128 e a
quel punto la previsione è sbagliata
speriamo però entro il prossimo 2 2 o
3 iterazioni lo avremmo imparato
in realtà questo è ora il nuovo il nuovo il
il nuovo ordine mondiale è quello che saremo
prendendo questo ramo ogni volta e noi
quindi prevedere correttamente da quel momento in poi
quindi sembra una previsione di ramo
ottenere la previsione del ramo proprio qui
sarebbe utile mentre nel caso
caso ovviamente il predittore del ramo è
sta andando a cercare di dedurre uno schema
per questo da questa affermazione se siamo
in effetti nessun modello esiste affatto lì
sono una varietà di strumenti che puoi eseguire
e ho corso uno chiamato perf che sono io
consiglio vivamente per questo tipo di
investigazione e se corri con loro
senza i dati ordinati puoi vederlo
lo stesso numero di istruzioni è
preso lo stesso numero di CPU in pensione
istruzioni che passano attraverso il sistema
lo stesso numero di rami è
incontrato incontrato ma il ramo
il tasso di previsione è molto diverso
tra i due quindi non è nessun altro
artefatto per quanto posso dire anche se
è ancora sorprendente per me che in un
linguaggio interpretato può ancora avere importanza
quello che puoi fare su questo non lo so
in senso pratico per questo particolare
esempio di giocattolo comunque ok
quindi ho fatto un caso ragionevole sul perché a
predizione delle diramazioni è utile ciò che
succede una volta che abbiamo previsto dove
il flusso del programma sta andando bene i risultati
del predittore di ramo sono un flusso di
l’indirizzo di istruzioni è come dove
vogliamo essere da prendere e quello
passa al primo stadio che è
questa fase di recupero e pre decodifica
il futuro è responsabile della lettura
il flusso di istruzioni è responsabile
per fare le ricerche TLB il
traduzione da virtuale a indirizzo fisico
e per lo streaming in blocchi di
istruzioni le istruzioni sembrano
qualcosa come questo
il fetcher li legge in sedici byte
pezzi e ha una cosa interessante
fare prima su così in giù sul
pipeline che vogliamo sbloccare tanto
parallelismo possibile e questo significa
che vogliamo fare in realtà più di
un’istruzione alla volta se questo è a
tutto fattibile ma a causa del lungo e
storia torturata della x86
architettura stiamo tipo di sinistra con
questo strano formato di codici op che no
essere razionale sarebbe venuto con
quindi se si guardano le istruzioni RISC
al giorno d’oggi sono di solito di dimensioni fisse
molto facile vedere dove ogni istruzione
è ma in una sequenza intel non c’è
modo ovvio per determinare dove
i byte sono ci dispiace dove il
le istruzioni sono all’interno di quel flusso di byte
questo è ciò che fa il fetcher
e si affaccia per l’inizio del
ogni istruzione che è sorprendente
risultato se ci pensi in 1
o 2 cicli di clock
è in qualche modo scansionare questa lista di
istruzioni decodificate dove l’inizio
di ogni istruzione forse e in qualche modo
fatto ciò in parallelo perché
necessariamente l’inizio di uno
l’istruzione segue dalla fine di
l’ istruzione precedente c’è a
dipendenza da ciascuno portato avanti
quindi l’unico modo in cui posso pensare di essere
fare è in qualche modo come la decodifica parallela
tutti i 16 possibili posti nel
flusso di istruzioni in cui le istruzioni
potrebbe essere e quindi in qualche modo filtrare
quelli che non hanno senso ma
qualunque cosa sia, è un risultato incredibile
e così questa istruzione scorre qui
questa sequenza di byte è in realtà il
prime poche istruzioni dell’esempio I
ti ho mostrato prima ci sono quei due
byte o EAX EAX e puoi vedere che abbiamo
tirato fuori quattro istruzioni qui e
allora abbiamo la F 200 F che io
non ho messo qui così al
inizio della prossima istruzione nel
flusso che sarà in qualche modo dipendente da esso
all’inizio del prossimo recupero
il prossimo ciclo
Sono costantemente là fuori e ho
Mi dispiace, quindi abbiamo i nostri quattro
oh si scusa a quel punto qui il
il pre decoder non sa cosa questi
le istruzioni sanno solo dove sono
si trovano nella sequenza di byte che c’è
questo è tutto quello che possono fare e loro sono dati
la quantità di tempo che devono fare
questo ma quei byte poi fluiscono come a
sequenza di byte e offset dove il
le istruzioni possono iniziare nello stream
sulla fase di decodifica che è dove
finalmente gli ingegneri Intel hanno una sorta di
ammesso la sconfitta di questo davvero
complicata istruzione bizantina
sequenza e hanno deciso che vogliono
qualcosa di più puro dentro così a questo
puntare le costruzioni SIS che arrivano
attraverso sono convertiti in una sorta di
rischio interno ora Intel non pubblicamente
scusami fino a quando non pubblichi il formato
di questo rischio interno ce ne sono alcuni
sorta di letteratura su dove il
le unità di esecuzione usano i vari tipi di
micro operazioni quindi in micro operazioni
è ciò che chiamano questo questo rischio
impostare e all’interno di tali micro operazioni
le istruzioni più complicate come
l’istruzione di lettura-modifica-scrittura che avevo
nella prima diapositiva il carico da a
aggiungere complicati indirizzi di memoria e
memorizzarlo di nuovo in realtà devolvere nella
tre istruzioni che qualsiasi normale
persona avrebbe scritto in un RISC
mondo è una cosa davvero importante
fare perché più avanti lungo la linea siamo
andando a essere in grado di rompere quelle parti di
le istruzioni e programmarle
in modo diverso che se parti del chip
sono occupati come se il moltiplicatore fosse occupato
possiamo ancora fare la parte di carico di un carico
istruzione che il moderno ha a
componente moltiplicatore ad esso possiamo
potenzialmente avere un se è sì mi dispiace
questo è probabilmente un buon esempio
scusa per aver infranto le istruzioni
pezzi aiuta perché possiamo pianificare
le singole parti in giro e abbiamo
molto più fedeltà in seguito per
cose paralizzanti che non lo farebbero
altrimenti essere paralizzato se abbiamo appena
ingenuamente li teneva come istruzioni atomiche
che abbiamo scritto per iniziare con i decoder
qui può gestire fino a quattro istruzioni
in un unico ciclo che è impressionante così
quelle quattro istruzioni che ti ho mostrato
la diapositiva precedente verrà visualizzata
nella fase di decodifica e lo saranno
trasformato in micro operazioni in uno
ciclare quelli
c’è una certa complessità con il
diversi decodificatori il primo decodificatore per
esempio è in grado di decodificare
assolutamente qualsiasi tipo di istruzione e
generando un numero qualsiasi di micro
operazioni mentre gli altri tre
decoder che ci sono in
parallelo può solo fare il più semplice
istruzione quindi c’è un qualche tipo di
chilometraggio in programma con molta attenzione
le tue istruzioni in un particolare
modello per consentire loro di scorrere attraverso come
il più velocemente possibile sui nuovi processi
questo è meno importante a causa del
micro cache di cui parlerò in a
secondo, ma vedrai se mai andrai
nelle profondità profonde di simili GCC
programmatore di istruzioni interne che prova
è meglio spostare le cose per adattarle
questo tipo di schema e davvero in realtà
è una specie di nota a parte se tu se tu
aprire uno dei posti migliori per ordinare di
vedere la documentazione per questo per il
reverse engineering di ciò che accade
dentro è guardare dentro le viscere di
il compilatore come ce ne sono alcuni
automi all’interno del compilatore che ha provato
di prevedere quello che il processore fa
internamente e programmare le istruzioni a
adattarsi con il flusso previsto così noi
hanno questi quattro decodificatori e li emettono
queste micro operazioni ad altre cose
prendere parte a questo punto abbiamo micro
fusione che è il nome per prendere due
micro operazioni e tipo di trattamento
li come uno anche se abbiamo attentamente
li devoluto in diversi pezzi che
occupa molta banda se tu
immagina di avere un flusso di
le istruzioni che arrivano sono una specie di
espandendo il numero di operazioni
quindi abbiamo una sorta di fan di cose
andando fuori di testa cosa succedendo e quello
ovviamente consuma risorse sul chip
quindi per le operazioni molto comuni come
negozi che richiedono un indirizzo
calcolo così come il negozio reale
beh non hanno più bisogno di temporanei
spazio ci sono due pezzi separati di
lavoro uno è quello di calcolare l’ indirizzo e
uno di loro è quello di fare il negozio ma
Non sarebbe bello solo per ordinare di
trattali come un’unità atomica come loro
scorrere lungo la conduttura e ma giusto
pianificare questi due bit in modo diverso
questo è ciò che sta facendo la micro fusione
due miei raccolti e tipo di loro raggruppamento
insieme come una specie di cianfrusaglie
fare insieme e poi ne abbiamo di più
importante fusione macro che è dove
il contrario accade piuttosto che
più micro operazioni
generato da un singolo input
istruzione prendiamo due input
istruzioni e possiamo bere generare
solo una micro operazione un esempio di
questo è il confronto seguito da un ramo
è così comune che vorremmo
come confrontare il nostro contatore di loop con alcuni
valore
e quindi ramo se non uguale o
decrementa un valore e nel ramo se
non è zero quel tipo di cose che
la maggior parte delle istruzioni dell’insieme di istruzioni
i set hanno effettivamente un decremento e salti
se non tipo zero di sentirsi x86
dozzina ma a questo punto se ne hai due
istruzioni una dopo l’ altra che hanno
questo modello sarà trasformato in a
singola operazione micro così abbiamo tipo
guadagnare un po ‘di questo
fan-out che stavamo ottenendo da da
più in basso nel Sandy Bridge e
sopra c’è qualcosa chiamato micro
contanti di operazione a questo punto anche così
abbiamo già l’orologio ha già
spuntato come sei o sette volte per arrivare
questo punto e quindi un sacco di cose
prezioso lavoro è stato fatto sarà
utile per aggrapparsi a quell’intermedio
risultati soprattutto se le volte che stiamo andando
per rivisitare questo codice in breve
ordine
così la cache di micro-operazione memorizza il
risultati delle operazioni decodificate a
questo punto ci sono circa 1.500 voci
ed è una sorta di cache molto complicata
che non è mappato a un normale come Urim
memoria cache nel modo in cui tu
probabilmente penserei ma se solo tu
pensala come qualcosa che può
tenere un loop piuttosto piccolo in è utile per
ma la ragione per cui questo è utile è
che quando facciamo un ramo più tardi, se noi
scopri che abbiamo sbagliato
lungo la pipeline ma il
la destinazione di quel ramo è all’interno del
cache dei microbi non dobbiamo andare tutti
la strada verso la parte anteriore della pipeline noi
può fare un cortocircuito e iniziare da
la cache di micro rob e solo da allora
in poi dobbiamo iniziare
istruzioni di ritrattamento che riduce
la latenza di un ramo imprevedibile così
anche se abbiamo investito tutto questo tempo
prima cercando di capire in che direzione il
il ramo sta andando se ci sbagliamo il
la cache delle micro-operazioni può salvarci un po ‘
di tempo recuperando da quello che ho
ha detto che la mia Intel non me ne frega molto
esempi di ciò che la loro micro operazione
per uno sembra così ho un po ‘su
il lato sinistro qui dato un esempio
del codice di nuovo e sulla mano destra
lato ho inventato il mio tipo di formato
per quello che potrebbero fare queste micro operazioni
Assomiglia a
quando la convention che ho qui è
quella linea di testo è un micro
operazione così le cose che voglio
sono alcuni punti in questo flusso
che confronta le istruzioni che confronta
con la memoria è alle micro operazioni
c’è una sorta di valore temporaneo e
temporaneo senza nome che viene letto e
allora il confronto avviene come un secondo
micro operazione separata e poi lì
in fondo al ciclo quello che abbiamo
perso in quell’unica micro operazione in più
tipo di artiglio qui perché il
compare seguito dalle mappe di salto in a
singola micro operazione che è la
fusione macro ma anche questo non è proprio
quello che è successo così a questo punto questo
modello mentale di cui potremmo avere
mettere il codice side-by-side non lo è
ciò che il processore sta vedendo in questo
punto perché ciò che il processo è davvero
vedere ovviamente è una sequenza di
istruzioni che fluiscono linearmente verso il basso
il programma previsto ordina il ramo
il predittore ha fatto la sua magia noi abbiamo il
fetcher è solo prendere qualunque cosa sia stata
detto di andare a prendere e questo è ciò che scorre
giù così ho cercato di catturare
questo su questo scivolo qui dove sul
proprio sul lato sinistro che ho tipo
metti l’indirizzo per darti un’idea
e per mettere in evidenza ciò che intendo
qui prendi questo confronto qui
è uno dei paragoni attorno al se
X è maggiore di Y e in questo caso
Ho arbitrariamente deciso che il
predittore di ramo ha previsto che questo
particolare sta per essere presa in modo
piuttosto che il prossimo essere dell’istruzione
i Nordics 14 che sarebbero i prossimi
indirizzo delle istruzioni ho detto hey noi
penso che questo andrà a 19 andare a
19 ora e così è la prossima cosa
che sta per essere in dirittura d’arrivo
Allo stesso modo qui è il ciclo al
in basso dove abbiamo fatto il confronto e
se non è uguale e ovviamente per il vasto
maggior parte dei casi che sarà
preso come per tutti tranne uno
iterazione che sta per essere il caso
quindi speriamo che il predittore sia indovinato
che così ancora una volta la prossima istruzione lo farà
essere di nuovo all’inizio del ciclo e poi
quaggiù solo per il confronto
questo è stato previsto non è stato preso così
piuttosto che essere l’indirizzo esadecimale di
il prossimo è il prossimo
indirizzo lineare in memoria all’esagono 14 ora
ovviamente questo onore di sottolineare cosa
succede quando il ramo arriva davvero
essere eseguito e questa è la succursale
devo dire bene da che parte è fatto davvero
andare e avevo ragione e se non ho ragione
cosa faccio bene abbiamo già detto
di
stiamo andando a lavare la pipeline ma
come succede questo parleremo
quello in un secondo
okay, quindi abbiamo decodificato il nostro flusso di
le istruzioni siamo circa le sei e sette
il ciclo di clock dipende dal modello
giù quelli lungo il gasdotto e noi
colpire questa cosa chiamata il renamer il
il tipo di rinominatore prende un’altra vista di rischio
e in qualche modo trasforma l’ istruzione x86
impostato per adattarsi così solo l’x86
questi otto o sedici in modalità 64 bit
registri che possiamo parlare
ignorando i registri xmm per ora ma
se guardi qualsiasi chip di rischio ci sono
centinaia se non migliaia di disponibili
registra perché è così bene se vuoi
per separare le nostre istruzioni indipendenti
scorre e ha parallelismo inter
parallelismo delle istruzioni che devi essere
non calpestare i tuoi registri allo stesso modo
tempo se usi lo stesso registro due volte
bene devi aspettare per il precedente
utilizzo da finire prima di poterlo riutilizzare
fare qualcos’altro era il
caso in cui i registri hanno preso un sacco di
immobiliare se guardi come vecchio
schemi circuitali o altri vecchi
muore di come il 6502 per esempio
c’è un grande progetto in cui le persone
hanno preso la cima di 6502 se
scansionandoli ad alta risoluzione
telecamere e in modo letterale come supporto
fuori dove ogni singolo transistor è ma
possono disegnare qualsiasi tipo di diagramma di
dove tutto è puoi vedere che il
i registri sono in realtà un sostanziale
blob of the the color che non è più
il caso rispetto a come le cache
che sono lì e tutto il
logica complicata i registri sono a
piccola proporzione, quindi potendo essere solo in grado
per codificare 16 nel formato anche con tutti
le estensioni che ci sono sono gentili
di una limitazione per questo così il renamer
fa analisi di dipendenza al volo e
trasforma il tuo codice in single static
modalità di assegnazione scusa forma e poi
costituisce un temporaneo intermedio intimo
valori e li mappa in una sorta di a
suite di un centinaio di istruzioni
come mi dispiace scusami un centinaio o più
registra così non abbiamo bisogno che non siamo
più a lungo rispetto ai sedici registri
quello è venuto
in possiamo usare questi valori intermedi
tutto e questi intermedio
esempio è piuttosto la cosa migliore
fai qui così qui sul lato sinistro
Ho un esempio leggermente diverso
abbiamo una routine che richiede due
valori e incrementi di due diversi
Globale e abbastanza ragionevolmente qui è un
pezzo di codice che il compilatore potrebbe avere
output che viene letto globale a in
EAX aggiunge X al primo parametro e
memorizzarlo e poi lo stesso di nuovo per
B nota che sta usando nuovamente EAX due volte
piuttosto ragionevole, ma se quella lettura prende un
molto tempo e penso che lo sappiamo tutti
accedere alla memoria di solito è piuttosto lento
allora bene è chiaro e ovvio
queste due istruzioni dopo di ciò che
dipende dal valore che non può essere eseguito
bene, ma abbiamo usato EAX nel prossimo
blocco di codice cosa succede se globale B
è già nella cache un pasticcio se
dovevamo farlo se avessimo usato un altro
registrati qui forse questo potrebbe essere stato
in programma ma abbiamo usato Dax che non possiamo fare
sarà calpestato da
qualunque sia questo flusso di istruzioni
facendo così il renamer dà un’occhiata a
questo lo inserisce nel modulo SSA e viene visualizzato
con qualcosa che sembra un po ‘
come questo di nuovo non c’è tipo di
formato documentato per questo quindi ho gentile
di usato come suffisso su ciascun registro a
sorta di indicare il nuovo nome che ciascuno
registro ha quindi piuttosto che EI X sul
lato sinistro abbiamo EE X sub 1 e
quindi aggiungiamo EI X 1 a EDI 1 e scriviamo
il risultato a un nuovo temporaneo
registro intermedio chiamato EDI 2 e
questa è la cosa che scriviamo di nuovo
di nuovo e poi in modo critico in questo
secondo blob, abbiamo determinato questo
il valore di EI X è completamente indipendente
del valore precedente di EI X potremmo
come pure abbiamo usato un altro registro noi
avremmo potuto fare non potremmo avere
codificati o l’ABI ci ha costretti a utilizzare un
particolare registro architettonico nominato
e ma a questo livello all’interno del chip noi
possiamo crearne uno nuovo , possiamo solo dire hey
chiamiamo questo EI X sub due e ora il
Orb scusa e ora quei due pezzi di
i codici sono indipendenti l’ uno dall’altro e
può correre insieme in parallelo o in grado di
vai di fronte all’altro e sblocchiamo
parallelismo che altrimenti lo farebbe
sono stato
impedito il modo in cui è realizzato è
guarda il renamer tiene traccia di quale di
questi registri temporanei intermedi
contiene la versione corrente di qualsiasi di
l’architettura nominata la registra
è la tabella alias di registro e mappa
in un buffer di riordino che è
come una base graffiata temporanea di tutti
di queste micro operazioni che hanno ancora
da eseguire o aver eseguito ma
non ho ancora finito o completato
mappe nel file di registro permanente
che è come il luogo canonico dove
la vera EAX e il vero edx live
interessante fino in fondo
Sandy Bridge tutto ciò che è complicato
una sorta di logica interna in cui tutto questo
queste varie cose vengono mescolate
intorno e previsto o qualunque cosa non fosse
il collo di bottiglia il fondo effettivo che
era questo PRF leggere qui quindi se se lo hai
modificato un registro recentemente sta andando
vivere in uno di questi temporanei
variabili che sono dentro questo questo
Oltre 100 serie di risultati intermedi
ma se non hai modificato un registro
la ragione di recente è nel reale
registrare il file nel permanente
registrare file e in questa fase come noi
lasciare il rinominatore qualsiasi istruzione
ha bisogno del vero EAX e della vera EAX
non è già nel vero debuff
dobbiamo leggere dal permanente
registra il file e inseriscilo ma
ci sono solo tre porte di lettura sul
registra file che significa che in qualsiasi momento
avevi bisogno di più di tre registri
che non era stato modificato di recente da te
richiederebbe più cicli di clock per leggere
loro e ora sembra molto
tre registri ogni singolo ciclo di clock
tranne che ormai abbiamo devoluto il nostro
istruzioni nel flusso di micro operazioni
ogni micro op ha fino a tre operandi
e stiamo cercando di farne quattro a
una volta così possiamo facilmente escogitare 12 e
questo significa che ne prenderemo quattro
tic tac dell’orologio solo per passare al successivo
stage così per fortuna su Sandy Bridge e
sopra hanno riparato questo e tu no
vedo più questo come un problema
Supponendo che voi ragazzi siete su dei sandwiches
corsi
l’altra cosa che renamer è intelligente
abbastanza da fare è capire questi divertenti
piccole cose come questa o XCX siamo noi
fatto prima in modo così ingenuo se eri solo
monitoraggio come il valore di ciascuno o
piuttosto se fosse o meno un registro
dipende da una precedente incarnazione di
che fa registrare il presente è tutto EI sguardi XCX
come dipende dal precedente
valore di EI X e non è rinominato
è abbastanza intelligente da sapere che questo significa
dammi una nuova EI x inserisci il valore 0 in essa
e andare avanti con la tua vita e in effetti
nella cosa più nuova
i chip più recenti come Ivy Bridge e
più recente a quel punto la micro operazione
in realtà cade fuori dal gasdotto che non facciamo
è necessario fare altro lavoro il lavoro è
fatto solo assegnando un nuovo spazio vuoto
che ha un valore zero in esso per alcuni di
le istruzioni e quelle che piacciono
confronta non con te stesso che per il
registri xmm imposta tutto su quelli
può anche accadere sui ponti dell’edera a
questo punto e nel registro si muove così
spesso di nuovo per adattarsi all’ABI dove
stiamo spostando i valori tra i registri
solo per essere sicuro che le cose siano nel
È disponibile il registro EDI pronto per
chiamare una subroutine bene tutto ciò che è la sua
solo un aggiornamento contabile se pensiamo
è il valore più recente di EDI
slot 7 beh questo è quello che ci serve
registra ok è nello slot 7 di tanto in tanto
la nota che la mossa stessa non ha
succede così molte delle istruzioni possono
essere sbucciato un sacco di simili
istruzioni intermedie le mosse e
i turni scusate le mosse e il
l’ORS esclusivo con il sé può effettivamente
scomparire il flusso di istruzioni a
questo punto e aggiorniamo solo le nostre tabelle
quindi il buffer di riordino è temporaneo
zero spazio di questi cento dispari
elaborare i miei raccolti e i loro operandi il
riordinare il buffer mantiene lo stato che conosce
qual è la micro operazione, conosce il
input e nel caso di micro
operazioni che non hanno i loro valori
pronto sa quali sono le altre operazioni
aspettando e snoop i risultati di
completare le istruzioni come a
l’istruzione dipendente completa il suo
trasmesso attraverso un bus interno
e ogni micro operazione che sta aspettando
per quei risultati ora puoi leggerlo
memorizzalo e diventa pronto per eseguire questo è
anche il palco dove quel permanente
registro letto succede
e a questo punto le micro-operazioni
rimanere nel buffer fino all’ultimo
fase della pipeline okay siamo quasi
nel punto in cui ora stiamo andando
entrare nel territorio magico di effettivamente
eseguendo queste istruzioni e per il
prima volta che andremo a uscire
ordina le stazioni di prenotazione proprio come
l’ ultimo passo questo è dove una sorta di
algoritmo di programmazione che di nuovo è molto
molto vagamente descritto nella letteratura
è responsabile di elaborare quale di
le micro operazioni stanno per andare a
quali parti del chip sia effettivamente
eseguito ci sono sei porte di esecuzione
e ogni porta di esecuzione può fare solo un
sottoinsieme di istruzioni c’è un sacco di
si sovrappongono tra loro ma c’è lì
anche come aree uniche che possono solo fare
un particolare tipo di istruzione e
quello sembra oh siamo qui sì così abbiamo
abbiamo davvero intenzione di parlare di cosa
quali parti fanno ciò che ora abbiamo appena fatto
la parte superiore qui che è l’inorder
parte della coda e ora siamo nel
scheduling domain down here ed è
vale la pena parlare di queste porte qui così
abbiamo le sei porte a questo è dispiaciuto
c’è Sandy Bridge ci sono sei porte
le prime tre porte qui che sono
piombo ossimorico zero uno e cinque loro
tutti hanno una ALU attaccata a loro così tu
tutti possono fare le semplici operazioni di spostamento
se non sono già stati rinominati
di esistenza possono fare turni che possono
fai tutto ciò che possono fare in esclusiva o loro possono
fare confronti e cosa significa questo
quello in ogni spunta se ce ne sono tre
semplici operazioni pronte possono tutti
iniziare l’esecuzione significa che lo abbiamo
ora ha iniziato a fare tre cose contemporaneamente
è fantastico se stai facendo carichi o
negozi è possibile fare uso di queste porte su
qui le porte 2 3 e 4 dobbiamo caricare
porte e una porta del negozio in modo da poter vedere
che questo tipo di un po ‘di contesa
lì in termini di numero di questi
le cose stanno succedendo c’è una cosa in più
riguardo ai negozi come ho detto il
le modalità di indicizzazione sono davvero complicate
può avere come questo indirizzo di base più due
si registra con uno di loro
moltiplicato per un valore costante potenza a
costante per quattro motivi non lo faccio completamente
capisci almeno su Sandy Bridge
questa quarta porta la porta del negozio no
avere la logica del circuito per farlo
calcolo dell’indirizzo e così ogni volta che tu
fare un negozio non è solo il caso
hai due caricatori in un negozio così
c’è un
disparità tra loro ogni volta che lo fai
un negozio deve prendere in prestito uno dei carichi
unità solo per fare il calcolo dell’indirizzo
e questo è un esempio di quelli
micro-operazioni fuse dove c’è un negozio
sia il calcolo dell’indirizzo che il
caricare ma prende in prestito due porte a
una volta anche se è solo una reale
slot nel buffer di riordino altre cose
notare qui è che una volta entrati
le istruzioni più complicate come
il punto in virgola mobile si moltiplica e aggiunge
vari shuffle ce ne sono solo uno o
forse due unità che possono farlo funzionare
che limita la quantità di quelli che possiamo
fai subito sì sei unità che è sì noi
hanno sì sei unità sono per lo più
pipeline di se stessi in modo che significa che
ogni unità lo stanno moltiplicando
potrebbe richiedere sei unità per sei cicli di clock
completo ma possiamo iniziare una nuova moltiplicazione
ogni singolo ciclo quindi anche se il
i risultati individuali di uno moltiplicano
non siamo pronti fino al sesto tick possibile
iniziare una nuova ogni ogni ciclo di clock
questo significa che il tasso scende
qui ci sono fino a tre cicli
quello che stavo dicendo con quelle ALU con
il fatto che abbiamo tre unità ALU
significa che ogni singolo clic clic
orologio possiamo iniziare un tre di quei ragazzi
possiamo solo iniziare un punto in virgola mobile
moltiplicare ogni ciclo di clock che è a
peccato in questo caso anche io sono solo
parlare di come lo scalare si moltiplica
questo può succedere se stai iniziando
usare le istruzioni X mmm per fare come
più punti mobili fluttuanti in
parallelo dove ti piace avere quattro o
più imballato nella XMM registra solo
uno di quelli può iniziare ciascuno, ma
sono come quattro multipli indipendenti
o otto a seconda della larghezza del tuo
registri c’è un altro tipo di
componente così come il throughput
problema di quanti ne possiamo iniziare ciascuno
spuntare abbiamo la dipendenza tra
istruzioni così per operazioni logiche e mosse
se inizi una mossa o un’esclusiva o
i risultati già al prossimo tick così
la prossima istruzione dipende da questo
potrebbe iniziare il ciclo successivo per
l’intero si moltiplica in tre quattro
la virgola mobile si moltiplica come ho detto
una specie di cinque ish sei per radici quadrate
1024 per divisione e resto siamo
cercando ovunque tra il 24 e l’ 84
dipende da
i dati effettivi che stai utilizzando e il reale
la cosa fondamentale di questo è che non è così
pipeline possiamo solo emettere
ha solo una divisione intera in corso a
una volta così in netto contrasto con quelli
moltiplicatori che sono in corso in cui siamo
può avere 301 alla volta ma tu ne conosci uno
uno ogni singolo ciclo a divisione o a
resto sta andando a prendere 80 cicli
ottieni il risultato e non possiamo farlo
l’altro divide i resti in modo che tutti
le tue tabelle hash che hai scritto
dove stai usando il modulo con
forse un numero primo di tavolo
dovrebbe prendere in considerazione l’ utilizzo di un altro
complicata funzione di hashing che utilizza
moltiplica i turni di spostamento ORS esclusivi
che possono essere tutti calcolati molto più velocemente
e poi termina con il potere di
due per adattarsi a una tabella di potere per dimensioni
piuttosto che aspettare 80 cicli per
ti dividi, sai di avere un livello più alto
la funzione hash di qualità potrebbe essere migliore
Scambio comunque comincio a finire
di tempo um questo è il mio tuffo veloce data
nella scusa per il motivo per cui non posso avere 4
gigabyte di cache Ram perché ci vuole 3
a 250 cicli per accedere a Ram sul
lato sinistro qui ho un po ‘ di
Ram statico che potresti trovare in
il tuo cache sul lato destro che ho
un po ‘di DRAM ora è abbastanza chiaro
che il lato sinistro è molto di più
complicato rispetto alla parte destra ma
perché è così male sulla sinistra?
lato abbiamo questo è un dispositivo logico puro
un componente discreto possiamo essere a 0 o 1
fuori da questo in ogni momento, ma richiede
potenza costante richiede 6 transistor
e un mucchio di complicate sovrapposizioni
fili che rendono molto molto difficile
per spiegarlo in modo ad alta densità
un chip
Non so come faccia a farlo Intel, ma tu
guarda il dado e c’è questo
belle aree che sono chiaramente il
cache della stessa cosa più e più volte
di nuovo ma in qualche modo sono stati in grado di farlo
fatelo ma è affamato di potere
significa che riscaldarsi è un problema per
per la dissipazione del calore um ma è una logica
dispositivo che è grande sulla mano destra
lato abbiamo qualcosa che è un
componente analogico
questo condensatore quaggiù ne conserva alcuni
numero molto piccolo di elettroni da immagazzinare
se c’è uno zero o uno là
il che significa che non abbiamo bisogno di pagare
alimentandolo quando non stiamo accedendo
possiamo spegnere il sistema e lo farà
essere lì tranne che poi si scarica via
tempo quindi dobbiamo restare occasionalmente
rabbocco che riduce la nostra memoria
larghezza di banda che dobbiamo continuare a utilizzare
solo per continuare a riempirlo, ma di più
importante ogni volta che leggiamo da questo
non è la conversione da analogico a digitale che
richiede tempo quindi il perché dovremmo farlo
questo bene, ovviamente , non abbiamo bisogno di energia
tutto il tempo è fantastico
questi sono molto più semplici che possiamo
esponete questi elementi a una densità molto più alta
ecco perché le tue celle DRAM sono molto
molto più strettamente imballato e tu
può avere i tuoi gigabyte di RAM e
ovviamente l’ altra parte è questa
la DRAM di solito è fisicamente
separato dal chip piuttosto che
essere sulla morte come tale questa propagazione
ritardi ci vuole solo un po ‘di tempo
le sfortunate leggi della fisica sono contrarie
questi elettroni non si muovono da nessuna parte vicino
la velocità della luce e stanno andando a
spostare abbastanza lontano dal chip RAM
per entrare nel processore così è gentile
delle mie scuse per il motivo per cui non possiamo avere un sacco
di cache Ram c’è qualche esempio
orari qui e penso che abbiamo tutti noi
sappi che è meglio tenerlo
le cose in un livello memorizzano nella cache il
cache di livello inferiore che memorizza nella cache lo faremo
esplosione attraverso quest’ultimo paio di bit
ecco quindi l’ultima cosa che succede è
quando l’istruzione ha completato
trasmette il suo risultato che libera qualsiasi
delle micro operazioni che stanno aspettando
per essere programmati diventano pronti per essere eseguiti
se sono nel qual caso lo scheduler
li raccoglierò il prossimo segno di spunta che abbiamo
ho alcune cose complicate da ripristinare
inoltro che ho il tempo di parlare
circa ora e l’ultimo stadio è questo
fase di pensionamento che è dove alcuni di
la magia migliore accade così nel
fase di pensionamento finora abbiamo tipo di
ogni istruzione che è stato volato giù
la pipeline è stata una transazione
è ancora da impegnare anche se possiamo avere
leggi dalla memoria tutti i diritti che abbiamo
fatto ho una sorta di rintanato in una memorizzazione
buffer che non ha ancora fatto perché
è così importante che abbiamo noi
riordinato tutto lungo la strada cosa
succede se ne abbiamo uno che è un ramo
è sbagliato ma cosa succede se ci ha portato
un po ‘per scoprirlo già
ha iniziato a fare parte del lavoro che è stato
l’altro lato di quel ramo di cui abbiamo bisogno
disfare quel lavoro e il modo in cui è
fatto è semplicemente non commettendo il
l’istruzione fondamentalmente sta spazzando via quello
transazione
l’ istruzione è iniziata e non scritta
torna al file di registro permanente no
permettendo al negozio di fluire effettivamente
verso l’ esterno del chip di no
permettendo che l’istruzione si ritiri
analogamente le eccezioni come / zeros significano
potrebbe essere il caso in cui divido il
i valori per una divisione non si sapranno risalire
davanti e così istruttori oltre il
il divario è già finito in
completato ma la divisione per zero deve
capita con il vecchio valore di quelli
operandi e c’è un questo tipo di
questo sta iniziando a diventare esposto a
il modello di programmazione elenca questo insieme
idea di avere questo tipo di
istruzioni transazionali dove così per
esempio ha ben presente questo software
modello di memoria transazionale dove puoi
chiedi di essere informato se se varie parti
della RAM sono accessibili mentre stai lavorando
e abortire e una serie di istruzioni così
che un’operazione atomica dal tuo punto
di vista non richiede un blocco solo
indica il rollback della transazione
Da allora ho scoperto che non lo è
effettivamente fatto da efficacemente come il
è la stessa logica della previsione del ramo
probabilmente fatto a livello di cache ma
si parla nel lago del cielo che è
come due altre revisioni su di loro
esponendo questo livello di istruzione
transazione per noi come programmatori okay
siamo arrivati alla fine, è terribile
molte cose che stanno succedendo sotto il
cappa e non penso di avere tempo per
domande a giudicare dal tempo ma
la ringrazio molto per il vostro tempo in cui
ci sono alcune risorse di esempio
lassù grazie
Please follow and like us: