Curso sistemas operacionais 2014

prof. Jorge Kinoshita.

Aulas terça: 16:00-17:40H sexta: 10:20-12:00H

Teremos 28 aulas e 2 provas nos seguintes dias:

Maio Junho Agosto Programação aula a aula.

Table of Contents

1 DONE 1 - 1.1 O que é um sistema operacional, 1.2 História dos sistemas operacionais

CLOSED: 2014-05-07 Wed 16:11 DEADLINE: 2014-05-06
Apresentacao do curso: programacao aula a aula. Apresentacao do material didatico: livros do Tanenbaum e Silberzchatz. Criterio de avaliacao.

O site http://www.cs.vu.nl/~ast/ é do prof. Tanenbaum. Em seu site, ele deixou o conjunto de transparênicas: http://www.cs.vu.nl/~ast/books/mos2/mos2-ppt.zip que vamos utilizar no curso.

transparencia a ser usada: Chapter-01.ppt slides 1-8.

Pedir para os alunos se dividirem em duplas. Extra: história do Minix, Linux e comentários sobre os projetos da fase 1.

1.1 1 - Linux, system call: read

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma a se ter um processo (correspondente ao init) executando a system call read. Para isso altere o rootfs e crie arquivo lá. O boot lerá a primeira linha do arquivo e ficará em loop imprindo-a. Quando a system call read é chamada no linux, a funcao doread é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

Daniel, Gustavo relatorio: ok apresentacao: ok - deveria ter apresentado ao vivo; mas excepcionalmente nao estou descontando ponto por causa disso. Nota: 8

1.2 2 - Linux, system call: fork

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que: O processo pai (correspondente ao init) fica imprindo "sou processo 1" e o processo filho imprime "filho imprimindo". Quando a system call fork (veja o código que implementa fork) é chamada no linux, a funcao dofork é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

Carolina, Mita. relatorio: ok; faltou screen shots no relatorio. apresentacao: ok - apresentou ao vivo. Nota: 8

1.3 3 - Linux, system call: execve (ou exec)

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que: O processo pai correspondente ao init faz fork e fica imprindo "sou processo 1". O processo filho faz execve e executa o código do filho. O filho imprime "filho imprimindo". O programa correpondente ao processo pai deve estar em pai.c e o correspondente ao filho em filho.c. Os programas pai e filho devem ser previamente armazenados em rootfs através de execve. Quando a system call exec é chamada no linux, a funcao doexec é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org. Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

Cassius Puodzius Lucas Figueiredo Marcelo Risse relatorio: ok apresentacao: ok; (da proxima vez por favor apresentem ao vivo). Nota: 8

1.4 4 - Linux, system call: write

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que ele faca um "write" em algum arquivo no rootfs. Quando a system call fork (veja o código que implementa write) é chamada no linux, a funcao dowrite é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

-> Minix: a idéia é repetir o que foi feito em Linux - ou seja, fazer com que o minix execute um primeiro processo que executará alguma system call e observar como ele se comporta. O problema é que não temos como debugar o código no minix; assim vamos apenas imprimir mensagens.

Anselmo, lucas, filipe relatorio: ok, colocaram screenshots no relatorio. apresentacao: ok, fizeram ao vivo. Nota: 9

1.5 5 - minix, system call read

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call read. Para isso, talvez tenha que se abrir um arquivo e depois lê-lo a menos que esteja usando o stdin (nesse caso é necessário definí-lo). Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

Darlan dos Santos Barros Junior João Guilherme Bersani Calice Thiago Luis Bardella dos Santos

relatorio: ok apresentacao: ok; mostraram ao vivo e apresentaram o código onde ocorre o trap (int). Nota: 9.5

1.6 6 - minix, system call fork.

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call fork. O processo pai (correspondente ao init) fica imprindo "sou processo 1" e o processo filho imprime "filho imprimindo". Para isso, talvez tenha que se abrir um arquivo e depois lê-lo a menos que esteja usando o stdin (nesse caso é necessário definí-lo). Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

Eduardo, Johnny relatorio: ok, colocaram screenshots no relatorio. apresentacao: ok, fizeram ao vivo; tiveram problemas: nao bootava mais a imagem. Nota: 6.5

1.7 7 - minix, system call execve

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call execve. Para isso faca: O processo pai correspondente ao init faz fork e fica imprindo "sou processo 1". O processo filho faz execve e executa o código do filho. O filho imprime "filho imprimindo". O programa correpondente ao processo pai deve estar em pai.c e o correspondente ao filho em filho.c. Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

Tomas, Rodrigo relatorio: ok apresentacao: negativo: faltou mostrar a relacao entre sendrec o trap.; positivo: criaram uma system call para imprimir jah que nao conseguiam usar o printf. Foi curioso ver que, provavelmente devido a essa system call, as mensagens do pai e do filho estavam intercaladas. Nota: 8- Tomas, 2.5 - Rodrigo (era importante observar o sendrec x trap; - tenho duvida de como foi implementado o init…).

1.8 8 - minix, system call write

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call write. Para isso, abra um arquivo e escreva algo nele. Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

Gabriela, Guilherme. relatorio: ok, colocaram screenshots no relatorio. apresentacao: ok, fizeram ao vivo; boa apresentacao. Nota: 9.5

2 DONE 2 - Visao do hardware

CLOSED: 2014-05-12 Mon 13:08 DEADLINE: 2014-05-09
Chapter-01.ppt 9-16 - Computer Hardware Review. comentários sobre os projetos da fase 1. Alocacao das turmas. Extra: história do Minix, Linux

3 DONE 3 - 1x.3 conceitos de sistema operacional; 1.4 chamadas de sistema

CLOSED: 2014-05-14 Wed 09:30 DEADLINE: 2014-05-13

Comeca a aula procurando explicar o melhor possivel como funciona interrupcao no computador. Explicar interrupcao de software e de hardware. Relacionar com o projeto de SO. Bater a foto da losa.

transparencias Chapter-01.ppt 16-22 hardware da aula passada: memoria.

Codigo relativo: os labels ainda nao foram definidos pelo linker. Codigo absoluto: os lables foram definidos pelo linker. O programa em codigo absoluto ao ser colocado na memoria deve entrar de forma "relativa" a algum endereco (um endereco definido em um registrador base).

Quando se faz uma system call, no final a pilha deve ser limpa incrementando o SP. Explicar que tem 4 formas de se implementar push e pop em pilha.

4 DONE 4 - 1.4 chamadas de sistema 1.5 estrutra do sistema operacional.

CLOSED: 2014-05-20 Tue 19:25 DEADLINE: 2014-05-16

Finalizar Chapter-01,ppt system calls comentar sobre máquinas virtuais. sistemas monolíticos (linux) x microkernel (minix). falar sobre o projeto: os alunos devem mostrar em que código (arquivo fonte) está a interrupcao de software quando ocorre a system call. Discutimos como ocorre a system call fork -> syscall -> sendrec para PM -> int // processo usuario fica bloqueado enquanto nao recebe retorno do PM. No linux, processo usuario nao eh debugado, mesmo se compilado com opcao -g; somente o kernel eh debugado.

5 DONE 5 => apresentação dos projetos (fase 1) : grupos ímpares

CLOSED: 2014-05-28 Wed 09:40 DEADLINE: 2014-05-20

TRAZER: apresentacao em powerpoint relatorio; enviar para mim via email no dia da apresentacao. relacionar a apresentacao com o codigo do linux e minix quando apropriado.

Se sobrar tempo: Filme: https://www.youtube.com/watch?v=iBVgcjhYV2A Revolution OS https://www.youtube.com/watch?v=xHu7qI1gDPA

6 DONE 6 - apresentação dos projetos (fase 1) : grupos pares

CLOSED: 2014-05-28 Wed 09:40 DEADLINE: 2014-05-23

7 DONE 7 - 2.1 introdução aos processos

CLOSED: 2014-05-28 Wed 09:40 DEADLINE: 2014-05-27

transparencias "Processes and Threads". 1-24. Se sobrar tempo falar sobre os exercicios que passei. resumir explicacao sobre a diferenca entre treads e processos: basta colocar as transparencias principais sobre thread de kernel e de usuário. Ao explicar sobre threads seja mais rápido em afirmar que existe uma parte que cuida da execucao (PC, registradores, ponteiro de pilha) e outra que cuida dos recursos (memoria, arquivos). process group - lidar com signals de processos em foreground e background. Serah que eh usado muito hoje em dia com o X-windows? group id. Coloquei tudo em um desenho: vetor de processos e tabela de processos.

8 DONE 8 - 2.2 comunicação interprocesso até semaforos

CLOSED: 2014-06-02 Mon 10:05 DEADLINE: 2014-05-30

transparencias "interprocess communication", 1-10,11 Solucao de Peterson: 3 casos: 1- a regiao critica eh acessada em momentos diferentes - sem problema 2- a regiao critica serah acessada quase ao mesmo tempo, mas nao hah conflito em enterregion (o processo 0 ou 1 nao chaveia em enterregion) - sem problema. 3- a regiao critica serah acessada quase ao mesmo tempo e hah conflito em enterregion: o último a fazer turn=process eh o que fica em loop e nao entra na regiao critica.

Sleep and Wakeup Para pensar:

  • explique a perda de wakeup com o buffer cheio.
  • como corrigir o código adicionando uma flag informando que o sinal foi perdido?

Semáforos: Explicar como exclusao mutua pode ser feita usando semáforos. Mostrar o caso em rede de Petri.

9 DONE 9 - de semaforos a 2.3 problemas clássicos de CIP

CLOSED: 2014-06-10 Tue 10:16 DEADLINE: 2014-06-03
A aula retoma o que seja o up e o down em semaforos. transparencias "interprocess communication", 11-25 explicar exclusao mutua com semaforos modelado em redes de Petri. explicar semaforos para resolver o problema do consumidor produtor.

static class: a declaracao permite que uma classe declarada dentro de outra seja visivel fora da classe-pai.

wait( ) tells the calling thread to give up the monitor and go to sleep until some other thread enters the same monitor and calls notify( ). notify( ) wakes up the first thread that called wait( ) on the same object. notifyAll( ) wakes up all the threads that called wait( ) on the same object. The highest priority thread will run first. Monitores, condition variables: http://en.wikipedia.org/wiki/Monitor_%28synchronization%29

10 DONE 10 - 2.4 agendamento de processo + problema reader/writer.

CLOSED: 2014-06-10 Tue 10:17 DEADLINE: 2014-06-06

Transparencias "scheduling - introduction to scheduling" provavelmente sobrará tempo; complementa com discussao sobre os exercicios fase 2; ou com exercicios.

Explicar melhor o conflito no batch system entre turnround time e throuput. Ao colocar jobs mais curtos na frente diminuo o tempo de retorno medio (mean turnround time) pg 109 - minix3. Ao colocar jobs mais curto na frente aumento a vazao, pg 107; porem posso ter tempos de retorno terriveis para processos longos.

11 DONE 11 => Projetos 2.5 visão geral de processos em minix (fase 2)

CLOSED: 2014-06-13 Fri 10:03 DEADLINE: 2014-06-10

equipes pares

12 DONE 12 => Projetos 2.5 visão geral de processos em minix (fase 2)

CLOSED: 2014-06-16 Mon 20:41 DEADLINE: 2014-06-13

equipes ímpares

13 DONE 13 prova 1

CLOSED: 2014-06-27 Fri 13:31 DEADLINE: 2014-06-27

14 DONE 14 - 3.1 Hardware Entrada e Saida 3.2 Software Entrada e Saida

CLOSED: 2014-06-26 Thu 10:52 DEADLINE: 2014-06-24

Transparencias do silberschatz capitulo 13. até 13.16

15 DONE 15 - 3.2 Software Entrada e Saida

CLOSED: 2014-07-08 Tue 08:49 DEADLINE: 2014-07-04

Transparencias do silberschatz capitulo 13. do slide 13.17 até o final. pula a parte de streams.

16 DONE 16 - 3.3 impasses

CLOSED: 2014-07-18 Fri 12:22 DEADLINE: 2014-07-18

17 DONE 17 => Projetos 3.4 visão geral de E/S no minix (fase 3)

CLOSED: 2014-07-14 Mon 10:54 DEADLINE: 2014-07-11

equipes ímpares

18 DONE 18 => Projetos 3.4 visão geral de E/S no minix (fase 3)

CLOSED: 2014-07-16 Wed 10:13 DEADLINE: 2014-07-15

equipes pares

19 DONE 19 - 4.1 gerenciamento básico de memória 4.2 troca (swap)

CLOSED: 2014-07-28 Mon 09:55 DEADLINE: 2014-07-22

-> Como gerenciar memória no evaluator 7t que nao possui MMU?

  • para deixar a aula mais interessante deveria comentar como funcionamento o gerenciamento de memoria no minix sem usar a memoria virtual.

-> dar a aula rapidamente e depois comentar o que eh cada exercicio da fase 4 no final da aula; enfatizando principalmente os exercicios que envolvem o minix.

20 DONE 20 -4.3 memória virtual, 4.4 algoritmos de substituição de página.

CLOSED: 2014-07-28 Mon 09:56 DEADLINE: 2014-07-25

Inverted page tables http://www.cs.nmsu.edu/~pfeiffer/classes/573/notes/ipt.html geralmente a tabela de páginas é uma por processo, mas no caso da inverted page table, não. Nesse caso, a memória RAM está dividida em páginas sendo algumas para um processo, outras para outro processo, etc. A inverted page table mapea essa RAM atribuida a vários processos. Funciona graças aa TLB que armazena as entradas da tabela de paginas. No maximo ateh algoritmo de troca otimo.

21 DONE 21 - 4.4, 4.5 questões para sistemas de paginação.

CLOSED: 2014-07-30 Wed 07:59 DEADLINE: 2014-07-29

termina algoritmos de troca tanenbaum transparencias vitural memory (2) 15-27 exercicio 4.12 pg 442

22 DONE 22 - 4.6 segmentação // sobrou tempo? Como é o gerenciamento de memoria no linux? // coloca algumas figuras do livro do silberschatz para discussao.

CLOSED: 2014-08-04 Seg 12:17 DEADLINE: 2014-08-01

  • De final de working set ateh segmentacao.
  • memória Linux.

http://www.youtube.com/watch?v=NtKAG46_3Vg - memoria linux http://kerneltrap.org/node/2450/ memoria linux http://www.youtube.com/watch?v=L2SED6sewRw - desenvolvimento do kernel Item 21.6.2 do Silberschatz

  • colocar um mapa geral de um SO.

23 DONE 23 => Projetos 4.7 visão geral do gerenciamento de memória do minix (fase 4)

CLOSED: 2014-08-12 Ter 10:39 DEADLINE: 2014-08-05
equipes pares

24 DONE 24 => Projetos 4.7 visão geral do gerenciamento de memória do minix (fase 4)

CLOSED: 2014-08-12 Ter 10:40 DEADLINE: 2014-08-08
equipes impares.

25 DONE 25 - 5.1 arquivos 5.2 diretórios 5.3 implementação do sistema de arquivos

CLOSED: 2014-08-13 Qua 09:16 DEADLINE: 2014-08-12
ateh inodes. Finalizar com: Qual o tamanho maximo do arquivo? transparencia de i-node no unix.

26 DONE 26 - 5.3 implementação do sistema de arquivos

CLOSED: 2014-08-18 Seg 10:25 DEADLINE: 2014-08-15
terminar sistemas de arquivos e falar sobre seguranca (cap 9 do sistemas operacionais modernos 3, ou cap 5 do projeto e implementacao).

27 [27] => Projetos 5.6 visão geral do sistema de arquivos minix (fase 5)

equipes impares

28 [28] => Projetos 5.6 visão geral do sistema de arquivos minix (fase 5)

equipes pares

29 TODO 29 Fechamento do curso; revisao rápida da disciplina com aspectos históricos de sistemas operacionais.

DEADLINE: 2014-08-19 Ter

  • uma visao unificada do minix: integrando caps 3,4,5 no microkernel.
  • do minix para o linux.
  • comentario sobre virus.
  • em que o curso pode ser melhorado?

30 TODO 30 prova 2

DEADLINE: 2014-08-22

31 TODO prova sub

32 Livro texto:

Sistemas Operacionais - Projeto e Implementação ; Tanenbaum A.S. Woodhull A.S.; Bookman terceira edição Obs: Este livro contém o Minix que serviu de base para a criação do Linux, mas a versão atual é a 3.0.

Bons Livros de apoio:

  • Sistemas Operacionais Modernos 3a. edição; Tanenbaum A.S.; Prentice Hall

Obs: Este livro é muito parecido com "Projeto e Implementação" mas não contém o Minix. Por outro lado é mais didático e contém mais informação que o outro.

  • Sistemas Operacionais com Java; Silberschatz, Galvin, Gane; Editora Campus

Obs: Este livro apresenta os conceitos de forma mais clara que os livros do Tanenbaum, porém não usa um sistema operacional próximo da realidade, usa apenas pequenos exemplos em java; e provavelmente o aluno perde a noção do sistema operacional como um todo.

Sobre Linux: Robert Love, Linux Kernel Development Understanding the Linux Kernel – Publisher: O'REILLY http://www.google.com/books?q=isbn%3A978-0-596-00565-8 Linux Kernel in a Nutshell – Publisher: O'REILLY: http://www.kroah.com/lkn/ UNIX Internals: The New Frontiers – Author: Uresh Vahalia http://www.google.com/books?q=isbn%3A9780131019089 Design of The Unix Operating system – Author: Maurice J.Bach http://www.google.com/books?q=isbn%3A9780132017992 Professional Linux Kernel Architecture [Paperback] Wolfgang Mauerer (Author)

33 avaliação:

Nesse caso a avaliacao eh dada por: Nota final = (3 P1 + 4 P2 + 3 P)/10 Caso contrário, a avaliacao final eh dada por: Nota final = (3 P1 + 4 P2)/7

34 Grupos para os projetos.

Grupo 1‬: Lucas, Ricardo e Rafael Grupo 2‬: Gabriel Andreatto, Vinicius, Thales Grupo 3‬: Carolina, Marcela e Thais Grupo 4: Mi Che Li, Felipe e Marcelo Jr Grupo 5: Diego, Henrique Kano e Leonardo Grupo 6: André, Marcelo Kiyukawa e Bruno Grupo 7: Tiago Goto, Ivan, Filippe Grupo 8: Gabriel Vilas Boas, Henrique e Tiago

35 Criterios de avaliacao.

  • tempo: 20 minutos por equipe, com 5 minutos para perguntas.
  • usar powerpoint para explicar o que foi feito.
  • apresentar o sistema rodando ao vivo (muito importante!!!) (caso contrário 1 ponto a menos no mínimo na nota).
  • entregar um relatorio em pdf no dia da apresentacao. Serah descontado um ponto por dia de atraso na entrega do relatorio.

O relatório e apresentacao em powerpoint devem conter: a. todos os passos para desempenhar a tarefa com referencias caso houver (a sites, livros, etc.). b. print screens da tela - geralmente da maquina virtual. A nota costuma ser dividida entre os alunos que apresentarem o trabalho em pesos iguais; porém os pesos podem ser alterados a critério dos alunos. 8 - bom; o aluno fez o esperado. 10 - melhor que o esperado. cada equipe deve entregar o relatorio no dia da apresentacao via email; cada dia de atraso corresponde a um ponto a menos.

36 Fase 1:

Objetivos gerais: . existem dois grandes tipos de sistemas operacionais: microkernel (minix) e monolítico (linux). Algumas equipes trabalharao com o minix e outras com o linux, de tal forma que os alunos possam comparar ambos. . criar processos de usuários que facam chamadas de sistema e observar como elas se comportam. . system call faz com que o processador passe do modo usuário para o modo kernel. Como isso ocorre? É possível visualizar isso? . dados do kernel sao mais difíceis de serem visualizados por processos comuns. Como o "ps" e "top" visualizam dados do kernel? Através de /proc. . fazer pequenas alteracoes no kernel. Exemplo: fazer o kernel imprimir uma mensagem em um dado momento.

Tarefas:

8 equipes: 4 minix e 4 linux.

-> Linux 4 equipes farão testes baseados em

http://balau82.wordpress.com/2010/03/22/compiling-linux-kernel-for-qemu-arm-emulator/

A idéia é criar um programa bem simples rodando como o init (primeiro processo rodando em cima do sistema operacional) em um linux rodando na máquina virtual. Esse processo pode disparar system calls. Cada uma das equipes testará uma system call diferente. O grande objetivo é observar o código do kernel sendo executado logo após a system call.

-> Minix Instalem o minix 3.1 em uma máquina virtual pois é a versão compatível com o livro e portanto com mais documentação. A imagem iso (ex: minix-3.1.0-book.iso na internet) deve ser bootada pela maquina virtual (ex: virtual box). Uma vez que ela logou entre com: root, e siga http://wiki.minix3.org/en/UsersGuide/DoingInstallation isto é: setup e vai seguindo praticamente só dando enter. Não se esqueca de usar a rede. Usei AMD Lance. Ao terminar o setup, faca: shutdown

Desligar e comecar novamente a maquina virtual MINIX3 mas com a imagem iso fora (remova da maquina virtual a imagem iso do disco para ver bootando pelo HD).

Observando https://groups.google.com/forum/#!topic/minix3/tSvzp81M8_o Ativando a rede: teste ifconfig - vc. pode observar /dev/ip /bin/service up /usr/sbin/inet

O minix 3.1 dentro da máquina virtual pode se comunicar via tcp/ip com o host - windows ou linux. É possível abrir um servidor de FTP de forma que o host enxergue todo o filesystem do minix. Isso possibilita navegar pelo código fonte do minix, bem como fazer alterações no código através do seu editor de texto preferido dentro do host.

36.1 1 - Linux, system call: read

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma a se ter um processo (correspondente ao init) executando a system call read. Para isso altere o rootfs e crie arquivo lá. O boot lerá a primeira linha do arquivo e ficará em loop imprindo-a. Quando a system call read é chamada no linux, a funcao doread é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Dica: use o grep. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

nota: 8

36.2 2 - Linux, system call: fork

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que: O processo pai (correspondente ao init) fica imprindo "sou processo 1" e o processo filho imprime "filho imprimindo". Quando a system call fork (veja o código que implementa fork) é chamada no linux, a funcao dofork é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

nota: 8

36.3 3 - Linux, system call: execve (ou exec)

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que: O processo pai correspondente ao init faz fork e fica imprindo "sou processo 1". O processo filho faz execve e executa o código do filho. O filho imprime "filho imprimindo". O programa correpondente ao processo pai deve estar em pai.c e o correspondente ao filho em filho.c. Os programas pai e filho devem ser previamente armazenados em rootfs através de execve. Quando a system call exec é chamada no linux, a funcao doexec é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org. Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

nota: 8

36.4 4 - Linux, system call: write

Altere o boot do linux apresentado em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org de forma que ele faca um "write" em algum arquivo no rootfs. Quando a system call fork (veja o código que implementa write) é chamada no linux, a funcao dowrite é executada dentro do kernel. Explique como isso ocorre, observando o código fonte do linux e o tutorial em http://www.pcs.usp.br/~jkinoshi/2012/linux-qemu-gdb.org . Localize no código do linux onde é feito o SWI - software interrupt. Da forma como estamos debugando o código podemos apenas observar código em modo kernel e não em modo usuário. Procure colocar o breakpoint o mais perto possível da instrucao SWI; se possível logo na primeira instrucao após o SWI. Relacione o endereco dessa primeira instrucao com o vetor de interrupcao. Gere um relatório anexando apenas as partes de código mais relevantes e relacionadas com o SWI, bem como print screens da tela do qemu.

-> Minix: a idéia é repetir o que foi feito em Linux - ou seja, fazer com que o minix execute um primeiro processo que executará alguma system call e observar como ele se comporta. O problema é que não temos como debugar o código no minix; assim vamos apenas imprimir mensagens.

Observaram que o registrador R7 contem o numero da syscall a ser executada; relacionaram sysread, syswrite com a macro. nota: 10

36.5 5 - minix, system call read

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call read. Para isso, talvez tenha que se abrir um arquivo e depois lê-lo a menos que esteja usando o stdin (nesse caso é necessário definí-lo). Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

-> usaram uma imagem pronta para o vmware que facilitava a entrada na internet e usaram o filezilla para o ftp. Nao trocaram o init.c

nota: 7.5

36.6 6 - minix, system call fork.

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call fork. O processo pai (correspondente ao init) fica imprindo "sou processo 1" e o processo filho imprime "filho imprimindo". Para isso, talvez tenha que se abrir um arquivo e depois lê-lo a menos que esteja usando o stdin (nesse caso é necessário definí-lo). Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

-> Usaram o minix normal e editaram com o elle. Tentaram mexer no init.c Mostraram imprimindo toda vez que ocorria o fork o que permitia observar quando a shell disparava ou nao um processo filho. Nao observaram o uso do sendrec.

nota: 8 -2 (atraso) = 6.

36.7 7 - minix, system call execve

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call execve. Para isso faca: O processo pai correspondente ao init faz fork e fica imprindo "sou processo 1". O processo filho faz execve e executa o código do filho. O filho imprime "filho imprimindo". O programa correpondente ao processo pai deve estar em pai.c e o correspondente ao filho em filho.c. Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

-> nao observaram o uso do sendrec, por outro lado mostraram a rotina que chamava a syscall. nota: 7.5

36.8 8 - minix, system call write

Altere o minix de forma que logo ao ser ligado, um processo correspondente ao init é criado e execute a system call write. Para isso, abra um arquivo e escreva algo nele. Para que a system call seja executada, o processo de usuário envia uma mensagem solicitando o servico ao servidor correspondente através de um sendrec. Coloque uma mensagem no servidor assim que ele comecar a tratar o servico.

nota: 0 nao entregaram.

37 Fase 2

4 experiencias envolvendo Linux e 4 Minix.

Objetivos gerais: observar topicos do cap. 2 do livro do minix tanto no linux quanto no minix.

Linux

37.1 1 `- semáforo.

Em http://www.linuxdevcenter.com/lpt/a/7029 temo a apresentacao de threads em modo usuario usando semaforos; porem versoes de semaforos para threads sem fazer chamadas de sistema. Em http://www.cis.upenn.edu/~lee/07cis505/Lec/SemaphoreOperations.pdf temos o uso de semaforos fazendo chamadas de sistema - semop.

Altere o init para fazer algo como:

if (fork() ) {
   while (1) {
      print "1"
      down(S) 
      print 2
      up(S)
      print 3
   }


} else {
  while (1) {
      print "A"
      down(S)
      print X 
      print B
      up(S)
      print C
   }
}

trocando up e down pelo semop. O valor do semáforo é gerenciado pelo kernel porque duas ou mais threads podem estar alterando o seu valor e o kernel deve evitar condicoes de corrida nessas alteracoes. Coloque um breakpoint para observar como o kernel altera o valor do semáforo e retire print screens. Vamos supor que uma thread A fique bloqueada aguardando o incremento do semáforo por outra thread B. No momento em que a outra thread B pedir ao kernel para incrementar o semáforo, o kernel deve desbloquear a thread A. Analise o código do kernel do linux e descubra onde isso ocorre. Coloque um breakpoint nessa posicao, rode o gdb até essa posicao, retire um printscreen. Analise a fila de execucao dos processos. Para isso será necessário estudar http://isis.poly.edu/kulesh/stuff/src/klist/ para entender como o kernel do linux gerencia listas. Motre o processo bloqueado no down e sendo desbloqueado pelo up. Verifique que no "up", o processo bloqueado é retirado da fila do semáforo e vai para a fila dos processos prontos. Encontre o código onde o processo desbloqueado é colocado na fila do escalonador.

9 -> bom, apresentaram bem, mostraram indo para o kernel e alterando as filas. Futuramente, ver o codigo do spin lock no kernel no up e no down. Faltou o cabo hdmi para a apresentacao

37.2 2 - signal

Entenda o seguinte código:

#include<stdio.h>
#include<signal.h>
void bypass_sigint(int sig_no)
{
  printf("dividi por zero\n");
}
int main()
{
  int a,b,c;
    struct sigaction sa;
    memset(&sa, 0, sizeof(sa));
    sa.sa_handler = &bypass_sigint;
    sigaction(SIGFPE, &sa,NULL);
    while (1) {
      sleep(1);
        printf("do nothing \n ");
    }
    return 0;
}

Esse código ativa a funcao sigint toda vez que houver uma divisão por zero. Mas um outro processo pode enviar um signal, dizendo que houve uma divisão por zero. Experimente em uma outra shell fazer: kill -8 #pidprocesso

onde -8 se refere a SIGPFE, divisão por zero. Para você realmente observar que houve uma divisão por zero, experimente colocar dentro do código, após sigaction:

a = 1; b= 0; c = a/b;

e veja que a rotina imprime "dividi por zero".

Experimente em uma outra shell fazer: kill -8 #pidprocesso

Como o linux trata a divisão por zero? Explique o código. É de se esperar que o linux envie um signal para o processo que fez a divisão por zero. Faça um programa executável que faz a divisão por zero no linux rodando no qemu. Rode o programa e capture o signal imprimindo na tela uma mensagem toda vez que for feita a divisão por zero. O kernel contém uma estrutura de dados guarda o signal handler do processo. Estude o código que trata sigaction(SIGFPE, &sa,NULL); e observe qual é essa estrutura de dados. Quando ocorrer a divisão por zero, essa estrutura de dados será usada para ativar o signal handler ( bypasssigint) adequado. Faça um print screen do qemu logo ao entrar na rotina que faz o tratamento da divisão por zero (observando qual é o endereco da rotina a ser executada dada pelo vetor de interrupcao do ARM - pesqui sobre isso). Realmente eh possivel que um processo A envie um signal a um outro processo B (através do kill), fazendo com que B ache que houve uma divisão por zero dentro do linux? O que acontece desde a interrupcao gerada pela divisao por zero ateh a chamada da rotina bypasssigint (signal handler)? Como o SO fica sabendo qual é o signal handler que deve ser chamado?

7 -> Nao observaram a estrutura de dados dentro do kernel onde amarra os handlers e os signals.

37.3 3 - escalonador diferente

Objetivo: No projeto anterior, a equipe 3 alterou o init e criou o processo pai e filho que ficaram imprimindo mensagens; porém ele ficava um tempo imprimindo mensagens do pai e um tempo imprimindo mensagens do filho. O printf faz uso da system call write; porém quando o write é chamado o processo não é chaveado (isto é, por exemplo, após a syscall write, o processo pai volta ao processo pai). Altere o kernel do linux 2.6.39 de forma que o escalonador troque de processo na chamada da system call write.

Antes de alterar, faca o seguinte e apresente ao professor:


Estude como funciona as listas no kernel do linux. Elas fazem uso de: struct listhead Veja: http://isis.poly.edu/kulesh/stuff/src/klist/ . Estude essa pagina, compile e debugue testlists.c para observar como os itens sao adicionados e removidos na lista; ou ainda, como a lista pode ser percorrida. Dentro de testlists.c existe o comentário:

/* at this point: pos->next points to the next item's 'list' variable and 
 * pos->prev points to the previous item's 'list' variable. Here item is 
 * of type struct kool_list. But we need to access the item itself not the 
 * variable 'list' in the item! macro list_entry() does just that. See "How
 * does this work?" below for an explanation of how this is done.
 */

Rode o código passo a passo no gdb e observe a estrutura mylist através de comandos como: p mylist->list->next->next->next Após isso, explique com suas palavras o significado do comentário acima.

Em particular observe:

Dentro do kernel, em fork.c existe: struct taskstruct *p; que contém a informacao sobre o processo sendo criado.

Essa estrutura é preenchida e depois é colocada em uma runqueue (fila de execucao) (em sched.c). Onde isso ocorre no código? Procure rodar o código até que o linux faca um listadd colocando o processo uma runqueue. Retire printscreens da tela. Explique as filas de execucao do linux e porque escolheu uma determinada fila para colocar o processo para rodar.

Podemos imprimir mensagens de dentro do linux kernel em um log. Veja: http://www.ibm.com/developerworks/linux/library/l-kernel-logging-apis/index.html

sugestao: No minimo, faca uma alteracao em picknexttaskfair de forma a retirar sempre o processo que estah rodando da fila de execucao. Eh uma modificacao muito simples que nao funciona a ponto de estar sempre chaveando os processos pai e filho a cada impressao.

9 -> fizeram a modificacao. Ficou bem interessante. A leitura em http://www.ibm.com/developerworks/library/l-completely-fair-scheduler/ foi boa.

37.4 4 - chaveamento dos processos.

Usando qemu rodando o linux compilado para o Versatile, faca com que o linux rode apenas um processo: o processo que continuamente le caracteres do teclado (usando getch) e os imprime na tela. Coloque um breakpoint na interrupção de teclado. Faça um print screen do qemu mostrando a primeira instrução logo ao entrar no tratamento de interrupção do teclado. Relacione o valor do endereço que você vê, com o manual do ARM7 (consulte na internet como o ARM trata interrupcoes de hardware; veja tambem a apostila usada no laboratorio de microprocessadores). Onde (em qual arquivo fonte do linux) o estado do processo é armazenado? Relacione isso com o código do linux e explique. Ao sair da rotina de interrupção, um outro processo foi escalonado para rodar? Qual processo? Apresente um print screen dos registradores antes de sair da interrupção. Como ao sair da interrupção, o novo processo passa a rodar? Com que Program Counter? Explique. Após a syscall getch, o processo é bloqueado enquanto nada é teclado. Mostre como o processo é bloqueado (retirado da fila de execucao e colocado em uma outra fila para esperar o caracter). Após o caracter ser teclado, ocorre a SWI, e o processo é então desbloqueado. Mostre como isso ocorre. Retire os printscreens mostrando isso ocorrendo e anexe no relatório.

9 -> embora nao tenham conseguido colocar um breakpoint logo na entrada da interrupcao de hw, colocaram em outros pontos consequentes e conseguiram observar quando era interrupcao de tempo (=4) e colocaram um breakpoint condicional (!=4) para observar a interrupcao de teclado. Nao chegaram a observar como o program counter eh trazido; mas foram bem. Usaram getchar ao inves de getch.

37.5 5 - semáforo.

Implementar semáforos no minix. Será necessário estudar o kernel do minix, observando como manter o processo em estado bloqueado ao fazer uma operação de down. Implemente as seguintes system calls:

int inicia(int valor); exemplo: S = inicia(3); # inica um semáforo com 3 e retorna o número do semáforo em S. O número zero é reservado; se S == 0 então deu erro em inicia.

int down(int S); faz a operação de down no semáforo S; se der problema retorna -1.

int up(int S); faz a operação de up no semáforo S

int status(int S, int *valor, int *procbloqueados); coloca em valor, o valor do semáforo S e em procbloqueados, o número de processos bloqueados no semáforo.

Essas system calls devem ser implementadas pelo processo PM (antigo MM).

Dica: dado que existe apenas um processo PM, é fácil pensar que up e down serão mutualmente exclusivos pois o PM estará tratando a mensagem up ou a mensagem down não podendo tratar as duas ao mesmo tempo. Isto é: não será necessário desabilitar as interrupções para se implementar o up e o down. Como o processo usuário vai enviar uma mensagem ao PM então o estado de bloqueado pode ser conseguido, simplesmente se o PM não responder ao processo enquanto o semáforo não subir.

Declare dentro de PM uma tabela que contenha 20 linhas, uma para cada semáforo; isto é, o minix terá no máximo 20 semáforos. Em cada linha existem duas informacoes: 1. o valor de semaforo e a fila de processos bloqueados esperando o incremento do semaforo.

Para comecar a mexer com o minix, entenda como um processo usuário fica bloqueado ao executar uma system call. Primeiro o processo usuário envia uma mensagem ao servidor. Exemplo: quando o processo faz signal; uma mensagem é enviada ao PM. O processo usuário fica bloqueado enquanto o PM não responder que a system call foi completada. Portanto, a falta de resposta leva um processo de usuário a ficar bloqueado. É justamente essa característica que vamos utilizar para bloquear um processo de usuário. Para isso, como sugestão: replique uma sistem call do PM; por exemplo, o signal. Crie o signal1, cópia do signal. Retire tudo de signal1 e estude apenas como o processo PM retorna uma mensagem ao processo que solicitou o signal desbloqueando-o. Agora crie um "bloqueia" que é igual ao signal1 e não envia a mensagem de retorno e o desbloqueia que apenas envia uma mensagem ao processo que fez o bloqueio como o signal1 enviaria. Use os semáforos no programa produtor-reprodutor.

6-> Infelizmente nao conseguiram fazer bem o "up". Aparentemente faltou pouca coisa no codigo; o problema eh que isso impactou o resto da apresentacao.

37.6 6 - signal

Entenda o seguinte código:

#include<stdio.h>
#include<signal.h>
void bypass_sigint(int sig_no)
{
  printf("dividi por zero\n");
}
int main()
{
  int a,b,c;
    struct sigaction sa;
    memset(&sa, 0, sizeof(sa));
    sa.sa_handler = &bypass_sigint;
    sigaction(SIGFPE, &sa,NULL);
    while (1) {
      sleep(1);
        printf("do nothing \n ");
    }
    return 0;
}

Esse código ativa a funcao sigint toda vez que houver uma divisão por zero. Mas um outro processo pode enviar um signal, dizendo que houve uma divisão por zero. Experimente em uma outra shell fazer: kill -8 #pidprocesso

onde -8 se refere a SIGPFE, divisão por zero. Para você realmente observar que houve uma divisão por zero, experimente colocar dentro do código, após sigaction:

a = 1; b= 0; c = a/b;

e veja que a rotina imprime "dividi por zero".

Experimente em uma outra shell fazer: kill -8 #pidprocesso

Como o minix trata a divisão por zero? Explique o código. É de se esperar que o minix envie um signal para o processo que fez a divisão por zero. Se o minix não fizer isso, implemente. Faça um programa executável que faz a divisão por zero no minix rodando no bochs (http://pdos.csail.mit.edu/6.828/2006/tools.html). Rode o programa e capture o signal imprimindo na tela uma mensagem toda vez que for feita a divisão por zero. Faça um print screen do bochs logo ao entrar na rotina que faz o tratamento da divisão por zero (observando qual é o endereco da rotina a ser executada dada pelo vetor de interrupcao). Realmente eh possivel que um processo A envie um signal a um outro processo B (através do kill), fazendo com que B ache que houve uma divisão por zero dentro do minix? E no linux? O que acontece desde a interrupcao gerada pela divisao por zero ateh a chamada da rotina? Como o SO fica sabendo qual é o signal handler que deve ser chamado?

6 -> Entenderam erradamente que eu havia pedido para alterar o tratamento global, imprimindo uma mensagem caso qualquer processo fizesse uma divisao por zero. Teoricamente, poderiam ter implementado sim, mas infelizmente nao conseguiram. Nao observarm como o endereco da funcao eh armazenado no PM. Conseguiram colocar o breakpoint logo ao dividir por zero e localizar a rotina de interrupcao.

37.7 7 - escalonador diferente

Modifique o escalonador do Minix3 para monitorar quanto tempo da CPU cada processo de usuário recebeu recentemente. Quando nenhuma tarefa ou servidor quiser executar, escolha o processo de usuário que recebeu a menor fatia de CPU.

Obs: exercicio retirado do livro do minix.

9 -> foram bem. Fizeram o que foi pedido, mostrarm na tela o minix chaveando dois processos em suas filas de execucao. Se disparar os processos em tempos diferentes, eles se acomodam em filas de prioridade diferentes. Se disparar ao mesmo tempo se acomodam na mesma fila de prioridade.

37.8 8 - chaveamento dos processos.

As equipes de linux estão vendo o ARM, porém o minix roda no pentium. O pentium é bem mais complexo que o ARM e o objetivo desse trabalho é estudar o chaveamento de processos no minix e sua interface com o pentium. Através da máquina virtual bochs, será possível ver o assembly do minix rodando nesse chavemento. Isso porque o bochs emula as instrucoes ao invés de executar direto no processador. Use o bochs em modo debug (deve ser compilado para isso de acordo com o lab1 do MIT http://pdos.csail.mit.edu/6.828/2006/tools.html) para estudar o minix. Veja:

  • Manuais da intel (na internet) como por exemplo: Pentium® Processor Family, Developer's Manual Volume 3: Architecture and Programming Manual.

Após a inicialização do minix, pare o minix dentro do bochs e coloque um breakpoint na interrupção de teclado. Faça um print screen do bochs mostrando a primeira instrução logo ao entrar no tratamento de interrupção do teclado. Relacione o valor do endereço que você vê, com o declarado na IDT, GDT e LDT. O minix guardará os registradores. Como o hardware e o código do minix fazem isso? Em particular, como é armazendo o Program Counter (ou Instruction Pointer, EIP)? Onde o estado do processo é armazenado? Relacione isso com o código do minix e explique. Ao sair da rotina de interrupção, um outro processo foi escalonado para rodar? Qual processo? Apresente um print screen dos registradores antes de sair da interrupção. Como ao sair da interrupção, o novo processo passa a rodar? Com que Program Counter (EIP)? Explique. Explique a funcao save chamada logo na entrada da rotina de interrupcao (rastreie usando o bochs). Como é guardado o endereco de retorno de save? Como a funcao "save" retorna? Rastreie usando o bochs. Pesquisem na internet sobre o TSS (além do IDT, GDT, LDT). Como o TSS é usado no chaveamento de processos? Rastree o retorno de save no bochs.

7.5 -> Nao apresentaram nada sobre o TSS e mal discutiram as estruturas GDT e LDT. Nao observaram como o EIP (program counter) eh armazenado na pilha (teriam que ver como a pilha eh setada antes do chaveamento). Porem, conseguiram colocar o breakpoint usando o bochs.

38 Fase 3

Todas as turmas: apresentem rodando ao vivo.

38.1 1 Linux sysfs

Leia: libudev and Sysfs Tutorial em http://www.signal11.us/oss/udev/ Responda:

  • por que criaram o sysfs?
  • por que criaram a libudev?

Experiencia:

  • 1. rode o código que faz uso da libudev para apresentar dados de dispositivos USB conectados ao linux normal.
  • 2. adapte esse código para rodar no kernel 2.6.39 usando ARM no qemu. Provavelmente voce nao terá USB conectados, mas com certeza terá um disco conectado. Procure apresentar dados de um dispositivo qualquer usando as rotinas do libudev.

7 -> erro ao rodar no init no qemu; ou seja, nao fizeram a parte 2 que era a mais complexa.

38.2 2 Linux -SIGALRM

fazer a placa versatile imprimir um caracter a cada 15 segundos. Para isso você pode criar um alarme que é disparado de 15 em 15 segundos (estude signal( SIGALRM, handler )). Usando o gdb, livros, internet, source do linux, printks estude o caminho entre a interrupcao de tempo desde o vetor de interrupcao ateh a ativacao do signal handler. Coloque um breakpoint no código do linux que analisa a interrupcao de tempo e observa se existe algum processo com algum signal handler vinculado. Altere o código do kernel do linux de forma a imprimir mensagens quando:

  • o signal handler é registrado.
  • o kernel encontra o signal handler a ser ativado.

Dica: consulte livros sobre o kernel do linux. Frisando novamente: examine e mostre como a interrupcao de tempo acaba disparando o signal handler no processo.

7.8 - 1(atraso) = 6.8 -> observaram diversos ponto de dentro do kernel onde o o registro do signal e a ativacao do signal sao feitos, colocando mensagens por printk. Ao inves de "signal" eh melhor usar sigaction (no kernel dosigaction). Infelizmente nao mostrarm o codigo fonte do kernel ao debugar (o source nao estava vinculado).

38.3 3 Linux - dtrace, driver de video.

O dtrace é uma modificacao no kernel do linux feita orignalmente pela Sun (vendida para a Oracle) com o objetivo de facilitar o debug de aplicativos observando dados do kernel. A idéia é colocar probes (como pontas de prova) dentro do kernel e apresentar os resultados dependendo de certas circunstancias (para nao poluir a saida).

Instale o dtrace no ubuntu: https://sites.google.com/site/opensparclabmodule/dtrace-notes/installdtraceonubuntu1204lts

Usando o dtrace podemos monitorar as leituras e escritas em um driver. Use o dtrace para monitorar o driver de uma webcam: quantos bytes sao repassados da camera por segundo?

Explique para a classe como funciona o dtrace; aprensente scripts bem simples (por exemplo que monitora certas system calls dependendo de certas condicoes) para a classe entender. Explique o monitoramento do driver da webcam com dtrace interecptando a leitura de um frame da webcam. Retire printscreens e apresente ao vivo em sala de aula.

Sugestao: Instale o dtrace em um ubuntu 12.4 e apresente o cheese fazendo leituras da webcam. Mostre o numero de bytes que estao sendo lidos.

9 -> Usaram o https://github.com/dtrace4linux/linux pois nao funcionou com o link apresentado. Mostraram ao vivo com a webcam.

38.4 4 Linux - construir o driver padrao no arm linux.

A partir de: http://www.pcs.usp.br/~jkinoshi/2008/Exp8_revisada_13_08_07.doc: 1 - crie um driver simples no linux normal (ex: ubuntu). 2 - crie o driver padrao e teste a leitura e escrita no driver usando "echo" na maquina virtual. O passo 1 é muito simples, porém existem diversas dificuldades para fazer o mesmo na maquina virtual/ARM:

  • como criar uma entrada no rootfs para o driver padrao? Deve ser através de system calls para se fazer o mknod. Assim, crie um init que somente irá criar uma entrada em /dev em rootfs para o driver da entrada padrao.
  • a compilacao do driver padrao para o ARM pode apresentar dificuldades. Existem duas formas de se fazer o driver padrao para o ARM - como um modulo a ser carregado ou já compilado no kernel. Dado que já estamos compilando o kernel deve ser bem mais fácil compilar o driver padrao no kernel. Verifique como se faz isso.

9 -> conseguiram fazer a segunda parte inserindo o driver no kernel. Ao fazer a system call mknod no init.c tiveram de preparar o parametro usando makedev. Alteraram o Makefile em /driver para criar o driver no kernel (obj-y).

38.5 5 MINIX: porta paralela.

Em uma experiência de laboratório trata do driver da porta paralela: http://www.pcs.usp.br/~jkinoshi/2007/2031e9.doc Através dessa experiência podíamos escrever caracteres no display da ALFACOM. Vamos criar /dev/pp e associar um driver do minix, baseado em driver padrão adaptado para o minix a partir de http://www.pcs.usp.br/~jkinoshi/2005/Exp8_revisada_13_08_04.doc que faça: echo "AB" > /dev/pp faz o caracter hexa "AB" ser colocado nos pinos da paralela. Já fizemos trabalhos com essa idéia. Use relatório antigos apenas como base apenas para adaptar ao minix novo. Dependendo da maquina virtual, voce terah que fazer uma adaptcao (talvez um script monitorando um arquivo onde a maquina virtual coloca a saida da impressora) para observar a saida da porta paralela.

Obs: Trate o valor do caracter hexadecimal para colocar nos pinos da impressora. Isto é: "AB" deve significar que o binário 0b10101011 será enviado para a paralela.

9 -> funcionou bem; geraram o arquivo de saida no vmware com os caracteres que iam para a impressora; sinalizaram que o caracter estava sendo impresso através do strobe.

38.6 6 MINIX: Driver de teclado

O objetivo é estudar o driver de teclado e como ele se comunica com o restante do kernel do minix. Para isso responda:

  • quais sao as mensagens que o driver de teclado trata?
  • como o driver de teclado lida com a interrupcao de teclado (recebe uma mensagem quando ocorre uma interrupcao - explique como a mensagem é gerada e como é tratada)?
  • como o driver notifica o microkernel de que deverá receber uma mensagem a cada interrupcao de teclado?
  • como o driver repassa o código teclado para cima? Qual é o processo que le dados do teclado?

Faca uma alteracao no minix de forma a imprimir mensagens toda vez que o driver do teclado receber uma mensagem e toda vez que o driver enviar uma mensagem. Imprima qual é o processo com que a mensagem é trocada (enviada ou recebida). Com base nisso, coloque no relatorio como voces imaginam que funciona o getch() no minix.

7.8 -> colocaram prints mostrando que a rotina de interrupcao do driver do teclado era ativada; por exemplo ao pressionar "w" e ao liberar "w". Faltou relacionar alguma variante de getch (fgetc, fgets, getc, getchar, gets ou ungetc) com o driver do teclado.

38.7 7 MINIX: Levante as mensagens trocadas entre o FS e o driver do disco, desde a inicializacao, durante a leitura de um determiado arquivo.

Escolha um arquivo pequeno e bem simples. Você pode se basear no trabalho do grupo do Pedro, Wilson, Hélio ( http://www.pcs.usp.br/~jkinoshi/2008/projs/r5-pedrodaquino.zip) para levantar as mensagens trocadas entre FS e driver. Como o FS mapeia um arquivo no disco? Certifique-se de observar as mensagens que o FS (VFS) envia e recebe do driver e as mensagens que o driver envia e recebe do FS. O trabalho de 2008 usou um kernel extremamente diferente do kernel atual. Tomem cuidado para imprimir todas as mensagens correspondentes ao trabalho de 2008 (mostrando as mensagens trocadas entre o FS/VFS e o driver). Através desse trabalho vamos entender melhor como o driver se comunica com o resto do sistema operacional. Obs: Nao esqueca de monitorar a comunicacao com o driver do HD.

8 -> apresentaram as mensagens trocadas entre o driver e o FS no minix 3.1.2, o mesmo usado no relatorio.

38.8 8 MINIX: driver padrão.

A experiência 8 do lab. de microprocessadores: http://www.pcs.usp.br/~jkinoshi/2005/Exp8_revisada_13_08_04.doc tem como objetivo apresentar o que é um driver em linux. Em linux, um driver é um conjunto de rotinas que implentam funções padronizadas como "read" e "write". No caso do minix, um driver é um processo que responde a mensagens padronizadas. Crie um driver muito simples em minix que apenas imprime mensagens quando recebe mensagens padronizadas de outro processo. O driver pode ser associado a /dev/teste. Declare /dev/teste associando um major e minor number e o código do processo associado ao driver. Use "service" para rodar o driver. Gere um relatório sobre isso. As mensagens que o driver deve responder são as mesmas que o driver da impressora respondem, ou seja:

*    m_type      TTY_LINE   PROC_NR    COUNT    ADDRESS
* |-------------+---------+---------+---------+---------|
* | DEV_OPEN    |         |         |         |         |
* |-------------+---------+---------+---------+---------|
* | DEV_CLOSE   |         | proc nr |         |         |
* -------------------------------------------------------
* | HARD_INT    |         |         |         |         |
* |-------------+---------+---------+---------+---------|
* | SYS_EVENT   |         |         |         |         |
* |-------------+---------+---------+---------+---------|
* | DEV_WRITE   |minor dev| proc nr |  count  | buf ptr |
* |-------------+---------+---------+---------+---------|
* | CANCEL      |minor dev| proc nr |         |         |
* -------------------------------------------------------

Envie mensagens a /dev/teste como em:

echo "lixo" >  /dev/teste

e veja a mensagem que é impressa pelo seu driver. Faça o driver imprimir a string que recebeu ("lixo"). Em 2008, tivemos a seguinte resposta para o problema acima: http://www.pcs.usp.br/~jkinoshi/2008/projs/r3-pedrodaquino-Relatorio3.pdf. Vamos chamar esse driver de driver-padrão e foi feito para uma versão antiga do minix. Refaça o driver teste para o minix atual. Dado que esse trabalho não é complexo, por favor use de fato o minix atual e nao versoes antigas.

8 -> adaptaram sem dificuldades ao minix 3.2.1. Para o proximo ano, revisar este exercicio.

39 Fase 4

39.1 1. LINUX DLL

Crie uma funcao que apenas soma dois numeros quando chamada e coloque essa funcao numa Dynamically Linked "Shared Object" Libraries: (.so). Crie dois processos que utilizam essa mesma funcao. Descubra uma ferramenta no linux que permite visualizar quais sao as DLLs carregadas no linux. Ative os dois processos e observe se a DLL está carregada. Voce pode rodar cada programa em uma shell diferente. Descubra em que parte da memória foi carregada a DLL. Esses enderecos de memoria onde a DLL foi carregada sao os mesmos para os dois processos que compartilham a DLL? Agora altere a funcao para que ela tenha um estado interno; ou seja, ao inves de somar dois numeros; faca com que a funcao apenas incremente alguma variavel interna a ela. Rode os dois processos fazendo com que um numero seja incrementado a cada "enter" do usuário. Isso funciona? É possivel que a DLL guarde valores proprios? Talvez não seja possível, procure comprovar isso. Observe que existem dois tipos de bibliotecas : dinamicas e carregáveis (as dinamicas precisam do comando ldd para carregar primeiro a biblioteca e depois executar o codigo). As loadble verificam se estah na memoria, se não estiver jah sai carregando. Experimente usar os dois tipos de biblioteca. Experimente usar DLL no linux/arm no qemu. Se der problemas, anexe o problema no relatorio com print screen do qemu.

7 -> tentaram (passando as mas nao conseguiram roda no qemu,

39.2 2. LINUX/ARM - memória compartilhada.

Em um linux normal (ex: ubuntu), crie uma area de memoria compartilhada por dois processos diferentes no linux e transfira dados usando essa área de memória. O endereco virtual onde estah essa area compartilhada eh o mesmo para os dois processos? Estude como voce pode verificar isso no linux. Usando ferramentas do linux, visualize essa área de memória compartilhada. Faca testes para verificar qual o maximo de área de memória possível compartilhada entre ambos os processos. No Linux/Versatile faca com que o init crie dois processos com área de memória compartilhada. Provavelmente voce usará a system call shmget. Coloque um breakpoint na entrada dessa system call, bem como em outras posicoes. Retire uns printscreens do bt (backtrace); isto é, para descobrir que funçoes do kernel sao chamadas para executar essa system call. Busque referencias na internet e livros para explicar como o kernel do linux faz a memória compartilhada.

0 Gabriel A. -> sem apresentacao. 7 Thales, Vinicius -> ao inves de usar o shmget eh melhor usar o mmap. Nao rodaram no arm/qemu.

39.3 3. LINUX slab/slub allocator

Procure na internet e livros sobre o alocador slab/slub; uma referência é: http://www.secretmango.com/jimb/Whitepapers/slabs/slab.html Entenda e explique no relatório para que serve esse alocador, como a memória é alocada e desalocada para uso do kernel. Quando um arquivo é aberto, o kernel aloca memória para o seu inode (uma estrutura de dados contendo ponteiros para blocos, data da criação, permissões, etc.). Crie um programa bem simples (o correspondente ao init) para rodar no Linux/Versatile para observarmos como isso funciona. O programa deve abrir um arquivo, escrever algo nesse arquivo e fechar o arquivo. Quando o arquivo é aberto, o kernel aloca memória para o inode. Quando o arquivo é fechado, a área para o inode deve ser desalocada. Usando o gdb rode até que a system call execve ative este programa (para garantir que as estruturas do kernel já estão prontas). Coloque breakpoints quando a área de memória para o inode é criada e liberada. Coloque os printscreens da tela no relatório. Apresente ao vivo para a classe. Rode no linux/arm no qemu.

8 -> colocaram os breakpoint no qmeu/arm. QUando ocorria o open pela primeira vez, memoria do kernel era alocada, quando se abria para ler os dados, a memoria jah estava alocada e a reutilizava.

39.4 4 linux - page fault.

Existem formas de se ver processos gerando page faults no linux. Exemplo: http://www.ewhathow.com/2013/09/how-to-identify-page-faults-on-linux/ Crie um programa em C que gere muitas page faults em um linux normal (idéia: que esteja continuamente alocando muito memória para si). Monitore esse programa para observar se de fato tem gerado muitas page faults. No linux/arm/qemu coloque o mesmo programa para rodar como init. Coloque um breakpoint no tratamento da page fault. Veja como uma pagina é colocada na tabela de páginas, procure entender o código e explique. A tabela de páginas depende da MMU do ARM. Por isso, a parte do kernel que lida com a MMU tem que estar em assembly. Localize e apresente isso no kernel do linux.

9 -> observaram minor faults. Seria interessante analisar melhor a struct page.

39.5 5 MINIX alocacao e desalocacao de memória

Mostrar através de um log como a memória foi alocada e desalocada a processos. Toda vez que um processo executar um fork, exec, exit afeta a alocação de memória e isso é registrado no log (em um deterinado arquivo). No log contém informações como: fork - processo /usr/bin/init + segmento 0x30 - 5 clicks. exec - processo /usr/bin/firefox + segmento 0x40 - 7 clicks. exit - processo /usr/bin/firefox - segmento 0x40 - 7 clicks.

onde:

  • : significa que memória está sendo alocada ao processo da posição 0x00230 até 0x00340
  • : significa que memória está sendo desalocada e devolvida para a área livre.

dica: http://www.pcs.usp.br/~jkinoshi/2007/r4-1.pdf

Adicione ao log a informação de qual tipo de segmento (código ou dados) está sendo alocado ou desalocado. A resposta dada pela turma (com uma versao antiga do minix; e portanto atualize para o minix novo) está em: resp: http://www.pcs.usp.br/~jkinoshi/2008/projs/r4_brunogrisi.zip Faça com que a informação sobre o tipo de segmento (código/dado) esteja na mesma linha onde está "fork", "exec", etc.

Faça um programa que fique em loop executando o fork e veja o que ocorre no log. O processo deverá fazer algo como: while (1) { fork(); } Esse tipo de processo vai travar o sistema porque vai consumir toda a memória; ou vai acabar com todas as entradas na tabela de processos. O que acontece no minix? Crie uma forma de monitorar o número de processos que rodam na máquina. Tire printscreens da tela enquanto o processo que gera processos roda.

9 -> traces no minix com memoria virtual.

39.6 6 MINIX precisamemoria.c

Quando o minix faz exec ele deve desalocar a memoria da imagem do processo pai e alocar memoria (dados, código, pilha) referente ao codigo executavel, como ele faz isso? Localize isso no código do minix; mas basicamente ele deve ler o arquivo executável e retirar essa informacao. Localize no código do minix onde isso ocorre. Com base nesse código crie um programa no minix que tem como entrada um arquivo executável do minix (vc. pode criar um arquivo executável qualquer) e mostre o quanto o programa precisa de área de memória (dados, codigo/texto, pilha). Exemplo: precisamemoria arquivoexecutavel retorna o entrypoint e o quanto precisa de área de dados, código e pilha. Uma forma de resolver o problema é criar uma system call que colhe esses dados do PM. Entretanto, deve ser possível realizar a mesma coisa usando system calls normais (sem criar nenhuma sytem call para o minix), de forma a ler o código do arquivo exectável e com base no formato do arquivo, extrair essas informações. Para isso é necessário estudar o código do minix (quase que replicando código do PM) no precisamemoria.c. Escreva o código de precisamemoria.c e apresente para a classe ao vivo. Retire printscreens da máquina virtual e anexe no relatório. Modifique o exec no PM para mostrar como ficam os enderecos virtuais e fisicos no minix.

7 -> faltou comentar sobre a relacao entre os enderecos virtuais e fisicos

39.7 7 MINIX invasao de memoria / usar bochs

Como o minix protege a área do kernel? Se algum processo tentar invadir a área do kernel ele é realmente barrado? Crie um processo que tenta invadir uma área a que nao tem acesso. Uma forma de fazer isso é criar um ponteiro que varre a memória, lendo e escrevendo dados. Ao fazer isso no minix que erro você observa? Localize o tratamento desse erro no código fonte do minix. Apresente uma mensagem diferente quando ocorrer esse erro. Qual a participacao do pentium nessa excessão? Como o pentium é informado da área de memória do processo? Localize isso no código do minix. Rode esse programa no bochs para observar a interrupcao de invasao de memória. Relacione com o sinal SIGSEV. Retire printscreens e anexe no relatório. Observem que o limite de memoria para o processo já é definido ao se programar a LDT.

9: Tiago, Ivan; 0: Filipe Carvalho -> ao varrer toda a memoria o processo em um minix sem memoria virtual gerava o SIGSEV. Existem algumas causa para SIGSEV em uma tabela no minix.

39.8 8 MINIX - estouro de pilha.

Estouro de pilha (stack overflow): monitorar quando ocorre estouro de pilha. Você pode criar uma rotina recursiva que chama ela mesma indefinidamente no minix - sendo que ela deve passar como parametro i+1 e imprimir esse valor; de forma que podemos identificar o numero maximo de chamadas recursivas que foi possivel antes de se ter o estouro de pilha. Rode o minix no bochs e intercepte a excessao de estouro de pilha. Coloque o printscreen no relatório. Altere a área de memória RAM da máquina virtual onde roda o minix; verifique se o número máximo de chamadas recursivas varia. Localize no código do minix, qual o tamanho máximo que uma pilha de processo pode ter. A equipe do ano passado usou o minix2 pois tiveram problemas no minix3 que usa memoria virtual e portanto demorava muito (o processo tinha muita memoria) para dar o estouro de pilha. Tentem usar o proprio minix3. Para agilizar o estouro de pilha basta empilhar mais coisas. Por exemplo, a cada chamada recursiva, alocar memoria usando malloc e colocar essa memoria alocada na pilha (uma ideia eh colocar um vetor como parametro de uma funcao e passah-lo como dado e nao como endereco). No minix 3.1.0 é possível observar a excessao de stack overflow - int 12 enquanto que no minix 3.1.5 já não foi possível por trabalhar com memória virtual.

8 -> observaram o estouro de pilha em um minix sem memoria virtual.

Footnotes:

1 6

2

2 9

3

3 13

4

4 16

5

5 20 F1

6

6 23 F1

7

7 27

8

8 30

9 3

10

10 6

11

11 10 F2

12

12 13 F2 17 P1 -> copa 20 feriado

14

13 -P1 27

14 24

13

15 4 8 -> Jogo BrasilxAlemanha

17

16 18

19

17 11 F3

18

18 15 F3

16

19 22

20

20 25

21

21 29

22 1

23

23 5 F4

24

24 8 F4

25

25 12

26

26 15

29

27 DEFINITION NOT FOUND: 27

28 DEFINITION NOT FOUND: 28

29 DEFINITION NOT FOUND: 30

30 22 P2

Date: 2014-08-19 11:23:21 BRT

Author: Jorge Kinoshita

Org version 7.8.02 with Emacs version 23

Validate XHTML 1.0