Reduced instruction set computer

Da Wikipedia, l'enciclopedia libera.
(Reindirizzamento da RISC)
bussola Disambiguazione – Se stai cercando altri significati, vedi RISC (disambigua).
Processore RISC DEC Alpha 21064 il primo esponente della famiglia DEC Alpha

L'acronimo RISC, dall'inglese reduced instruction set computer, indica una filosofia di progettazione di architetture per microprocessori che predilige lo sviluppo di un'architettura semplice e lineare. Questa semplicità di progettazione permette di realizzare microprocessori in grado di eseguire il set di istruzioni in tempi minori rispetto a una classica architettura CISC.

L'architettura CISC prevede un set esteso di istruzioni con metodi di indirizzamento complessi. Una definizione semplicistica dei microprocessori RISC parla di microprocessori con un set di istruzioni ridotto (semplificato) rispetto a quello dei classici processori CISC. La definizione attualmente più diffusa in ambito informatico parla di architettura load-store dato che le architetture RISC permettono di accedere alla memoria unicamente tramite delle istruzioni specifiche (load e store) che provvedono a leggere e scrivere i dati nei registri del microprocessore, mentre tutte le altre istruzioni manipolano i dati contenuti all'interno dei microprocessori. Nei microprocessori CISC è l'esatto opposto, praticamente tutte le istruzioni possono accedere ai registri o alla memoria in modo indifferente. I più comuni processori RISC sono: AVR, PIC, ARM, DEC Alpha, PA-RISC, SPARC, MIPS e POWER.

L'idea che ha ispirato questa architettura è la constatazione che i progettisti impiegavano molte risorse e molto tempo per realizzare istruzioni molto potenti che i programmatori in realtà ignoravano. Gli sviluppatori tendevano a utilizzare le istruzioni e i metodi di indirizzamento più semplici ignorando tutti gli altri metodi e le istruzioni specializzate. Inoltre negli anni 80 il divario tra la velocità dei processori e delle memorie aumentava e quindi i progettisti iniziarono a studiare tecnologie che riducessero gli accessi alla memoria e che aumentassero la velocità dei processori, ma queste tecnologie erano molto difficili da implementare con set di istruzioni molto estesi.

Filosofia Pre-RISC[modifica | modifica wikitesto]

All'inizio dell'industria dell'informatica i compilatori non esistevano e i programmatori scrivevano direttamente in codice macchina o in assembly. Per facilitare i programmatori i progettisti dei processori decisero di inserire nel set di istruzioni dei processori delle istruzioni anche molto complesse in modo da simulare le funzioni ad alto livello dei linguaggi di programmazione direttamente nei processori. Sempre al fine di facilitare lo sviluppo dei programmi il set di istruzioni dei microprocessori permetteva dei metodi di indirizzamento dei dati complessi che permettevano di manipolare direttamente i dati in memoria, senza passare dai registri dei microprocessori. Questo non era in realtà possibile dato che il processore può elaborare solo dati contenuti nei registri e quindi quando il programmatore utilizzava questi metodi di accesso alla memoria il processore provvedeva a copiare il dato in un registro (a volte un registro riservato) a eseguire l'operazione e poi a salvare il dato in memoria.

Un altro vantaggio dell'avere un set di istruzioni molto complesso è l'occupazione di memoria. Istruzioni molto complesse consentono di realizzare programmi compatti e all'inizio dell'informatica la memoria era una risorsa molto costosa. Quindi i processori avevano molte istruzioni e utilizzavano codifiche a lunghezza variabile di bit per definire le istruzioni in modo da massimizzare la densità di istruzioni.

Le CPU erano dotate di pochi registri per due motivi fondamentali:

  • Realizzare i registri nei processori era molto costoso, i bit all'interno di un processore costano molto più dei bit memorizzati dalla memoria principale. Realizzare molti registri avrebbe richiesto molti transistor e questo avrebbe richiesto di sacrificare le altre unità funzionali del processore.
  • Molti registri richiedono molti bit per essere indirizzati e quindi richiedono più memoria per l'immagazzinamento delle istruzioni.

Questi motivi spinsero i progettisti a realizzare istruzioni molto complesse, per esempio erano comuni istruzioni in grado di caricare due dati, sommarli e poi salvare il risultato in memoria tutto utilizzando una sola istruzione. Un'altra versione della stessa istruzione caricherebbe i dati dalla memoria, li sommerebbe e salverebbe il dato in un registro per esempio. Una terza variante caricherebbe i dati dalla memoria e da un registro, eseguirebbe la somma e salverebbe i dati in un registro. I processori dotati di molte istruzioni di questo tipo vengono definiti processori CISC.

L'obiettivo principale di allora era realizzare processori che fossero in grado di eseguire operazioni con ogni possibile modo di indirizzamento. La possibilità di utilizzare memorie e registri come ingresso o uscita con le varie combinazioni era chiamata ortogonalità delle istruzioni. Sebbene questo complicasse la realizzazione dei processori si riteneva che velocizzasse i programmi dato che il programmatore poteva di volta in volta utilizzare il comando migliore a seconda del programma che stava scrivendo.

Filosofia di progetto RISC[modifica | modifica wikitesto]

Architettura PowerPC G4 (RISC)
Architettura Pentium 4 (CISC), notare la complessità di questa architettura rispetto a quella RISC del PowerPC G4

Verso la fine degli anni 70 ricercatori dell'IBM (e di progetti analoghi) dimostrarono che la maggior parte dei modi di indirizzamento venivano ignorati dai programmi. Questo era dovuto alla diffusione dei compilatori che sostituendosi all'ottimizzazione a basso livello applicata dai programmatori ignoravano i modi di indirizzamento più potenti per concentrarsi su quelli semplici. I compilatori di allora erano in grado di gestire solo le caratteristiche più semplici dei processori anche perché allora la teoria dei compilatori era solo agli inizi. Comunque il mercato si stava muovendo con rapidità verso l'utilizzo sempre più massiccio dei compilatori dato che i linguaggi ad alto livello permettevano di realizzare programmi con rapidità riusando il codice in modo efficiente.

Inoltre gli studi dimostrarono che molte istruzioni esotiche venivano utilizzate molto raramente e a volte erano più lente del codice scritto con le istruzioni generiche. L'esempio classico era l'istruzione INDEX dei VAX, questa istruzione era più lenta di un loop implementato con le istruzioni comuni.

In quel periodo la velocità delle CPU e delle memorie era simile ma era evidente l'incremento di velocità dei processori e che quindi in futuro si sarebbe avuto un divario sempre maggiore tra la velocità dei processori e il tempo di accesso delle memorie. Per ridurre il problema i progettisti pensarono di includere più registri e cache nei processori in modo da ridurre gli accessi alla memoria; i registri e la cache richiedevano molto spazio e quindi si cercò di recuperare spazio riducendo la complessità dei processori.

Studi effettuati da informatici come Andrew Tanenbaum dimostrarono che le CPU prodotte allora erano molto sovradimensionate rispetto alle reali esigenze dei programmi. Tanenbaum dimostrò che il 98% delle costanti in un programma poteva essere memorizzato con parole di 13 bit sebbene la maggior parte delle CPU utilizzasse parole a multipli di 8 bit (quindi 8/16/24 etc.) e quindi sprecasse spazio. Questi studi suggeriscono di memorizzare le costanti nei bit non utilizzati del set di istruzioni, riducendo il numero degli accessi alla memoria. Quindi le costanti non verrebbero caricate dalla memoria o dai registri ma sarebbero inglobate direttamente nel codice binario dell'istruzione rendendo la CPU più veloce ed efficiente. Tuttavia questo approccio richiede istruzioni con codifiche corte una lunghezza di parola di almeno 32 bit per poter aver a disposizione uno spazio ragionevole per le costanti.

Dato che nelle applicazioni reali la maggior parte del tempo viene dedicata all'esecuzione di operazioni molto semplici i ricercatori si concentrarono su queste operazioni comuni cercando di rendere la loro esecuzione il più veloce possibile. Dato che la massima frequenza di funzionamento delle unità era limitata dal tempo necessario ad eseguire le istruzioni più lente e i modi di indirizzamento più esotici si decise di eliminare le istruzioni e i modi di indirizzamento poco usati in modo da ottenere un set di istruzioni più snello contenente solo quelle istruzioni che effettivamente venivano richieste e che potevano essere ottimizzate per essere eseguite rapidamente, spesso in un solo ciclo di clock.[1] L'obiettivo di ridurre le istruzioni portò alla creazione del nome "reduced instruction set computer" (set di istruzioni ridotto). Un numero ridotto di istruzioni con metodi di accesso semplici e lineari permettevano l'utilizzo di soluzioni di tipo pipeline. L'utilizzo di pipeline permette di realizzare microprocessori in grado di eseguire la maggior parte delle istruzioni in un ciclo di clock. In un'architettura CISC è molto più difficile includere una pipeline dato che i molteplici metodi di indirizzamento complicano nettamente il funzionamento dell'unità, quindi a parità di potenza di calcolo un'architettura CISC a pipeline richiede molti più transistor di una architettura RISC a pipeline.

L'acronimo RISC ha portato spesso dei fraintendimenti. Molti leggendo set di istruzioni ridotti pensarono a un set di istruzioni menomato, non in grado di eseguire con semplicità programmi complessi. Invece spesso i processori RISC sono dotati di un set di istruzioni molto completo ma non forniscono metodi di indirizzamento esotici o istruzioni utilizzate raramente. Ispirati dalla filosofia RISC sono state sviluppate macchine basate realmente su set di istruzioni minimali come le MISC, le OISC e le Transport Triggered Architectures, mentre alcune ricerche si sono mosse verso il Turing tarpit.

L'approccio RISC ha il grande vantaggio della velocità ma il suo principale svantaggio è l'occupazione di memoria da parte del codice. Essendo presenti solo istruzioni relativamente semplici il codice scritto per macchine RISC tende ad essere più grande del codice scritto per macchine CISC.

Nello stesso periodo[modifica | modifica wikitesto]

Mentre la filosofia RISC si stava sviluppando, gli ingegneri, cercando di ottenere prestazioni migliori, svilupparono alcune tecnologie che incrementarono grandemente la velocità dei processori.

All'inizio degli anni 80 si era diffusa l'idea che l'architettura dei processori avesse raggiunto il suo limite teorico di velocità. Si riteneva che nuovi incrementi di prestazioni si sarebbero ottenuti solamente grazie alle migliorie dei semiconduttori che, permettendo transistor più compatti, avrebbero permesso di innalzare la frequenza di funzionamento. Molti sforzi furono rivolti verso il calcolo parallelo e verso la realizzazione di metodi di collegamento rapidi. Tuttavia i timori iniziali vennero fugati dallo sviluppo di alcune nuove tecnologie che innalzarono le prestazioni dei processori senza innalzarne la frequenza.

L'idea che migliorò maggiormente le prestazioni fu sicuramente quella che portò allo sviluppo delle pipeline. In una pipeline l'istruzione viene divisa in sottoperazioni che vengono svolte in modo sequenziale dalle unità funzionali disposte come una catena di montaggio. Un normale processore preleva un'istruzione, la decodifica, carica gli operandi, esegue l'operazione vera e propria e salva il risultato. Queste fasi vengono svolte in modo sequenziale da un processore classico ma un processore dotato di pipeline invece esegue queste operazioni in parallelo incrementando in misura notevole le prestazioni.

Un'altra strategia per incrementare le prestazioni prevedeva la creazione di più unità funzionali che lavorassero in parallelo. Per esempio un processore con due unità aritmetiche può lavorare in parallelo su due istruzioni di somma raddoppiando le prestazioni. Questa replicazione delle unità funzionali combinate con le pipeline portarono alla realizzazione di processori superscalari in grado di eseguire più di un'operazione per ciclo di clock.

Queste nuove idee avevano lo svantaggio di richiedere molti transistor per essere implementate, quindi i RISC si trovarono subito avvantaggiati dato che il loro progetto semplice e parco di transistor lasciava molto spazio libero nel processore per poter implementare queste tecniche. Invece i CISC con la loro architettura più complessa si trovarono ad implementare con maggior difficoltà queste idee anche perché il loro set di istruzioni ampio e i molti modi di indirizzamento rendevano più complesso implementare una pipeline rispetto a un classico processore RISC. I primi RISC avevano prestazioni inferiori agli equivalenti CISC ma i processori RISC colmarono presto il divario e all'inizio degli anni 90 superavano i processori CISC praticamente in ogni campo.

Oltre a considerazioni di carattere prestazionale il fatto di dedicare pochi transistor al core vero e proprio del processore permetteva al progettista di un processore RISC un approccio molto flessibile. Con i molti transistor liberi si poteva per esempio:

  • Aumentare il numero di registri presenti
  • Incrementare il parallelismo interno del processore
  • Aumentare la dimensione della cache
  • Aggiungere altre funzionalità come la gestione dell'I/O o di timer
  • Aggiungere unità vettoriali SIMD come AltiVec o Streaming SIMD Extensions
  • Offrire processori a basso consumo per applicazioni portabili.
  • Realizzare i processori in fabbriche con tecnologie antiquate contenendo i costi.

Normalmente un processore RISC è dotato di alcune caratteristiche distintive, le principali sono:

  • Codifica delle istruzioni di lunghezza fissa, questo spreca spazio in memoria ma permette di realizzare una decodifica delle istruzioni rapida e semplice.
  • Gestione omogenea dei registri, questi sono accessibili a tutte le operazioni senza distinzione in modo da semplificare la realizzazione dei compilatori (sebbene spesso i processori siano divisi tra quelli per interi e quelli per le operazioni a virgola mobile).
  • Metodi di indirizzamento semplici (i metodi di indirizzamento complessi possono essere emulati con semplici operazioni aritmetiche)
  • Pochi tipi gestiti nativamente (alcuni processori CISC per esempio possono gestire nativamente polinomi e numeri complessi ma ben difficilmente questi tipi saranno gestiti da un processore RISC).

I progetti RISC quasi sempre sviluppano i processori seguendo l'architettura Harvard. In questa architettura i flussi dei dati e i flussi delle istruzioni devono essere separati in modo da consentire al processore di funzionare senza interruzione e permette al processore una gestione più rapida ed efficiente della cache. Questo vuol dire che se il processore è dotato di cache il programma non può modificare dinamicamente il suo codice dato che le modifiche non verrebbero viste dalla cache del processore. Questo impedisce al codice automodificante di funzionare su questi processori.

Alcuni dei primi RISC erano dotati di alcune peculiarità non desiderate, la più famosa è la branch delay slot. La branch delay slot indica il fatto che ogni volta che il processore incontrava una condizione di salto eseguiva comunque l'istruzione successiva al salto anche se questa istruzione non doveva essere eseguita. In sostanza è come se il salto venisse ritardato di un'istruzione. Questo è un effetto indesiderato delle pipeline e quindi i processori moderni utilizzano particolari accorgimenti per evitare l'esecuzione dell'istruzione se questa non è realmente necessaria.

Primi RISC[modifica | modifica wikitesto]

Il primo sistema al mondo che si può ritenere aderire alla filosofia RISC era il supercomputer CDC 6600 sviluppato nel 1964 da Jim Thornton e Seymour Cray. Thornton e Cray progettarono una CPU specializzata per eseguire calcoli (dotata di 74 opcode, un numero non paragonabile rispetto alle 400 opcode delIntel 8086) e 10 processori periferici dedicati alla gestione dell'I/O. Il CDC 6600 è dotato di un'architettura load/store con solo due metodi di accesso. Il computer aveva 10 unità funzionali aritmetiche/logiche più cinque unità dedicate al caricamento e al salvataggio dei dati. La memoria era suddivisa in più banchi in modo da consentire alle unità load/store di funzionare in parallelo. Il clock del processore era dieci volte il clock della memoria.

Un'altra delle prime macchine load/store era il minicomputer Data General Nova sviluppato nel 1968.

I progetti che portarono alle prima architetture che esplicitarono il concetto di processore RISC comunque furono svolti in seno alle università statunitensi che utilizzando i fondi forniti dal DARPA per il programma VLSI svilupparono molte innovazioni nel campo dell'elettronica e della miniaturizzazione.

Il progetto Berkeley RISC iniziò nel 1980 sotto la direzione di David Patterson. Il progetto mirava ad ottenere elevate prestazioni tramite l'uso di pipeline e di molti registri gestiti con la tecnica della register window. In una normale CPU vi erano un numero ridotto di registri (8 o 16 era un numero comune) che erano accessibili a tutto il programma. Nella CPU progettata dal gruppo di Patterson i registri erano 128 ma il programma poteva accedere in ogni momento solamente a 8 di questi. Questa organizzazione permetteva di realizzare delle chiamate di sistema o dei cambi di contesto molto rapidi. In una CPU classica una chiamata di sistema imponeva al processore di salvare i registri in memoria per permettere alla procedura di avere i registri liberi, nella CPU di Patterson basta spostare l'indice della finestra per ottenere dei registri liberi, senza salvare niente in memorie e quindi velocizzando notevolmente il tutto.

Il progetto RISC sviluppò il processore RISC-I nel 1982. Il processore era formato da 44.420 transistor (pochi rispetto agli oltre 100.000 utilizzati da alcuni CISC dell'epoca). Il RISC-I era dotato di sole 32 istruzioni ma era più veloce di qualsiasi processore a singolo chip dell'epoca. Il suo successore il RISC-II (1983) era addirittura più piccolo, aveva solo 40.760 transistor, 39 istruzioni ed era tre volte più rapido del RISC-I

Pipeline del processore MIPS

Nello stesso periodo John L. Hennessy iniziò un progetto simile chiamato MIPS alla Stanford University nel 1981. Il progetto MIPS si concentrava sul realizzare un processore ove la pipeline fosse sempre operativa. La pipeline era già in uso allora su alcuni processori ma il progetto MIPS sviluppò molte soluzioni che sono diventate di uso comune. Per ottenere una pipeline sempre piena era necessario garantire che le operazioni fossero state sempre completate in un solo ciclo di clock da tutte le unità funzionali e quindi i progettisti decisero di eliminare dal processore tutte le istruzioni troppo lente anche se utili. Difatti il processore MIPS non prevedeva operazioni di moltiplicazione o divisione in quanto troppo lente.

Il primo progetto di produrre una CPU su un singolo chip lo si deve all'IBM che nel 1975 iniziò un progetto che fu di ispirazione per i gruppi successivi. Il progetto di ricerca ha portato allo sviluppo del processore IBM 801. L'801 venne prodotto su singolo chip nel 1981 con il nome di ROMP, un acronimo che indica Research (Office Products Division) Mini Processor. Come dice il nome la CPU era progettata per svolgere compiti d'ufficio e difatti nel 1986 l'IBM presentò l'IBM RT che non ebbe successo per le prestazioni non all'altezza delle aspettative. Nonostante tutto il progetto 801 ispirò molti altri progetti di ricerca incluso il progetto POWER della stessa IBM.

Durante quegli anni i lavori sulle architetture RISC erano molto diffusi all'interno dei centri di ricerca. Il progetto svolto a Berkeley era talmente importante che spesso veniva utilizzato come sinonimo dell'intero paradigma RISC. Molte aziende erano inizialmente restie a investire sull'architettura RISC dato che in un prodotto commerciale la ridotta efficienza della memoria avrebbe potuto compromettere le prestazioni dei processori. Comunque nonostante alcune difficoltà iniziali nel 1986 tutti i progetti RISC erano diventati dei prodotti commerciali e non si può negare che tutti i moderni processori RISC debbano molto al progetto del RISC-II.

RISC successivi[modifica | modifica wikitesto]

La ricerca svolta a Berkeley non portò direttamente allo sviluppo di prodotti commerciali ma il progetto del RISC-II venne utilizzato dalla Sun Microsystems per sviluppare i processori SPARC, dalla Pyramid Technology per sviluppare la sua linea di macchine multiprocessore e da praticamente ogni altra società che lavorò in questo settore. Le macchine della Sun dimostrarono che il progetto RISC era valido, che i benefici erano reali e permisero alla società di dominare il settore delle workstation.

John Hennessy abbandonò (temporaneamente) Stanford per commercializzare il progetto MIPS e fondò la MIPS Computer Systems. Il primo progetto della società fu l'R2000 un processore MIPS di seconda generazione. I processori MIPS sono diventati tra i processori RISC più utilizzati: difatti sono integrati all'interno di console come la PlayStation e la Nintendo 64. Attualmente è un processore molto utilizzato anche nel mercato embedded.

IBM reduce del fallimento del progetto RT-PC imparò dai suoi errori e sviluppò la piattaforma RS/6000 basata su architettura POWER. La società spostò i suoi server AS/400 sulla nuova architettura e gli ingegneri riuscirono a realizzare anche chip con istruzioni molto complesse ma anche molto veloci. Questi progetti portarono allo sviluppo della linea iSeries. Il POWER subì un processo di semplificazione che portò allo sviluppo dei processori PowerPC, processori più semplici, non dotati delle istruzioni peculiari dei prodotti IBM e realizzabili su singolo chip per contenerne i costi. I processori PowerPC sono molto utilizzati in applicazioni legate all'automazione e alle automobili, esistono alcune macchine dotate di più di 10 processori PowerPC. La CPU è stata utilizzata per anni da Apple per i suoi computer, sebbene ultimamente la società abbia deciso di passare ai processori Intel Core.

Molti altri progetti sono sorti rapidamente. Dal Regno Unito ricerche simili hanno portato alla creazione di processori come l'INMOS Transputer e l'Architettura ARM. L'architettura ARM ha avuto un'enorme diffusione nel settore dei dispositivi embedded. Intel ha prodotto i processori i880 e i960 alla fine degli anni 80 sebbene questi abbiano avuto poco seguito commerciale. Motorola ha prodotto il Motorola 88000 un processore che non ha mai avuto molto successo e che è stato abbandonato quando Motorola si è consociata con IBM per produrre i processori PowerPC. AMD ha realizzato l'AMD 29000 un processore molto utilizzato nelle stampanti laser e nelle macchine per l'ufficio.

Attualmente la maggior parte delle CPU prodotte seguono un approccio RISC. La filosofia RISC offre potenza con costi ridotti e consumi parchi, difatti domina il settore dei dispositivi embedded. Telefoni cellulari, palmari, automobili, videogiochi portatili e altri si affidano a processori RISC. I processori RISC inoltre diventarono i dominatori incontrastati dei server ad alte prestazioni durante gli anni 90. Dopo la presentazioni delle Sun SPARCstation i concorrenti della Sun si convertirono alle macchine RISC rendendo il mercato dei server totalmente RISC in breve tempo.

Nonostante i molti successi dei processori RISC, attualmente la piattaforma di riferimento per i computer da tavolo è l'architettura x86 prodotta da Intel. Intel ( e il suo contendente diretto AMD) dominano il mercato dei personal computer con macchine ad architettura CISC. Questo è dovuto al fatto che gli utenti preferiscono mantenere la compatibilità con le loro applicazioni piuttosto che cercare prestazioni più elevate utilizzando architetture più moderne. Difatti nessuna architettura RISC ha una base utenti talmente ampia da poter competere con quella dell'architettura x86. Inoltre Intel, avendo enormi guadagni dai suoi processori, può investire immense cifre di denaro in ricerca per produrre processori che pur rispettando i vincoli dell'architettura x86 offrano prestazioni accettabili. Comunque dall'avvento del processore Pentium Pro in poi i processori Intel prelevano le istruzioni x86 di tipo CISC e le traducono internamente in rapide istruzioni RISC che poi il processore elabora come un RISC classico. Quindi i processori pur comportandosi da processori CISC in realtà internamente funzionano come processori RISC.

I consumatori sono interessati alle prestazioni dei processori al loro costo e alla loro compatibilità con i programmi, non sono interessati a sapere quanto spendono le società per sviluppare i processori. Questo ha generato un fenomeno curioso, lo sviluppo di nuovi processori diventa un affare sempre più costoso e complesso, i costi di sviluppo sono esplosi negli ultimi anni e anche i costi per approntare nuove fonderie di silicio è costantemente in aumento. Questo ha portato fuori mercato tutti i produttori RISC ad alte prestazioni tranne IBM con l'architettura Power. Le architetture MIPS e SPARC vengono sviluppate a ritmi ridotti e sempre per settori specializzati mentre altre architetture (come la PA-RISC e la DEC Alpha) sono state abbandonate all'inizio degli anni 2000. Attualmente i processori più veloci nei calcoli interi sono basati su architetture x86 mentre nei calcoli in virgola mobile le soluzioni RISC di IBM sopravvivono per via della inefficiente gestione dei numeri in virgola mobile dell'architettura x86.

Comunque le soluzioni RISC hanno portato ad alcuni prodotti di grande successo come:

Note[modifica | modifica wikitesto]

  1. ^ Microprocessors From the Programmer's Perspective Review by Andrew Schulman Copyright (C) Dr. Dobb's Journal, Settembre 1990

Voci correlate[modifica | modifica wikitesto]

Collegamenti esterni[modifica | modifica wikitesto]

informatica Portale Informatica: accedi alle voci di Wikipedia che trattano di informatica