di  -  giovedì 8 novembre 2012

Dopo aver sezionato l’architettura x86 a caccia di elementi che possano essere classificati come legacy, è arrivato il momento di chiudere questa lunga serie di articoli con una sintesi e alcune riflessioni sull’argomento, riprendendo anche in parte quanto elaborato nel precedente pezzo sulle unità SIMD, che rappresenta una sorta di cartina al tornasole della situazione.

Ripropongo, per comodità, tutti i link ai precedenti otto articoli:

parte 1 (istruzioni 8086)
parte 2 (istruzioni 80186+)
parte 3 (FPU x87)
parte 4 (i segmenti)
parte 5 (i selettori)
parte 6 (istruzioni privilegiate)
parte 7 (istruzioni non privilegiate)
parte 8 (SIMD: MMX, 3DNow!, e… SSE)

e riprendo brevemente quanto proposto nel primo link, nella fase introduttiva, riguardo alla classificazione degli elementi legacy: la mappatura degli opcode delle istruzioni, le istruzioni più complesse e raramente utilizzate, e i famigerati segmenti (poi divenuti selettori).

Per quanto riguarda le istruzioni, abbiamo visto che, in fin dei conti, non sono poi tante, e per alcune la loro inutilità può certamente essere messa in discussione (mi riferisco, nello specifico, alle istruzioni “di stringa”).

Tolti i casi limite, è innegabile che le rimanenti debbano essere riconosciute (ma ciò attiene principalmente al decoder, che in questa serie non abbiamo trattato nello specifico), richiedano eventuali microistruzioni (chiamate anche micro-op) “RISC86″ dedicate (una o più) per essere eseguite, eventualmente tramite microcodice per i casi più complicati (che non possono essere gestiti tramite l’esecuzione di due-tre micro-op).

Si tratta essenzialmente di transistor da impiegare appositamente allo scopo. Sono dell’idea che non ne siano necessari tanti (non ci sono molte istruzioni, e poche hanno un’elevata complessità), ma non essendo un esperto in microelettronica mi astengo da ogni altro giudizio. Certamente alcune, trattandosi di vecchiume, non verranno mai utilizzate, ma rimane il costo fisso della loro necessaria implementazione.

Un discorso simile vale anche per il terzo elemento discusso, i segmenti e i selettori. Dovendo, però, impiegare appositi registri (anche interni / “nascosti”), diverse altre istruzioni, e cambiare il comportamento di istruzioni esistenti che devono portare a termine operazioni anche molto complesse (per implementare i meccanismi dei gate), credo che il costo fisso di questa parte legacy dell’architettura x86 risulti decisamente più elevato rispetto alle altre.

Rispetto a queste, però, c’è da dire che segmenti e selettori impongono costi fissi non soltanto a livello implementativo, ma anche a runtime, durante la normale esecuzione, e questo anche nel caso in cui non se faccia sostanzialmente mai uso (mentre le vecchie istruzioni possono non essere mai eseguite, poiché non appaiono mai nel codice dei programmi).

Ricordiamo, infatti, che la segmentazione richiede appositi controlli sui limiti dell’area di memoria che indirizzano, sul tipo di accesso consentito per quest’area, e concorrono pure al calcolo dell’indirizzo virtuale tramite un indirizzo base (che si va poi a sommare all’offset normalmente calcolato dalle istruzioni che indirizzano la memoria).

Tutto ciò va effettuato “contemporaneamente” (semplifico il discorso) per un massimo di tre segmenti/selettori, per ogni singola istruzione che dev’essere eseguita: uno per il codice (l’opcode va caricato dalla sua area di memoria) e al più due per l’indirizzamento della memoria (sorgente e/o destinazione di alcune istruzioni).

Abbiamo visto che, alla fine, il tutto viene realizzato facendo uso di poca logica (comparatori, sommatori, porte logiche), per cui non richiederanno molti transistor per la loro implementazione, ma è certamente vero che si tratti di logica sempre attiva e che non può essere spenta, per cui incide sempre nei consumi del processore (anche se bisognerebbe vedere in che misura rispetto a tutto il resto).

Tutt’altro peso ha, invece, la mappatura delle istruzioni, che influenza ovviamente il decoder. Abbiamo visto in due articoli (che trovate qui e qui) quanto complicato sia lo schema di decodifica delle istruzioni, e quanti milioni di transistor siano richiesti per ottemperare all’arduo compito.

In estrema sintesi, le problematiche derivano dal:

  • ricorso al famigerato concetto dei prefissi per cambiare alcune impostazioni / comportamento delle istruzioni
  • introduzione di speciali opcode che fungono da prefisso per estendere la tabella degli opcode
  • schema di definizione degli operandi registro e memoria, il quale richiede dei byte che si aggiungono alla fine di quelli usati per specificare l’opcode vero e proprio, e il cui numero totale è determinato non dall’opcode, ma esclusivamente dal byte di estensione / definizione degli operandi
  • possibilità di specificare un valore immediato (a 8, 16, o 32 bit)

In parte lo abbiamo anche visto nell’ultimo pezzo, in cui si discuteva del legacy legato alle istruzioni SIMD (MMX, 3DNow! ed SSE): si fa pesante uso dei prefissi per cambiare il comportamento delle istruzioni SSE (ad esempio per specificare di voler operare su dati scalari o packed/vettoriali), e sono stati introdotti due speciali “sub-opcode” per aggiungere due altre tabelle per i nuovi opcode.

Se consideriamo che per la sola sezione di decodifica il primo Pentium impiegava quasi un milione di transistor e il PentiumPro circa 2,2 milioni, ed entrambi non dovevano tener conto di alcuna estensione SIMD, è facile supporre che l’introduzione di MMX, ma soprattutto di SSE ed SSE2, abbia fatto lievitare ulteriormente il costo del decoder, sia in termini di transistor impiegati che di consumo (quest’unità, poi, è quasi sempre attiva).

L’introduzione delle estensioni SIMD AVX da parte di Intel rappresenta un’ulteriore dimostrazione, se ce ne fosse ancora bisogno, di come sia proprio la decodifica delle istruzioni il più grosso tallone d’Achille che l’architettura x86 si porta dietro.

Con AVX, infatti, Intel ha introdotto due speciali prefissi (non c’è altro da fare, purtroppo: è l’unico modo per estendere agevolmente quest’ISA), rispettivamente di 2 e 3 byte, che consentono di mappare qualunque opcode SIMD SSE (quindi non MMX) in maniera molto più semplice (i prefissi SIMD 66/F2/F3 sono già “inglobati”).

Il tutto mettendo anche a disposizione parecchio spazio per estendere ulteriormente l’ISA senza richiedere l’introduzione di altri prefissi e/o di “sub-opcode“. E’ stata aggiunta, inoltre, la possibilità di specificare un terzo registro, così da poter avere istruzioni dotate di 3 o 4 operandi, similmente a ciò che avviene in altre architetture (RISC).

In questo modo tutte le istruzioni SIMD occupano 3 o 4 byte “di base” (2 o 3 di prefisso AVX, a cui si aggiunge poi il byte di opcode vero e proprio), mentre prendendo in considerazione soltanto le estensioni SSE (che poi sono le più usate; è raro trovare codice MMX ormai) si va dai 2 ai 4 byte.

Sulla carta può sembrare un peggioramento, visto che il codice SSE per le medesime istruzioni può risultare anche più denso (e mediamente lo è, statistiche alla mano), ma c’è da dire che, sfruttando la possibilità di specificare un terzo registro, codice appositamente compilato per AVX dovrebbe richiedere meno istruzioni e, quindi, risultare più denso ed efficiente.

AVX non risolve certo tutti i problemi, visto che non elimina tutti i prefissi (inoltre ne aggiunge due nuovi), e inoltre l’indirizzamento della memoria resta abbastanza macchinoso, ma si tratta comunque di una buona soluzione (con Larrabee / Knights Corner Intel ha seguito un approccio simile per la nuova estensione SIMD a 512 bit, ma con un prefisso di 4 byte), specialmente in ottica futura, per lo meno per l’unità SIMD.

Tolto questo (che comunque ha un suo peso), per tutto il resto ci sarà sempre un costo fisso, a livello implementativo e/o a runtime, che l’architettura x86/x64 dovrà continuare a pagare nei confronti delle altre, e che può incidere più o meno pesantemente, a seconda dello specifico ambito applicativo.

L’integrazione dei core ARM nelle CPU Opteron di AMD è un segnale molto chiaro in merito, che dovrebbe far riflettere molto. Evidentemente il mercato ha bisogno non soltanto delle prestazioni, e AMD non è in grado di offrire un’alternativa valida. Questo non significa che lo stesso debba necessariamente valere per Intel, sebbene la situazione non sia poi molto diversa, dovendo entrambe dar conto al legacy, ineliminabile, della loro architettura.

Aggiungo un’ultima riflessione, e concludo, che riguarda anche altri costi, quelli di progettazione e testing, che non si possono certo trascurare quando parliamo di un progetto, specialmente di queste dimensioni e importanza.

Un’architettura così complessa, e in particolare il suo decoder, richiede notevoli sforzi per essere progettata e testata, perché deve tenere conto di tutto quanto abbiamo analizzato finora. In particolare, visto che parliamo di silicio, un malfunzionamento potrebbe creare gravi problemi, che non sono sempre facilmente risolvibili con un aggiornamento del microcodice (operazione che fanno i BIOS delle schede madri all’avvio).

Alla luce di tutto ciò, forse è arrivato il momento di una svolta, di un forte cambiamento, che non richieda obbligatoriamente il salto sul carro di ARM, come ha fatto AMD…

18 Commenti »

I commenti inseriti dai lettori di AppuntiDigitali non sono oggetto di moderazione preventiva, ma solo di eventuale filtro antispam. Qualora si ravvisi un contenuto non consono (offensivo o diffamatorio) si prega di contattare l'amministrazione di Appunti Digitali all'indirizzo info@appuntidigitali.it, specificando quale sia il commento in oggetto.

  • # 1
    Giuseppe
     scrive: 

    “Alla luce di tutto ciò, forse è arrivato il momento di una svolta, di un forte cambiamento, che non richieda obbligatoriamente il salto sul carro di ARM, come ha fatto AMD…”

    Quale sarebbe l’alternativa al “salto sul carro AMD” che lei ha in mente?

  • # 2
    Giuseppe
     scrive: 

    Intedevo “saltare sul carro ARM”, scusate.

  • # 3
    Cesare Di Mauro (Autore del post)
     scrive: 

    E’ un discorso ancora prematuro. Lo affronteremo più avanti.

    In particolare, seguiranno altri articoli che analizzeranno l’ISA x86 dal punto di vista statistico, dai quali salteranno fuori altre riflessioni.

    P.S. Si può evitare il lei, e passare al tu. ;)

  • # 4
    massimo
     scrive: 

    Un concetto a cui penso da un pò di tempo è che un emulatore (diciamo VirtualBox di Oracle) non è altro che un interprete, in ultima analisi… e se un programma può essere interpretato, allora lo si può anche compilare.

    Voglio dire che nulla osta, in teoria, allo scrivere un compilatore che prenda il codice e relative call al SO di un .EXE x86 per windows e lo compili per ARM/linux, ARM/android o qualunque altra piattaforma. E viceversa, ovviamente.

    Per cui, posto che AMD o Intel decidano di modificare il set di istruzioni x86, non dovrebbe essere un problema mettere a punto una utility che prenda un vecchio .EXE e lo renda compatibile con i nuovi processori… Microsoft dovrebbe poterlo fare alrettanto facilmente. Basta che la nuova ISA (la chiameranno y86? :-) sia progettata con un minimo di accortezza.

  • # 5
    Cesare Di Mauro (Autore del post)
     scrive: 

    Assolutamente d’accordo. E’ esattamente ciò che penso (e non solo ;).

  • # 6
    Giacomo
     scrive: 

    Ma nel 2012 il microcodice dei processori si può ancora riprogrammare direttamente, o ci si affida alle patch dei sistemi operativi/programmi?

  • # 7
    Z80Fan
     scrive: 

    @Giacomo #6:

    Quasi tutti i moderni processori hanno la possibilità di caricare un nuovo microcodice, usando una procedura particolare in base al produttore e modello, passando alla CPU un binario fornito dal produttore stesso.
    (Cercando “intel linux microcode update” con Google, il primo risultato è proprio il link dove scaricare il binario)

    Ovviamente questo binario è altamente proprietario e specifico per ogni modello, Intel/AMD non forniscono informazioni sulla sua struttura.

  • # 8
    Cesare Di Mauro (Autore del post)
     scrive: 

    Penso ci sia un qualche meccanismo per cui sia possibile caricare il nuovo microcodice. Infatti tante volte nei changlog degli aggiornamenti del BIOS delle schede madri compaiono frasi del genere.

  • # 9
    Z80Fan
     scrive: 

    Più informazioni sul tema:

    “Intel 64 and IA-32 Architectures Software Developer’s Manual (volume 3a)”
    http://www.intel.com/Assets/PDF/manual/253668.pdf

    Sezione 9.11: “microcode update facilities”

  • # 10
    Giacomo
     scrive: 

    @ Z80fan e Cesare
    grazie.
    Googlando ho scoperto che la maggior parte degli aggiornamenti vengono forniti tramite l’aggiornamento del BIOS e nel caso di Linux tramite patch che vengono caricate dal SO a ogni boot, mentre l’opzione di “flashare” direttamente il processore sembra non più usata o assente.

  • # 11
    Cesare Di Mauro (Autore del post)
     scrive: 

    Onestamente nemmeno ricordavo che fosse possibile aggiornare direttamente il processore per aggiornare il microcodice. Comunque non ho mai approfondito questa caratteristica dei processori, per cui sarebbe una novità anche per me.

  • # 12
    Z80Fan
     scrive: 

    @Giacomo:

    Non sono a conoscenza di nessun processore dove la modifica del microcodice è permanente.
    Tipicamente il microcodice è programmato nel processore durante la produzione (attraverso una ROM OTP). Se all’avvio il processore viene istruito sul caricamento del nuovo microcodice, viene bypassata la ROM e il decoder viene collegato in una RAM dove il nuovo microcodice è caricato.

    Immagino che una memoria non volatile come una flash sia troppo lenta per le prestazioni di accesso richieste da un microprocessore, per questo si usa una RAM (immagino statica), che però obbliga a ricaricare a ogni avvio il microcodice.

  • # 13
    makrov
     scrive: 

    il forte cambiamento probabilmente non si avrà in tempi brevi in quanto il mercato x86 è stato per 20 anni praticamente fermo al palo WIntel, dove la compatibilità con i vecchi binari era una priorità assoluta
    ARM soffre molto meno di questo problema in quanto difficilmente un nuovo processore dovrà eseguire binari compilati per una versione precedente dell’architettura, anche a causa dell’estrema modularità sia del processore sia dell’ISA (debian ha 3 binari differenti per gli ARM 32bit senza contare FPU/NEON/jazelle)
    adesso che il binomio WIntel è stato messo in discussione dalla stessa M$ (in realtà è apple che ha dato il primo colpo prima confondendo le acque passando ad x86 e poi aprendo un nuovo mercato con iphone/ipad dove le app sono praticamente usa e getta, il secondo colpo è stato dato da android che relega la retrocompatibilità dei binari delle app alla virtual machine e slegandosi dall’architettura, potendo girare su arm x86 mips e potenzialmente qualsiasi ISA) l’unico modo che ha intel per svecchiare x86 e renderlo competitivo è quello di tagliar via tutta la compatibilità 16/32 bit ed esporre il microcode relativo a x64 e riorganizzarlo in un ISA che abbia come priorità l’espandibilità dell’ISA stessa e la compattezza del decoder, aggiungendo magari qualche istruzione per agevolare il lavoro alle virtual machine così da emulare tutto l’x86 tagliato fuori (un po come faceva il vecchio crusoe/efficeon)
    naturalmente dovrebbe vendere parallelamente questi nuovi processori relegando il nuovo ai progetti mobile e embebbed, cosa che effettivamente gia sta tentando di fare con atom ma che francamente non reputo una mossa felice

  • # 14
    Cesare Di Mauro (Autore del post)
     scrive: 

    In realtà il nuovo processore con la nuova ISA potrebbe coprire qualunque segmento, non soltanto quello mobile/embedded, se fosse in grado di eseguire il vecchio codice x86/x64 in emulazione all’incirca alla stessa velocità di quello nativo; il che è certamente possibile se la nuova ISA fosse ben progettata. ;)

    Inoltre sarebbe anche possibile “tagliare” la nuova ISA a seconda dell’ambito applicativo.
    Ad esempio una versione a 32 bit (nessun registro a 64 bit) e con soli 16 registri general purpose per il settore embedded (dove non serve nemmeno l’infrastruttura per accelerare l’emulazione x86/x64 e/o ARM).
    Un’altra a 64 bit (perché a breve anche sugli smartphone ci supererà il tetto dei 2GB di memoria fisica installata), con 16 registri general purpose e un’unità SIMD con 16 registri a 128 bit per il settore mobile, che rappresenta un buon compromesso fra prestazioni, consumo, e silicio impegnato.
    Una versione desktop, che è come la prima, ma magari con 32 registri general purpose, e l’unità SIMD con 32 registri a 256 bit.
    Una versione server, che è come la precedente, ma con 64 registri SIMD a 256 o 512 bit.
    Una versione HPC / workstation multimediale (il target di Larrabee/Knights Corner), che invece è dotata di unità SIMD con 128 registri (e 16 per le maschere anziché 8) da 512 o 1024 bit.
    Il tutto in maniera scalabile, dal basso verso l’alto: il binario prodotto per l’ISA “tagliata” per l’embedded può girare sull’ISA mobile, quello per quest’ultimo sull’ISA desktop, e così via.

    Sono soltanto idee, eh! O:-)

    Un piccolo appunto: ARM su mobile non è così variegata. E’ vero che Android delega molto alla virtual machine, astraendosi dall’hardware, ma ci sono anche le applicazioni native (circa il 10%, mi pare), basate sull’NDK, che sono compilate generalmente per ARM (unico target come ISA) e che girano (o dovrebbero girare) su tutte le versioni Android (tenendo conto della versione di API, della presenza o meno di accelerazione hardware grafica, della quantità di memoria installata).

  • # 15
    makrov
     scrive: 

    per quanto riguarda ARM nel mobile concordo dato che android ha dettato uno standard a livello di piattaforma che prima non c’era, basti pensare al periodo nokia/symbian dove cellulari simili montavano cpu con o senza fpu senza tener conto del target del device, infatti uscendo dal mondo android ARM è talmente frammentata da dare qualche grattacapo anche ai developer di debian http://wiki.debian.org/ArmPorts e questo è a mio avviso uno dei principali limiti di arm in ambiti server/desktop

    l’idea di tagliare l’ISA (o cmq utilizzarne solo un subset) è un idea che funziona sulla carta ma difficilmente verrà presa in considerazione da qualche produttore, basti pensare ad intel che abilita/disabilita le funzionalità dei core e la cache per castrare le cpu di fascia piu bassa (e non solo, castra anche gli i5 evitando di attivare l’HT mentre non si fa problemi ad attivarlo sugli atom e gli i3) quindi non ha bisogno di ulteriore differenziazione
    una scelta del genere potrebbe essere presa da AMD che negli anni ha dato prova di saper osare piu di intel ma al momento nn ha risorse ne una posizione di mercato tale da poter permettersi un passo falso
    infine c’è VIA che non ha intenzione di competere con intel e se ne sta chiusa nel suo angolino, anche se sembra avere le idee piu chiare dei rivali (ha inserito le istruzioni aes prima dei concorrenti per velocizzare la criptazione dei dati delineando uno specifico segmento di mercato, e nn ha bisogno di rivedere l’ISA fino a quando ARM non minaccerà pesantemente la sua piccolissima nicchia)
    per il resto MIPS è stata scquisita da imagination, m68k sopravvive solo tra i microcontroller, PowerPC nelle console e i vari itanium/sparc abbandonati a loro stessi, l’unica speranza è che la nuova ARM_64 sia veramente competitiva con x86_64 altrimenti rimarrà di nuovo relegata al mobile

  • # 16
    Cesare Di Mauro (Autore del post)
     scrive: 

    Per essere aggressiva ARM64 dovrà presentare prestazioni comparabili a quelle degli x64 coi quali si dovrà confrontare, e questo dipende molto più dall’implementazione che dalla struttura dell’ISA.
    A mio avviso x86 e x64 non avranno nulla da temere, almeno sul piano puramente prestazionale.

    Riguardo alla scalabilità dell’ISA, è vero che Intel ricicla lo stesso core, abilitando e disabilitando delle caratteristiche, ma questo vale per il mercato desktop sostanzialmente.
    Infatti ha altri due core, molto diversi da quello desktop, che sono Atom e Knights Corner (ex Larrabee), pensati appositamente per il mobile e l’HPC/GPGPU computing.

    Come vedi anche Intel ha bisogno di differenziarsi per essere competitiva in tutti i settori in cui lavora già (per difendersi) o vuole entrare (per attaccare).

    Un’ISA disegnata in un certo modo potrebbe renderle la vita molto più facile, consentendole di differenziare meglio i suoi prodotti, realizzando core “tagliati su misura” per i particolari target, con benefiche ricadute sul piano delle prestazioni e/o dei consumi e/o del silicio impiegato.

    Che non è cosa da poco. Infatti Atom rimane un core “cicciotto” paragonato alla concorrenza, e lo stesso vale per Knights Corner, per il quale il problema è moltiplicato per il numero di unità/processori x64 impacchettati nel silicio. Milioni di transistor sprecati per il decoder, che fanno aumentare i consumi e castrano anche le prestazioni (un decoder molto più semplice accorcerebbe la pipeline, e richiederebbe unità di branch prediction meno avanzate, il che si tradurrebbe in ulteriore risparmio di transistor e consumo di corrente).

  • # 17
    Adriano
     scrive: 

    Cesare Di Mauro (Autore del post) scrive:
    “Per essere aggressiva ARM64 dovrà presentare prestazioni comparabili a quelle degli x64 coi quali si dovrà confrontare, e questo dipende molto più dall’implementazione che dalla struttura dell’ISA.
    A mio avviso x86 e x64 non avranno nulla da temere, almeno sul piano puramente prestazionale.”

    Sono d’accordo ma il mecato per processori dove la prestazioni contano si restringerà sempre di più confinadolli alla fine su ciò che oggi chamiamo workstation a favore invece di mercati dove è più importante il rapporto prestazioni/consumi ovvero il mobile ma anche le server farm per il cloud.

    Con know-how su processori e litografia Intel potrebbe produrre una cpu per il mobile(con una nuova ISA) che sbaraglierebbe la concorrenza, mi chedo cosa aspetti a farlo

  • # 18
    Cesare Di Mauro (Autore del post)
     scrive: 

    Intel è troppo legata a x86. In passato ha provato con altre architetture (80860 prima e Itanium poi), ma ha sempre fallito nel togliere di mezzo x86.

    E’ talmente legata a x86, che ha dismesso la divisione ARM (famosi i suoi StrongARM) puntando tutto su Atom. Quindi rimanendo sempre in ambito x86.

    Sì, potrebbe sviluppare una nuova ISA che unisca le prestazioni di x86 a consumi comparabili a quelli di ARM & co., ma dovrebbe buttare via x86.
    Oppure trovare una soluzione che sia anche in grado di traghettare agevolmente x86 verso la nuova ISA, in maniera indolore. Compito non certo facile, ma sicuramente non impossibile. O:-)

    Quanto ad ARM64, nasce per competere proprio nel mercato workstation/server, dove le prestazioni contano molto, ma anche i consumi. Quindi non propriamente desktop come target.

Scrivi un commento!

Aggiungi il commento, oppure trackback dal tuo sito.

I commenti inseriti dai lettori di AppuntiDigitali non sono oggetto di moderazione preventiva, ma solo di eventuale filtro antispam. Qualora si ravvisi un contenuto non consono (offensivo o diffamatorio) si prega di contattare l'amministrazione di Appunti Digitali all'indirizzo info@appuntidigitali.it, specificando quale sia il commento in oggetto.