Il Little Man Computer (LMC, letteralmente L'omino-computer) è un modello di computer a istruzioni, creato dal dottor Stuart Madnick nel 1965. Viene generalmente usato come mezzo di istruzione, perché rappresenta un semplice computer con Architettura di von Neumann, la base di ogni computer contemporaneo. Può essere programmato sia in linguaggio macchina sia in linguaggio Assembly.Yurcik, W.; Osborne, H. (2001). "A crowd of Little Man Computers: Visual computer simulator teaching tools". Proceeding of the 2001 Winter Simulation Conference (Cat. No.01CH37304) 2. p. 1632. doi:10.1109/WSC.2001.977496. ISBN 0-7803-7307-3.Yurcik, W.; Brumbaugh, L. (2001). "A web-based little man computer simulator". Proceedings of the thirty-second SIGCSE technical symposium on Computer Science Education - SIGCSE '01. p. 204. doi:10.1145/364447.364585. ISBN 1581133294.Osborne, H.; Yurcik, W. (2002). "The educational range of visual simulations of the Little Man Computer architecture paradigm". 32nd Annual Frontiers in Education. pp. S4G–S19. doi:10.1109/FIE.2002.1158742. ISBN 0-7803-7444-4.
Architettura di sistema L'idea di base del LMC è la seguente: si immagina un omino chiuso in una stanzetta (o direttamente dentro il computer). Da un lato della stanza, ci sono 100 buche delle lettere (che rappresentano la memoria del computer), numerate da 0 a 99. Ognuna di esse può contenere un'istruzione oppure un dato, codificati con 3 caratteri numerici, dal valore 000 al valore 999. Dall'altro lato della stanza ci sono invece due ulteriori buche delle lettere, chiamate INBOX e OUTBOX, usate per ricevere dati e trasmetterli in uscita. Al centro della stanza c'è una sorta di scrivania da lavoro con un calcolatrice che ha solo due semplici funzioni: addizione e sottrazione. La calcolatrice rappresenta l'accumulatore. Assieme alla calcolatrice è presente un contatore azzerabile, che rappresenta il Program Counter. Il Program Counter contiene l'indirizzo della prossima istruzione che l'Omino dovrà portare a termine. In condizioni normali, non appena tale istruzione viene eseguita, il Program Counter viene incrementato di 1: in questo modo l'Omino svolgerà tutte le istruzioni in sequenza. È però possibile attraverso istruzioni di salto codificare istruzioni di iterazione (cicli), o anche strutture di selezione condizionata del tipo if-else, queste ultime semplicemente settando il Program Counter a una specifica istruzione se qualche particolare condizione è verificata, ad esempio se il valore mostrato dalla calcolatrice è zero oppure è positivo. Proprio come nell'Architettura di von Neumann, la memoria contiene sia istruzioni sia dati, bisogna quindi fare attenzione a fermare il contatore quando si raggiunge un indirizzo contenente dei dati, o l'Omino li considererà istruzioni e tenterà di trattarli come tali. Per utilizzare l'LMC, l'utente immette dei dati nelle buche delle lettere e poi segnala all'Omino di cominciare l'esecuzione. L'Omino comincerà dall'istruzione contenuta nell'indirizzo di memoria numero zero: in questo modo, resettando il Program Counter a zero si riavvia il programma.
Ciclo d'esecuzione
Per eseguire un programma, l'Omine svolge i seguenti passi:
Guarda il Program Counter per capire quale buca delle lettere contiene l'istruzione da eseguire (ad esempio, la numero zero) recupera l'istruzione dalla buca con il numero corrispondente incrementa il Program Counter, in questo modo esso conterrà il numero dell'istruzione seguente decodifica l'istruzione, ottenendo anche il numero delle buche delle lettere che contengono i dati necessari allo svolgimento dell'istruzione stessa recupera i dati dalla buca delle lettere corrispondente al numero trovato nel passaggio precedente e li immagazzina nell'accumulatore esegue l'istruzione immagazzina i nuovi dati nella buca delle lettere da cui aveva ottenuto i vecchi dati ripete il ciclo o si ferma
Comandi Anche se l'LMC in realtà rappresenta il lavoro di un processore binario, è stato scelto di utilizzare numeri decimali per semplicità e per venire incontro agli studenti che potrebbero non essere accostumati a lavorare con il sistema binario o esadecimale.
Istruzioni
Alcuni simulatori di LMC sono programmati direttamente con istruzioni numeriche a tre cifre, altri con codici o etichette mnemoniche (sempre di 3 caratteri). In entrambi i casi, il numero di istruzioni è comunque molto limitato (circa dieci istruzioni) per semplificarne la comprensione. Se l'LMC è del tipo che utilizza etichette mnemoniche, queste sono convertite in codici a tre cifre durante la compilazione del programma. La prima cifra di un'istruzione numerica rappresenta il comando da eseguire, e le ultime due cifre l'indirizzo di memoria della buca delle lettere legata a quel comando
La tabella sottostante mostra un insieme di istruzioni numeriche tipico e le relative etichette mnemoniche.
+ Istruzioni Codice numerico Codice mnemonico Istruzione Descrizione 1xx ADD ADD Somma il valore immagazzinato nella casella xx a quello contenuto nell'accumulatore. Il risultato è memorizzato nell'accumulatore.
Nota: il contenuto della casella non viene cambiato. L'azione non è definita per istruzioni che causerebbero somme non codificabili in tre cifre (overflow). 2xx SUB SUBTRACT Sottrai il valore immagazzinato nella casella xx da quello contenuto nell'accumulatore. Il risultato è memorizzato nell'accumulatore.
Nota: il contenuto della casella non viene cambiato. L'azione non è definita per istruzioni che causerebbero risultati della sottrazione negativi (underflow); in ogni caso, viene impostato un flag di negatività cosicché l'istruzione 8xx (BRP) possa essere eseguita correttamente. 3xx STA STORE Immagazzina il contenuto dell'accumulatore nella casella xx, cancellandone il contenuto precedente.
Nota: il contenuto dell'accumulatore non cambia, mentre quello della casella xx sì, a prescindere dal contenuto precedente. 5xx LDA LOAD Carica il valore contenuto nella casella xx nell'accumulatore, cancellandone il contenuto precedente. Nota: il contenuto della casella xx non cambia, mentre quello dell'accumulatore sì, a prescindere dal contenuto precedente. 6xx BRA BRANCH (incondizionale) Imposta il Program Counter all'indirizzo xx. Quindi, l'istruzione contenuta nella casella xx sarà la prossima a essere eseguita. 7xx BRZ BRANCH IF ZERO (condizionale) Se l'accumulatore contiene il valore 000, imposta il Program Counter al valore xx, altrimenti, non fare nulla.
Nota: Il Program Counter potrebbe essere modificato anche se l'accumulatore riporta valore 000 a causa del comportamento indefinito dell'istruzione SUBTRACT quando il risultato è negativo. 8xx BRP BRANCH IF POSITIVE (condizionale) Se il flag di negatività non è impostato, modifica il Program Counter al valore xx, altrimenti non fare nulla.
Nota: Il flag di negatività è impostato quando il risultato dell'istruzione SUBTRACT è negativo. Di conseguenza, BRP modifica il Program Counter quando il risultato della sottrazione è maggiore o uguale a zero. 901 INP INPUT Acquisisci dalla casella INBOX il valore digitato dall'utente e memorizzalo nell'accumulatore.
Nota: questa istruzione sovrascrive qualunque valore sia presente nell'accumulatore. 902 OUT OUTPUT Emetti nella casella OUTBOX il valore presente nell'accumulatore.
Nota: Il contenuto dell'accumulatore non cambia. 000 HLT/COB HALT/COFFEE BREAK Termina il programma. DAT DATA Questa istruzione assembly carica il valore nella prima casella disponibile. DAT si usa anche in combinazione con delle etichette per dichiarare delle variabili. Per esempio, DAT 984 immagazzina il valore 984 nella casella di destinazione dell'istruzione di DAT.
Esempi
Uso dei codici di istruzione numerici
Questo semplice programma (dall'istruzione 901 all'istruzione 000) è stato scritto usando solo codici numerici. Il programma accetta due numeri come input e produce la loro differenza come output. L'esecuzione comincia alla casella 00 e finisce alla casella 07. Successivamente verranno discussi gli svantaggi di usare istruzioni a codice numerico per programmare l'LMC.
Casella Codice numerico Operazione Commenti 00 901 INBOX --> ACCUMULATOR INPUT del primo numero, che viene scritto sull'accumulatore (cancellando qualunque cosa vi fosse memorizzata prima) 01 308 ACCUMULATOR --> MEMORY STORE (Immagazzina nella casella 08) il valore corrente dell'accumulatore, in preparazione al passaggio successivo. 02 901 INBOX --> ACCUMULATOR INPUT del secondo numero, che viene scritto sull'accumulatore (cancellando qualunque cosa vi fosse memorizzata prima, in questo caso il primo input) 03 309 ACCUMULATOR --> MEMORY STORE (Immagazzina nella casella 09) il valore corrente dell'accumulatore, sempre in preparazione al passaggio successivo. 04 508 MEMORY --> ACCUMULATOR Ora che entrambi i numeri in INPUT sono immagazzinati nelle caselle 08 e 09... LOAD (carica) il primo valore di nuovo nell'accumulatore (sempre cancellandone il contenuto) 05 209 ACCUMULATOR = ACCUMULATOR - MEMORY SUBTRACT (sottrae) il secondo numero al contenuto dell'accumulatore, che contiene il primo numero 06 902 ACCUMULATOR --> OUTBOX OUTPUT (produce) il risultato del calcolo immagazzinato nell'accumulatore sull'OUTBOX 07 000 (nessuna operazione eseguita) HALT (ferma) il Little Man Computer
Uso di istruzioni con etichette e codici mnemonici
L'Assembly è un linguaggio di programmazione a basso livello che usa codici mnemonici ed etichette al posto di codici numerici. Nonostante l'LMC faccia ne faccia un uso limitato, si nota subito la convenienza di utilizzare tali codici dall'esempio sottostante, che è il programma appena presentato (sottrazione di due numeri) riscritto in linguaggio assembly: non è più necessario che il programmatore memorizzi un insieme di codici numerici anonimi, ma può programmare usando dei codici mnemonici più facili da ricordare. Se tali codici rappresentano istruzioni che coinvolgono indirizzi di memoria (ad esempio istruzioni di salto o di caricamento e salvataggio dei dati), un'etichetta viene impiegata per identificare l'indirizzo di memoria.
Questo programma d'esempio può essere compilato ed eseguito sul simulatore di LMC, disponibile sul sito internet della York University (Toronto, Canada) o sull'applicazione desktop scritta da Mike Coley. Questi simulatori includono istruzioni complete e programmi d'esempio, il compilatore assembler per convertire il codice assembly in codice macchina, interfacce di controllo per eseguire e osservare i programmi e descrizioni passo passo dettagliate di ogni istruzione dell'LMC.
INP STA FIRST INP STA SECOND LDA FIRST SUB SECOND OUT HLT FIRST DAT SECOND DAT
Etichette Senza le etichette il programmatore dovrebbe calcolare manualmente gli indirizzi di memoria: nell'esempio fatto usando i codici numerici, se una nuova istruzione venisse inserita prima dell'ultima istruzione (HLT), l'istruzione di HLT, attualmente situata all'indirizzo 07, verrebbe spostata all'indirizzo 08 (gli indirizzi vengono etichettati a partire dallo 00). Supponendo che l'utente inserisca 600 come primo input, l'istruzione 308 farebbe sì che questo valore venisse immagazzinato alla casella di indirizzo 08 e sovrascriverebbe l'istruzione 000 (l'HLT). Dal momento che l'istruzione 600 significa "salta alla casella di indirizzo 00", il programma, anziché fermarsi, finirebbe in un ciclo infinito, ricominciando dall'istruzione iniziale (alla casella 00) e tornandoci sempre alla fine (grazie all'istruzione 600, erroneamente memorizzata al posto dell'HLT). Per sopperire a questa eventualità, molti linguaggi assembly (compreso il modello LMC) combinano i codici mnemonici con delle etichette. Un'etichetta è semplicemente una parola usata sia per identificare un indirizzo di memoria dove è immagazzinata un'istruzione o dei dati, sia per riferirsi a tale indirizzo all'interno di un'istruzione.
Quando il programma è compilato dall'assembler: