Porte do XINU para o cMIPS
CI315 © Roberto André Hexsel, 2017
Este material foi escrito sob a premissa de que você leu as notas de aula
sobre Sistemas Operacionais e Interrupções, e sobre a Interface Serial.
Caveat emptor.
Antes de mais nada, crie um prompt vazio, copiando a linha
abaixo no seu terminal
alias prompt:=""
Três clicks no botão esquerdo para copiar, um click no meio para colar.
O repositório do XINU é mantido separado do repositório do cMIPS porque o
desenvolvimento do processador para o XINU caminha mais lentamente do que o
cMIPS propriamente dito. Mudanças no cMIPS só são propagadas para o XINU
quando há confiança de que elas são boas.
Atualize o código fonte do simulador.
Se você já possui um clone do repositório, atualize-o com
prompt: cd ~/xinu-cMIPS
prompt: git pull
do contrário, execute os comandos abaixo, para fazer uma cópia do
repositório para o diretório $HOME/xinu-cMIPS.
prompt: cd
prompt: git clone https://github.com/rhexsel/xinu-cMIPS.git
Acrescente ao seu caminho o diretório dos executáveis:
prompt: export PATH=$PATH:~/xinu-cMIPS/bin
Talvez seja uma boa ideia acrescentar a linha acima ao seu ~/.bashrc.
Reconstrua o simulador com a versão atualizada:
prompt: cd ~/xinu-cMIPS ; bin/build.sh
Teste sua instalação:
prompt: cd tests ; doTests.sh
1- Hierarquia de Diretórios
Em ~/xinu-cMIPS está uma réplica quase que exata do repositório do cMIPS.
A diferença é o diretório xinu, que contém a árvore com o código do
XINU.
1.1- Árvore do XINU
A distribuição do XINU foi mantida, e é organizada em:
- compile contém o Makefile e a compilação deve ocorrer neste
diretório;
- config contém os arquivos de configuração da instalação;
- device contém o código dos drivers para os dispositivos de E/S;
- include contém os arquivos com cabeçalhos, mais os cabeçalhos
específicos para o cMIPS;
- lib com o código de uma libc mínima;
- net com código da implementação do TCP/IP;
- shell com código para uma shell mínima;
- system com código para os componentes do miolo do SO, este é o
nosso diretório de trabalho principal;
- test contém programas de teste do Xinu;
- zSrc contém os fontes e versões originais de arquivos que foram
modificados para o porte.
1.2- O que temos em 2017mai02
Temos um programa main() que cria dois processos que escrevem na tela do
simulador, e que executam concorrentemente com um par produtor-consumidor,
e mais um processo (pai de todos) que imprime na tela a sequência de
números de Fibonacci.
Para reduzir a duração das simulações, o intervalo das interrupções do
relógio de tempo-real foi muito reduzido, bem como o número de ticks que
perfazem um quantum. A cada quantum, o escalonador provoca
uma troca de processos.
O intervalo entre as interrupções do relógio não pode ser curto demais para
dar tempo de o processador fazer algum trabalho útil entre duas
interrupções sucessivas.
O número de processos, o número de semáforos e de caixas postais foi muito
reduzido, com relação ao original. Isso nos permite simular com pouca
memória e portanto com tempos de simulação relativamente menores.
Toda a comunicação com o "usuário" ocorre através de kprintf(), que escreve
diretamente na saída padrão do simulador.
Vários dos arquivos fonte em system contém montes de comentários com
código de depuração. Na medida em que ganharmos confiança no porte,
trocarei estas versões pelo código original do XINU.
2- Das Simulações
Para construir o XINU são necessários os seguintes comandos:
cd ~/xinu-cMIPS/xinu
cd config ; make clean ; make install ; cd -
cd lib/libxc ; make clean ; cd -
cd compile ; make clean ; make
Os Makefiles foram adaptados para usar o cross-compilador para o cMIPS.
Há problemas com os Makefiles que não consegui resolver. Algumas mudanças
em arquivos em system provocam a re-compilação correta, outras não. Em
caso de dúvida, faça uma limpeza geral, e re-compile tudo do zero.
Com o XINU construído, suba para ~/xinu-cMIPS e diga
run.sh -v cop0.sav -t 3 -u m -n
A saída deve ser algo muito parecido com
(cMIPS Xinu) #2 (roberto@kipling) Tue May 2 10:01:04 -03 2017
sem c=0 q(10) p=1 q(12)
pid cons=3 prod=2
cons sta
c 0
prod sta
p 1
pr_A
c 1
p 2
pr_B
c 2
p 3
main
1
1
2
3
5
8
d
15
22
...
Esta simulação demora vários minutos.
Leia o código fonte de main() para entender o que está acontecendo. Em
system/main.c.
3- Da Tarefa
Passeie pelos vários diretórios, especialmente system, para ter uma
noção da excelente qualidade do código fonte do XINU.
A próxima tarefa é usar o sistema de interrupções da UART para
implementarmos a comunicação através do driver para TTY. O código
está em xinu/device/tty.
Isso significa compreender o código de baixo nível, na interface entre o
driver e o hardware e o sistema de interrupções.
XINU usa um vetor de interrupções e excessões que fica em RAM; tentaremos,
na medida do possível, usar o modelo de despacho de interrupções mais
simples, que vimos no trabalho da Interface serial. Se isso for viável.
Documentação
O arquivo docs/cMIPS.pdf contem toda a documentação do cMIPS. Para
além disso, veja o código fonte.
Repetição dos três avisos sobre o simulador:
(i) não sei como fazer para terminar a simulação sem que os asserts
emitam as mensagens de erro. De qualquer forma, o texto em maiúsculas
indica o término normal de uma simulação, ou alguma condição de erro
detectada pelo simulador;
(ii) o código de inicialização do processador é executado a partir do
endereço zero, seguido pelo código de tratamento de excessões (excp_0000 e
excp_0180) e interrupções (excp_0200). O "código normal" inicia no
endereço 0x0300 para que seja fácil identificar quando o processador
executa "programas" ou "tratadores". O compilador preenche a ROM com
zeros, que são desmontados para NOPs;
(iii) a instrução WAIT é usada para terminar a simulação e seu
argumento indica o motivo. Na função _exit() o wait 0 indica
terminação normal; em excp_handler, os códigos de terminação são
aqueles para as respectivas excessões.
--fim da aula--