Little Man Computer
O Little Man Computer (LMC) é um modelo didático de um computador, criado pelo Dr. Stuart Madnick em 1965.[1] O LMC é geralmente usado para ensinar estudantes, porque ele modela um computador simples da arquitetura de von Neumann - que possui todas as características básicas de um computador moderno. Ele pode ser programado em máquina (embora frequentemente o seja em decimal) ou em código assembly.
Arquitetura de sistema
O modelo LMC é baseado no conceito de um homenzinho trancado em uma sala pequena. No fim da sala, há 100 caixas de correio (memória), numeradas de 0 a 99, que podem conter em cada uma uma instrução de 3 dígitos ou dados (no intervalo de 000 a 999). Há ainda duas caixas de correio na outra extremidade, etiquetadas INBOX e OUTBOX, que são usados para recebimento e saída de dados. No centro da sala, há uma área de trabalho contendo uma calculadora de duas funções simples (adição e subtração) conhecida como o Accumulator e um contador reprogramável conhecido como o Program Counter. O Program Counter mantém o endereço da próxima instrução que o Little Man empregará. Este Program Counter é normalmente incrementado em 1 após cada instrução executada, permitindo ao Little Man executar um programa sequencialmente. Instruções de desvios permitem iteração (loops) e estruturas programáveis condicionais para serem incorporadas dentro de um programa. Isto obtido pela configuração o Program Counter para um endereço de memória não-sequencial se uma condição particular é verificada (tipicamente o valor armazenado no acumulador sendo zero ou positivo). Como especificado pela arquitetura de von Neumann, a memória contém ambos, instruções e dados. Cuidado precisa ser tomado para impedir o Program Counter de atingir um endereço de memória contendo dados ou o Little Man aceitará tratar isso como uma instrução. Para usar o LMC, o usuário carrega dados dentro das caixas de correio e então sinaliza para o Little Man começar a execução, começando com a instrução armazenada no endereço de memória zero. Reprogramando o Program Counter para zero efetivamente reiniciará o programa.
Ciclo de execução
![](http://upload.wikimedia.org/wikipedia/commons/thumb/3/3a/Magnifying_glass_01.svg/17px-Magnifying_glass_01.svg.png)
Para executar um programa, o Little Man realiza estes passos:
- checar o Program Counter para o número da caixa de correio que contém uma instrução de programa (ex: zero)
- fetch a instrução da caixa de correio com este número
- incrementar o Program Counter (desta forma ele contém o número da caixa de correio da próxima instrução)
- decodificar a instrução (inclui encontrar o número da caixa de correio para o dado it will work on) (say it says obter dado da caixa 42)
- fetch o dado da caixa de correio com o número encontrado na etapa anterior (por exemplo, armazenar o dado no Accumulator)
- executar a instrução
- armazenar o novo dado na caixa de correio da qual o antigo dado foi retrieved
- repetir o ciclo ou halt
Comandos
Enquanto o LMC reflete os trabalhos atuais dos processadores binários, a simplicidade dos números decimais foi escolhido para minimizar a complexidade para estudantes que não se sentem confortáveis trabalhando em binário/hexadecimal.
Instruções
Cada instrução LMC é um número decimal de 3 dígitos. O primeiro dígito representa o comando a ser trabalhado e os dois dígitos finais representam o endereço da caixa de correio afetada pelo comando.
Código numérico | Código mnemônico | Instrução | Descrição |
---|---|---|---|
1xx | ADD | ADD | Adiciona o valor armazenado na caixa de correio xx to whatever valor está atualmente no acumulador (calculadora).
|
2xx | SUB | SUBTRACT | Subtrai o valor armazenado na caixa de correio xx do whatever valor está atualmente no acumulador (calculadora).
|
3xx | STA | STORE | Armazena o conteúdo do acumulador na caixa de correio xx (destrutivo).
|
5xx | LDA | LOAD | Carrega o valor da caixa de correio xx (não-destrutivo) e entra no acumulador (destrutivo). |
6xx | BRA | BRANCH (incondicional) | Configura o contador do programa para o endereço dado (valor xx). Isto é, valor xx será a próxima instrução executada. |
7xx | BRZ | BRANCH IF ZERO (condicional) | Se o acumulador (calculadora) contém o valor 000, configura o contador do programa para o valor xx. Otherwise, não faz nada.
|
8xx | BRP | BRANCH IF POSITIVE (condicional) | Se o acumulador (calculadora) é 0 ou positivo, configura o contador do programa para o valor xx. Otherwise, não faz nada.
|
901 | INP | INPUT | Vai para o INBOX, fetch o valor do usuário, e põe ele no acumulador (calculadora).
|
902 | OUT | OUTPUT | Copia o valor do acumulador (calculadora) para o OUTBOX.
|
000 | HLT/COB | HALT/COFFEE BREAK | Interrompe o trabalho. |
DAT | DATA | Esta é uma instrução assembly que simplesmente carrega o valor dentro da próxima caixa de correio disponível. DAT pode também ser usado em conjunção com etiquetas para declarar variáveis. Por exemplo, DAT 984 armazenará o valor 984 dentro de uma caixa de correio. |
Exemplos
Numérico
Este programa (instrução 901 para instrução 000) é escrito apenas utilizando códigos numéricos. O programa toma dois números como entrada e como saída a diferença. Informado que a execução começa na caixa de correio 00 e termina na caixa de correio 07. As desvantagens desta forma de programação em linguagem de máquina são discutidas abaixo.
Caixa de correio | Código numérico | Operação | Comentários |
---|---|---|---|
00 | 901 | INBOX --> ACCUMULATOR | ENTRA o primeiro número, entra para a calculadora (apagando whatever estava ali) |
01 | 308 | ACCUMULATOR --> MEMORY[08] | ARMAZENA o valor atual da calculadora (para preparar para o próximo passo...) |
02 | 901 | INBOX --> ACCUMULATOR | ENTRA o segundo número, entra para a calculadora (apagando whatever estava ali) |
03 | 309 | ACCUMULATOR --> MEMORY[09] | ARMAZENA o valor atual da calculadora (novamente, para preparar para o próximo passo...) |
04 | 508 | MEMORY[08] --> ACCUMULATOR | (Agora que ambos os valores de ENTRADA são ARMAZENADOS nas caixas de correio 08 e 09...) CARREGA o primeiro valor de volta para a calculadora (apagando whatever estava ali) |
05 | 209 | ACCUMULATOR = ACCUMULATOR - MEMORY[09] | SUBTRAI o segundo número do valor atual da calculadora (que já configurou o primeiro número) |
06 | 902 | ACCUMULATOR --> OUTBOX | OBTÉM o resultado da calculadora para o OUTBOX |
07 | 000 | (nenhuma operação realizada) | HALT o LMC |
Mnemônica
A conveniência da mnemônica é fabricada apparent da versão da linguagem assembly do mesmo programa mostrado abaixo - o programador não é muito exigido para memorizar uma configuração de códigos numéricos anônimos, e pode agora programar com uma configuração de mais códigos mnemônicos memoráveis (este exemplo também usa etiquetas como um further aid para programação).
- Este exemplo de programa pode ser compilado e executar no simulador LMC[2] disponível no site da Universidade de York (Toronto, Canadá) ou Mike Coley.[3] Todos estes simuladores incluem instruções completas e programas sample, compiladores para converter o assembly em linguagem de máquina, controlar interfaces para executar e monitorar programas, e descrição detalhada passo-a-passo de cada instrução LMC.
INP STA FIRST INP STA SECOND LDA FIRST SUB SECOND OUT HLT FIRST DAT SECOND DAT
Etiquetas
Sem etiquetas, o programador é exigido para manualmente guardar track das locações de caixa de correio (memória). No exemplo numérico, se uma nova instrução estava para ser inserida antes da instrução HLT final então esta instrução HLT poderia se mover do endereço 07 para o endereço 08 (endereço labeling começa na locação de endereço 00). Suppose o usuário entrou 600 como a primeira entrada. A instrução 308 poderia significar que este valor poderia ser armazenado na locação de endereço 08 e sobrescrever a instrução (HLT) 000. Desde que 600 significa "saltar para o endereço da caixa de correio 00", o programa, instead de halting, poderia obter stuck em um laço sem fim.
Trabalhar around esta dificuldade, muitas linguagens assembly (incluindo o LMC) permitem o uso de etiquetas. Uma etiqueta é simplesmente uma palavra que é usada to either nome em um endereço de memória onde uma instrução ou dado é armazenada, ou para se referir para este endereço em uma instrução.
Quando um programa é assembled.
- Uma etiqueta para a esquerda de uma instrução mnemônica é convertida para o endereço de memória, a instrução ou dado é armazenada ali.
- Uma etiqueta para a direita de uma instrução mnemônica toma o valor de um endereço de memória referido abaixo.
No exemplo da linguagem assembly que usa mnemônica e etiquetas, se uma nova instrução foi inserida antes da instrução HLT final então a locação de endereço etiquetada FIRST poderia agora estar na locação de memória 09 rather than 08 e a instrução STA FIRST poderia ser convertida para 309 (STA 09) rather than 308 (STA 08) quando o programa foi assembled.
Etiquetas são, portanto, usadas para:
- identificar uma instrução particular como um alvo para uma instrução de salto
- identificar uma locação de memória como uma variável nomeada (usando DAT) e opcionalmente carregar dados no programa na vez do assembly para uso pelo programa (este uso não é óbvio até um considerar que não meio de adicionar 1 ao contador. Um poderia perguntar ao usuário para entrar 1 no início, mas isso poderia ser melhor para ter carregado isso na vez do assembly)
Exemplo
Este programa tomará uma entrada do usuário, e contará regressivamente até zero.
INP LOOP SUB ONE // Etiqueta este endereço de memória como LOOP, a instrução subtrairá o valor armazenado em ONE do acumulador OUT BRZ QUIT // Se o valor do acumulador é 0, saltar para o endereço de memória etiquetado QUIT BRA LOOP // Se o valor do acumulador não é 0, saltar para o endereço de memória etiquetado LOOP QUIT HLT // Etiqueta este endereço de memória como QUIT ONE DAT 1 // Armazena o valor 1 em seu endereço de memória, e etiqueta isso ONE (declaração de variável)
Este programa tomará uma entrada do usuário, square ela, sai a resposta e então repetir. Entrando em um zero o programa terminará.
(Nota: uma entrada que resulta em uma saída maior que 999 causará um erro devido o limite de 3 dígitos do LMC).
START LDA ZERO // Inicializa para múltiplos programas rodarem INP // Usuário provided entrada BRZ END // Salta para o fim do programa se entrada = 0 STA VALUE // Armazena entrada como valor LOOP LDA RESULT // Carrega o resultado ADD VALUE // Adiciona valor, o usuário provided entrada, ao resultado STA RESULT // Armazena o novo resultado LDA COUNT // Carrega o contador ADD ONE // Adiciona um ao contador STA COUNT // Armazena o novo contador SUB VALUE // Subtrai o valor de entrada provided pelo usuário do contador BRZ ENDLOOP // Se zero (valor adicionado ao resultado pelas vezes do valor), salta para o final do laço BRA LOOP // Salta para o laço para continuar adicionando valor ao resultado ENDLOOP LDA RESULT // Carrega o resultado OUT // Sai o resultado BRA START // Salta para o início para inicializar e obter outro valor de entrada END HLT // HALT - um zero foi registrado dessa forma! RESULT DAT // Resultado computado (defaults to 0) COUNT DAT // Contador (defaults to 0) ONE DAT 1 // Constante, valor de 1 VALUE DAT // Usuário provided entrada, o valor para ser squared (defaults to 0) ZERO DAT // Constante, valor de 0 (defaults to 0)
(Nota: DAT's default para o valor 0 porque o valor default em todas as locações de memória no Little Man Computer é 0, e dessa forma não precisa ser configurado a 0 - algum outro número, contudo, deve ser especificado.)
lmc = true
Referências
- ↑ «Little Man Computer». Illinois State University. 1 de maio de 2000. Consultado em 8 de março de 2009. Arquivado do original em 27 de fevereiro de 2009
- ↑ Chen, Stephen Y.; Cudmore, William C. «The Little Man Computer». York University. Consultado em 7 de outubro de 2010
- ↑ Coley, Mike. «The Little Man Computer». Consultado em 12 de abril de 2012
Ligações externas
- Richard J. Povinelli:Teaching:Introduction to Computer Hardware and Software:Little Man Computer
- The "Little Man" Computer
Simuladores
- Microsoft Excel LMC simulator
- Windows Executable
- Java Applet
- Windows Executable
- JavaScript
- Emacs Lisp
- Windows Executable