SlideShare uma empresa Scribd logo
Um Carregador Rápido para
   TK-2000 e Apple II
que virou Sistema Operacional




                        http://tk2k.lisias.net/CB2k
Premissa

    i.Restaurar um obscuro
computador doméstico de quase 30
          anos de idade
ii.Escrever um sistema operacional
             pro dito cujo
             iii.?????
          iv.PROFIT! :-)
@Lisias
|
    http://lisias.net
                   3/89
@Lisias
http://retro.lisias.net
                     4/89
As Vítimas
●   Scene Retrô brasileira de Apple II e Compatíveis (ou quase)
    –   Intensa movimentação nos últimos 18 meses
●   Inúmeras novidades
    –   engenharia reversa do Cartucho Controlador de Discos do TK-2000
    –   Tomato Board




                                                                     5/89
O Motivo
●   Acesso à Hardware equivalente, mais barato e
    abundante, da linha Apple
●   Mas os jogos (e parte significativa dos demais
    softwares) ainda estavam em formato Cassete
●   Soluções (software) prontas, importadas do Apple II,
    eram
    –   Muito complexas para portar
        ●   ProntoDOS, DiversiDOS, ProDOS
             –   todos ótimos, mas sistemas operacionais completos!
    –   Overkill
    –   Over memory :-)
                                                                      6/89
Enquanto isto...
●   “lá fora” (news:comp.sys.apple)
    –   CompatiBoot original (Raven/C700 Club)
        ●   Rápida
        ●   Prática
        ●   Mas não adequada
             –   Capenga no TK-2000
             –   One shot only
             –   Altas gambiarras pra convencer a dita cuja a fazer o que
                 precisávamos
             –   Efeitos colaterais diversos e inesperados



                                                                            7/89
Indo direto ao ponto
●   Benchmark : TK-DOS 3.3
    –   Tempo entre ligar a máquina (com um disquete com boot no drive) e o Prompt do
        Applesoft:
        ●   31 segs.
    –   Tempo para carregar uma tela gráfica HGR:
        ●   10 segs
    –   Espaço livre na RAM depois de carregado:
        ●   ~ 24 Kbytes.
             –   Não, não é Mega. É Kilo mesmo! :-)
●   Demais S.O.s
    –   Overkill
●   Outras Soluções
    –   Não são práticos nem flexíveis
    –   São perdulários
    –   Não funcionam, ou o fazem porcamente, no TK-2000

                                                                                        8/89
O Crime


      “Hummmm...”
        Groo faz o que...

“Eu acho que faço melhor!”


                             9/89
Advertência
O uso indiscriminado e                   Podem causar danos
concomitante de                          irreversíveis à/ao
–   Linguagem Assembler
                                         –   Sanidade mental
–   Rotinas de Tempo Real
–   Computadores Vintage
                                         –   Relacionamentos amorosos
–   Conceitos (nem tão assim)            –   Vida social
    avançados de Arquitetura de
    Computadores e Sistemas
                                         –   Convivência familiar
    Operacionais                         –   Organização domiciliar
–   Café, cerveja, pizzas, lanches e     –   Paz condominial
    snacks
–   EL&P, Rick Wakeman, Jean Michel
                                         –   Perímetro da sua cintura :-)
    Jarre, Vangelis, Daft Punk e
    Kraftwerk

                  Depois não digam que a culpa é minha!! :-)
                                                                            10/89
Planejando a ação
●   A CB2k deve:
    –   Carregar arquivos com a maior eficiência possível
    –   Permitir carregar programas que querem ocupar o
        espaço onde normalmente ficaria o DOS
    –   Ser prática para criar/atualizar disquetes
    –   Oferecer uma API consistente para programação
    –   Fornecer exemplos de como desenvolver
        aplicações


                                                        11/89
Planejando a ação
●   A CB2k não pode deixar de:
    –   Ser extensível e portável
    –   Ficar pronta em umas 4 ou 5 semanas.
        ●   Férias acabam!
    –   Ser útil e agregar valor
●   Demais funcionalidades (rede, ambiente
    gráfico, co-processamento, etc.)
    –   são totalmente fora de escopo
        ●   Hoje! ;-)

                                               12/89
It's coding time!




    ●   BELEZA!!
        Já sei o que quero fazer, agora é
        só ligar a máquina e... Oh, wait...
        –   Como se programa nesta joça?

                                           13/89
First Things First




                           code
       “One does not simply walk into Mordor!”
                  Boromir, The Fellowship of the Ring

                                                        14/89
Programação de Baixo Nível
                    Não tem este nome à toa...
●   O legendário 6502
●   Arquitetura dos Computadores
    –   Apple II+
    –   MPF-II/TK-2000
    –   Semelhanças e diferenças entre as máquinas target
●   Disquetes: um problema em tempo real
    –   A Shugart
    –   A Disk II do Woz
    –   Persistência de dados em mídias magnéticas


                                                            15/89
O 6502
●   Registradores
●   Instruções
●   Clock Cycle Time
    –   Cycle para os íntimos
        ●   T States
    –   A únidade básica de tempo do processador
    –   A únidade básica de ansiedade do programador
●   Os diferentes Endereçamentos à memória
    –   O segredo do sucesso!
    –   A Salvação da Pátria!
●   O primeiro RISC?
●   Sucessores
    –   65C02
    –   65816

                                                       16/89
$0000     Zero Page
$0100       Stack
                                                         O 6502
                                    A
                         7 6 5 4 3 2 1 0

                                    X                          Y
                         7 6 5 4 3 2 1 0                 7 6 5 4 3 2 1 0

                                    S                          P
                         7 6 5 4 3 2 1 0                 N V 1 B D I Z C

                                                   PC
                         15 14 13 12 11 10 9 8           7 6 5 4 3 2 1 0


                                ●   Load / Store                ●   Trasnfer                   ●   ROR, ROL, SHL, SHR
                                        –   Pero no mucho!          –   AX, XA                     –   A
        Free Addresses                                              –   AY, YA                             #imm
                                ●   LD / ST                                                            ●


                                                                    –   XS, SX                         ●   Abs
                                        –   [A,X,Y] #imm        ●   Branchs                            ●   Abs,X
                                        –   A abs,X                 –   EQ / NE (Zero Flag)            ●   Abs,Y
                                        –   A abs,Y                     MI / PO (Minus Flag)
                                                                    –                                  ●   (Indi,X)
                                        –   A (indi,X)              –   CS, CR (Carry)                 ●   (Ind),Y
                                        –   A (indi),Y              –   VS, VC (Overflow)      ●   ADC, SBC
                                ●   JMP                         ●   P (Status)                     –   A
                                        –   JMP abs                 –   SEC, CLC                       ●   #imm
                                                                    –   Etc                                Abs
                                        –   JMP (indi)                                                 ●

                                                                ●   INC / DEC                          ●   Abs,X
                                ●   JSR / RTS
                                                                    –   A, X, Y                        ●
                                                                                                           Abs,Y
                                ●   Stack                           –   Abs                            ●   (Indi,X)
                                        –   PHA / PLA               –   Abs,X                              (Ind),Y
$FF00                                                                                                  ●


            ROM                         –   PHP / PLP               –   Abs,Y                      Muito Mais!          17/89
$FFFF                                                                                          ●
O Apple II+
●   Hardware
    –   Memory Mapped I/O
    –   Modos de vídeo
    –   Mapa da RAM
●   ROM
    –   Principais entry-points
    –   Uso da Página Zero
●   Console I/O
    –   Teclado
    –   Caracteres


                                         18/89
$0000      Zero Page


                                            O Apple II+
$0100        Stack
$0200      I/O Buffer
            Free RAM
$0300     System Pointers

$0400
         TEXT/GR Page 1                                           ●   Buffer de I/O
$0800                                                                 – Usado pelo sistema (e pelo DOS) para
        TEXT/GR Page 2                                                  entrada e saída de dados
                                                                         ● Teclado
$1000
           Free RAM
                                                                         ● Disco

$2000                                                                    ● Etc.

            HGR 1                                                 ●   2 Páginas de texto
$4000
                                                                      – 1 delas pode ser usada para programação
            HGR 2
                                                                  ●   2 Páginas de gráficos
                                                                      – Ambas podem ser usadas para programação
$6000                                                              ● A ROM pode ser “sombreada” por um

                                            L.C. P0                  mecanismo chamado “Language Card”
                                                                  L.C. P1

           Free RAM                     Saturn Bank 7
                                                                      – A LC é dividida em 3 bancos
                                            Main                         ● 1 Principal


                                                                         ● 2 Secundários, que dividem o mesmo


$C000    Mem Map I/O              L.C. P0               L.C. P1            endereço
$C100                                                                 – A LC pode ser expandida através de bancos
         Expansion Slot
             ROM               Saturn Bank 1                            de memória
                                    Main
$D000                                                                    ● Saturn 128Kb.
                               L.C. P0            L.C. P1

             ROM            Language Card
                                Main                                                                              19/89
$FFFF
O Apple II+
●   Teclado “ASCII”
    –   Um uC faz o serviço sujo para você
    –   Curto e Grosso
        ●   E simples de ler!
    –   Mas um saco para os jogos
        ●   Control e Shift não são dectáveis sem mods
        ●   Combinações de teclas (que não envolvem as
            modificadoras acima) são impossíveis de
            serem detectadas
             –   A segunda sobrescreve a primeira, e ponto final
●   Caracteres
    –   ASCII
        ●   Alfanuméricos
        ●   Suporte à Minúsculas opcional (!!!)
    –   Inverso e Flash

                                                                   20/89
O MicroProfessor II
                            e seu primo brasileiro

                            TK-2000
●   Hardware
    –   Memory Mapped I/O
    –   Modos de vídeo
    –   Mapa da RAM
●   ROM
    –   Principais entry-points
    –   Uso da Página Zero
●   Console I/O
    –   Teclado
    –   Caracteres
                                                     21/89
$0000
$0100
            Zero Page
               Stack
                                      O MicroProfessor II
                                               e seu primo brasileiro
$0200        I/O Buffer


                                              TK-2000
              Free RAM
$0300       System Pointers
$0400        Free RAM
                 &
        Some System Variables                          ●    2 páginas de gráficos
$0800
                                                            –   Como não há modo texto, uma delas
            Free RAM                                            obrigatoriamente precisa estar em uso pelo
                                                                sistema
$2000                                                       –   O TK-DOS ocupa quase toda a página 2 :-(
              HGR 1
                                                       ●    ROM pode ser programaticamente
$4000         HGR 1                                         substituída pelas Extra RAM
                                                       ●    Bloco I : 15.75 Kbytes
            Free RAM                                   ●    Bloco II : 4 bancos de 16Kbytes
                                                            –   1 banco de 8 kbytes
$A000                                                       – 2 sub-bancos de        4 kbytes
                                                   Bloco II/D P0     Bloco II/D P1
              HGR 2                                         – Saturn 64Kb! :-)
                                                    Extra RAM ●   O meu tem 128Kb! :-)
$C000     Mem Map I/O                               Bloco II/D
$C100
                                                       ●    Apenas um Bloco pode estar ativo num
                                                            momento
$D000                                       Bloco II/A P0         Bloco II/A P1
               ROM
                                Extra RAM                   –   Os bancos do Bloco II precisam escolher qual
                                 Bloco I
                                             Extra RAM          página de 4 kbytes deve estar ativa
                                             Bloco II/A
$FFFF                                                                                                          22/89
O MicroProfessor II
                                           e seu primo brasileiro

                                           TK-2000
●   Teclado com a Matriz exposta
    – Sem um MicroControlador pra fazer o serviço pesado
    – Vantagens
       ● Acesso individual (e múltiplo!) ao estado de cada tecla


          – permite algumas combinações interessantes para jogos
    – Desvantagens
       ● Gasto de processamento para ler o teclado


       ● Principal e maior motivo da “má fama” do TK-2000


          – A rotina do fabricante, oferecida no Manual Técnico
            como alternativa à leitura do teclado do Apple II era
            porca – simples assim
          – Um dos principais artefatos secundários do projeto:
             ●
               Uma rotina rápida de leitura de teclado! :-)
    – Caracteres
       ● ASCII


          – Alfanuméricos
          – Sem suporte às minúsculas (!!!)
       ● Semigráficos                                               Fonte: pág.21 TK2000/II Manual Técnico
                                                                                Microdigital Eletrônica LTDA


                                                                                                               23/89
$0000
$0100
          Zero Page
            Stack
                                 O Apple //e & //c                                             Zero Page
                                                                                                 Stack
$0200
$0300
          I/O Buffer
           Free RAM
         System Pointers
                                     (porque todo castigo...)                                  I/O Buffer
                                                                                                Free RAM
                                                                                              System Pointers
$0400      TEXT/GR                                                                            80TEXT/DGR
            Page 1                                                                               Page 1

$0800
                           ●   Revisões
           TEXT/GR                                                                            80TEXT/ DGR
            Page 2              –   Apple // Extended                                            Page 2

$1000
          Free RAM                  ●    6502                                                  Free RAM

$2000                           –   Apple //c, //e Enhanced e Platinum
           HGR 1                                                                               DHGR 1
                                    ●
                                         65C02
$4000                               ●    “Mouse Chars”
           HGR 2                    ●    DTEXT (80 COLs), DGR & DHGR                           DHGR 2


$6000
                           ●   128Kb
                                –   Mas num esquema totalmente diferente
          Free RAM                                                                             Free RAM
                                –   Descreve isto, Lisias!
                                    ●    Nah... Deixa quieto! =D
$C000                                                     Mem Map I/O
$C100                                           Expansion Slot         Extension
                                                    ROM                  ROM
$D000      L.C. P0             L.C. P1                                             L.C. P1      L.C. P0

        Language Card                                            ROM                         Language Card
            Main                                                                                 Main
$FFFF                                                                                                           24/89
            Main                                                                               AUX
Resumo da Ópera
●   As diferenças da ROM enchem o saco
    –   Oferecer uma camada de “abstração” da ROM seria bacana, mas
        exigiria mais memória
        ●   Mas não sai de graça
●   As diferenças na memória principal são facilmente gerenciáveis
    –   Mas o mesmo não acontece com os bancos de memória estendida
        ●   E lá se vão funcionalidades pela janela
●   O 65C02 têm instruções extras que seriam (muito) úteis
    –   Maior densidade de código e mais “semântica” por ciclo de clock
        ●   TXY (1 byte, 2 Ciclos)
             –   PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!)
             –   STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma posição da ZP)
             –   STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos)
    –   Mas alienaria o TK-2000 e o Apple II+
                                                                                            25/89
Mas não é só isso!




                     26/89
Mídias Magnéticas
●   Revoluções Por Minuto
    Mas sem as louras geladas... =/
    –   Densidade Magnética
        ●   Coerção
        ●   Histeresys
    –   Velocidade Angular “constante” versus
        Velocidade Linear “constante”
        ●   (Constante, o escambau! O motor não é estável...)
    –   Largura de Banda
    –   Desgaste físico!
                                                                27/89
Discos Magnéticos
●   As trilhas não têm todas o mesmo tamanho físico.
    –   Perímetro é função do raio!
●   Mas tem o mesmo tamanho lógico...
    –   Velocidade angular constante
        ●   Densidade dos dados varia em função da trilha
●   Pragmatismo
    –   A Shugart ajustou o mecanismo para ser confiável na trilha
        mais interna, e desperdiçou densidade nas mais externas
    –   Drives mais sofisticados (e caros) variam a velocidade do
        motor em função da trilha
        ●   aproveitar melhor a densidade da mídia

                                                                    28/89
Discos Magnéticos
●   Os dados são gravados (re)alinhando polaridade na
    superfície da camada de óxido de ferro
    –   Descobriu-se não ser eficiente usar uma polaridade para o bit 1,
        e outra para o bit 0
        ●   Mudança de polaridade na linha do tempo indica bit 1
        ●   Não mudança de polaridade na linha do tempo indica bit 0
●   Mas o motor não consegue fornecer uma velocidade
    constante ao nível do microsegundo
    –   Pequenas variações no motor “distorcem” o comprimento de um
        bit
    –   Dada uma distância longa o suficiente sem inversão de
        polaridade, o hardware não sabe mais quantos bits '0' foram
        lidos... 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ?
        ●   As inversões de fase, então, são usadas como “clock” para a leitura dos
            dados
                                                                                 29/89
Discos Magnéticos
●   Mas isto tudo foi problema da Shugart!
    –   E do Woz...
        ●   E do Langhton!
             –   Quem? :-)
●   Qual foi o meu problema?
    –   32 * 1 / 1.023 MHz
        ●   0,0000031280547409579667644183773216031 Segundos
        ●   É o tempo que se tem para ler um raw byte do disquete, salvar
            na memória e estar pronto para ler o próximo!
        ●   3196 a 12787 bytes lidos a cada piscar de olhos
             –   E eu só preciso perder UM para causar o infame I/O Error!


                                                                             30/89
Discos Magnéticos




1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ?
             32 T states
                                  31/89
Algoritmos de Tempo Real
●   Quediaboéisso?
    –   São algoritmos em que o tempo de resposta faz parte do
        resultado do processamento
        ●
            Não é o mesmo que “fazer rapidinho”
             –   “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo.
             –   “Entregar” antes do prazo é desperdício de processamento
●   E o Kiko? Kiko'eu tenho a ver com isto?
    –   Acessar disco é uma tarefa de tempo real
        ●
            Missão Crítica!
    –   Computadores modernos possui um micro controlador
        especializado para lidar com disco
        ●   O Apple II não.
             –   Welcome to hell...

                                                                                            32/89
Tá ficando complicado




                        33/89
Reavaliação
●   Riscos
    –   Gravar setores dá mais trabalho que ler
        ●   E eu nem tinha certeza de que iria conseguir ler...
    –   Não vou conseguir fazer tudo!
        ●   Muitas diferenças entre cada target, praticamente um
            software diferente pra cada um
●   Prioridades
    –   BOOT eficiente
    –   Carga rápida de Binários
    –   Serviços (mínimos) de diretório
    –   (nice) API
        ●   Sólida
    –   Abrir mão da memória extra, e focar na principal
        ●   E economizar onde der
                                                                   34/89
Reação
●   Começar prototipando as rotinas básicas de disco
    –   Se eu não estabilizar a rotina de leitura de setores, o resto
        não serve de nada
    –   Um terço do esforço total do projeto foi gasto só nelas
●   Redução de escopo
    –   Serviços de “Console I/O” pelo Kernel :-|
    –   Cache de disco (em especial, do CATALOG) :-|
    –   Gravação de Dados ¬¬
    –   Gerenciamento da memória ¬¬
    –   Relocação em memória X-(
    –   Suporte à programas BASIC X-(
                                                                        35/89
Resolução
●   “Internalizar” algumas funções da ROM para o S.O.
    –   Não sem conseqüências... ¬¬
●   Delegar à aplicação gerenciar o resto do hardware
    –   O S.O. identifica para você a máquina em que está rodando
    –   “Bibliotecas” padrão no “User Space”
    –   E cada um que se vire!
●   BASIC.SYSTEM
    –   Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no
        User Space.
●   “Forkar” o Kernel para casos especiais
    –   Versões especializadas para cada arquitetura e/ou funcionalidade
        específica
    –   Gerência de Configuração to the rescue! :-)
                                                                           36/89
E o inesperado
                                 (porque todo castigo...)

●   O uso da Página Zero me mordeu o traseiro.
    –   Feio. :-(
    –   Quase assassinou o projeto no berço
         ●   Quando a R*TS não matava o resto da máquina, o resto da máquina
             matava a R*TS
         ●   Cerca de 20% do esforço de desenvolvimento foi gasto mapeando e
             documentando, corretamente, o uso da Z.P.
              –   No TK-2000 e no Apple II
              –   Um esforço com o qual eu não contava
    –   Não havia mais o que fazer exceto desistir ou pagar o pato e
        seguir adiante
         ●   5 dias de trabalho indo pelo ralo.
              –   E as férias, digo, o prazo acabando! =]
         ●   A única documentação formal do projeto.
                                                                           37/89
; Depends on rwts.def.
; Updates zp_profile.s
;                                             Apple II Zero Page Usage
;
;                                             Lo Nibble of Address
;     Hi
;     Nib 0      1     2      3       4    5      6     7    8     9   A    B    C     D     E     F
;      ----- ----- ------ ------ ----- ------ ----- ---- ---- ---- ---- ---- ----- ----- ----- -----
;      0 | A~    A~    A      A       A    A      -     -    -     -   A    A    A     AI    A     A
;      1 | A     A     A      A       A    A      A     A    A     A   A    A    A     A     -     M*
;      2 | M     M     M      M       M3   M      MA3   MA3 M3     M3  M3   M3   MA3   MA3   M3    MA3
;      3 | MA    M     MA     MA3     M    M3     M3B   M3B M3B M3B M~      M~   MA3~^ MA3~^ MA3~^ MA3~^
;      4 | M3~+^ M3~+^ M3~@^ M3~@^ M3~@^ M3~@     M3~   M3~ M3~ M3~ I3~ I3~ I3~        I3~   M~@# M@#
;      5 | MA    MA    MA     MA      MA*  MAI*   AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
;      6 | AI+   AI+   AI@    AI@     AI@  AI@    AI@# AI3 AI3 AI3 AI3 AI        AI    AI    AI    AI3
;      7 | AI3   AI    AI     AI3     AI3  AI     AI3   AI   AI    AI  AI   AI   AI    AI    AI    AI
;      8 | AI    AI    AI     AI      AI   AI     AI    AI@ AI@ AI     AI   AI   AI    AI    AI    AI
;      9 | AI    AI    AI     AI      AI   AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
;      A | AI    AI    AI     AI      AI   AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI3
;      B | AI3   AI    AI     AI      AI   AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
;      C | AI    AI    AI     AI      AI   AI     AI    AI   AI    AI  AI3 AI3 AI3     AI3   I#    I#
;      D | AI    AI    AI     AI      AI   AI     AI3   I!   AI3 AI3 AI     AI   AI    AI    AI3   AI
;      E | A     A     A      A       A    A      A     A    A     A   A    ?    -     -     -     -
;      F | A     A     A      A       A    A      A     A    A     A   -    -    -     -     Ik    AI
;
;
;     M = Used by Monitor; * used in early Apple IIe ROMs-- now free
;     A = Used by Applesoft BASIC
;     I = Used by Integer BASIC
;     3 = Used by DOS 3.3
;     ~ = Used by ProDOS ($40-$4E is saved before and restored after use)
;     B = Used by ProDOS BASIC.SYSTEM (also uses all Applesoft locations)
;     - = Free; not used
;
;     k = Used by TK-2000 / MPF-II
;
;     + = RWTS, Comunicação com "Cliente"
;     @ = RWTS, Conteúdo descartável.
;     ! = RWTS, Posição Chave: não pode ser mudada nem destruída!
;
;     ^ = CompatiBoot 2k, Comunicação com "Cliente"
;     # = CompatiBoot 2K, Conteúdo descartável.
;     ? = CompatiBoot 2K, Posição Chave: não pode ser mudada nem destruída!
;
;     --Bryan Dunphy, Michael J. Mahon, Rubywand, CompatiBoot 2k
                                                                                                           38/89
E quando tudo o mais falhar...




          “How many times do I have to tell you,
                 the right tool for the right job!”
                              Montgomery Scott (Scotty)
             Chief Engineer, NCC-1701-A USS Enterprise
                                                          39/89
Anatomia de um
   Disquete




                 40/89
Anatomia de um
                                                          Disquete
                                                     35 Trilhas
                          0         1         2                   …                           35
                                                                                                   Address Field
                        gapzão    gapzão    gapzão                                          gapzão
                                                                                                            14
                        Addr_0    Addr_0    Addr_0                3              2            Addr_0
                                                                                                   2                 2               2              3
                         gap       gap       gap               Prologo       Volume            gap
                                                                                                Track             Sector         ChkSum          Epilogo
                         Data      Data      Data            'D5 AA 96   '4 & 4 encoding   '4 &Data
                                                                                                4 encoding '4 & 4 encoding   '4 & 4 encoding   'DE AA EB
=4096 bytes (lógicos)




                         gap       gap       gap                                               gap
                        Addr_1    Addr_1    Addr_1                                            Addr_1
  ~48000 bits (raw)




                         gap       gap       gap                                               gap Data Field
                         Data      Data      Data                                              Data        349
                         gap       gap       gap                 3                             gap
                                                                                                 342                               1                3
                        Addr_2    Addr_2    Addr_2            Prologo                         Addr_2
                                                                                                 Data                           ChkSum           Epilogo
                         gap       gap       gap            'D5 AA AD                          gap
                                                                                           6 & 2 encoding                         'XX          'DE AA EB
                         Data      Data      Data                                              Data
                         gap       gap       gap                                               gap
                        Addr_3    Addr_3    Addr_3                …         “gapzãp”          Addr_3“Self Sync bytes”             gap
                         gap       gap       gap                             48 a 100          gap                               5 a 60
                         Data      Data      Data                         'FF FF FF …          Data 1 1 1 1 1 1 1 0 0
                                                                                                   '1                          'FF FF FF
                         gap       gap       gap                                               gap
                        Addr_4    Addr_4    Addr_4                                            Addr_4
                         gap       gap       gap                                               gap
                         Data      Data      Data                                              Data
                         gap       gap       gap                                               gap


                          …         …         …                                                …


                        Addr_15   Addr_15   Addr_15                                         Addr_15
                          gap       gap       gap                                             gap
                         Data      Data      Data                                            Data


                                                                                                                                                41/89
Anatomia de um
                                  Disco DOS 3.3
   Disk                                                  Trilha
             0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
        0    0                                               1A 15 31 47 62 78 0 15 23 102 109 116 120
        1    8                                                0 16 32 48 63 79 1 16 24 103 110 117 121
        2    1                            1                   1 17 33 49 64 80 2 17 25 104 111 118 122
        3    9                                                2 18 34 50 65 81 3 18 26 105 112 119 1B
        4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
        5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
        6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
Setor




        7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
        8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
        9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
        10   5                                                9 25 41 57 72 88 10 95   99 106 113    60 126
        11 13                         6                      10 26 42 58 73 89 11 96   100 107 114   61 127
        12   6                                             4 11 27 43 59 74 90 12 97   101 108 115   62 127
        13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
        14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
        15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65

                                                                                                              42/89
Boot
●   Power On RESET
    –   RESET Vector
●   Autostart ROM (BOOT 0)
    –   Busca por uma placa DISK II na ROM de expansão
●   BOOT 1 (second stage)
    –   Trilha 0, Setor 0
    –   L-Boot1
●   BOOT 2 (third stage)
    –   Sistema Operacional
        Ou outro payload qualquer...


                                                         43/89
A L-Boot1
●   Fornece a melhor performance possível para carga
    sequêncial
    –   Multi trilha
●   Serviços independentes de “plataforma”
    –   Impressão em tela
    –   Carga de setores
    –   Descompressão de dados
●   Também foi usada com sucesso:
    –   Boot do TK-DOS 3.3
    –   Boot do Apple DOS 3.3
    –   Jogos stand-alone
                                                       44/89
Finalmente: CB2k
●   R*TS
●   Kernel
    –   Serviços de Diretório
    –   Serviços “Raw Files”
    –   Serviços Binary Files
    –   Serviços de House Keeping




                                    45/89
O Inferno das Entry-Points
00B3D5 2                KERNEL__ADDR_START:
00B3D5 2                        ; Prevents accidental running
00B3D5 2 00                     BRK
00B3D6 2 1E                     .byte    __WARM_BOOT - __KERNEL_SERVICES_TABLE
00B3D7 2
00B3D7 2                __KERNEL_SERVICES_TABLE:
00B3D7 2 F8 B3                  .word    __PANIC
00B3D9 2 59 B5                  .word    KERNEL_SYSTEM_IDENTIFICATION
00B3DB 2 F4 B8                  .word    KERNEL_FILE_LOAD
00B3DD 2 21 B9                  .word    KERNEL_FILE_RUN
00B3DF 2 61 B5                  .word    KERNEL_SESSION_FINISH
00B3E1 2 10 B6                  .word    KERNEL_CATALOG_ENTRY_SET
00B3E3 2 33 B6                  .word    KERNEL_CATALOG_ENTRY_QUERY
00B3E5 2 92 B6                  .word    KERNEL_CATALOG_ENTRY_GET
00B3E7 2 F7 B6                  .word    KERNEL_RAWFILE_SEEK
00B3E9 2 82 B7                  .word    KERNEL_RAWFILE_READ
00B3EB 2 23 B5                  .word    KERNEL_HANDLER_SET
00B3ED 2 9E B5                  .word    KERNEL_CONFIGURATION_SET
00B3EF 2 DB B5                  .word    KERNEL_CONFIGURATION_GET
00B3F1 2 F9 B4                  .word    KERNEL_SECTOR_READ
00B3F3 2 F5 B3                  .word    __WARM_BOOT
00B3F5 2                __KERNEL_SERVICES_TABLE_end:
00B3F5 2
00B3F5 2                __WARM_BOOT:
00B3F5 2 4C 5A BA               jmp      KERNEL__WARMBOOT
00B3F8 2
00B3F8 2                __PANIC:
00B3F8 2                        ; System is unstable. The next reset will reboot from the
same slot the CB2K was rebooted last time.
00B3F8 2 20 9D BA               jsr      KERNEL__HW_RESET_HANDLER_REBOOT_SET
00B3FB 2 A9 80                  lda      #KERNEL_ERR_PANIC
00B3FD 2 A6 EB                  ldx      KERNEL_SUPERVISOR__STACKPOINT                 46/89
O Supervisor
●   A instrução mágica
     –    BRK
KERNEL_SUPERVISOR:
          cli        ; Desativamos interrupções.
                     ; O Kernel não sabe ser interrompido, e a R*TS *NÃO PODE* ser interrompida!
                     ; A RTI abaixo restaurará o Status, e se a IRQ estava ativada, ela voltará a
estar.

.ifndef   LANGUAGE_CARD
          jsr       MON_RESTORE              ;   Pois é... A ROM do Apple IIe faz o favor de,
                                             ;   trabalho fodástico de resetar o estado da
                                             ;   anterior para permitir restauro!), tirar da
                                             ;   (o que eu não queria), e *não manter* o
                                             ;   virtualmente fodendo com o conceito de
                                             ;
                                             ;   TODO: Mover a CB2K para Language Card, escrever
.endif
          jsr        __SAVE_THE_WORLD

          ldx        KERNEL_SUPERVISOR__STACKPOINT ; O Supervisor *NÃO É* reentrante.
          bne        @PANIC

          lda        __REG_P
          and        #%00010000              ; Checa se o BRK STATUS está ativo
          beq        @PANIC                  ; Se não está, a máquina tá despirocada e o PC caiu
                                             ; aqui por acidente!
                                                                                                   47/89
A (nice) API
.define VERSION_MAJOR 1
.define VERSION_MINOR 1
.define VERSION_RELEASE   "2012.0901"

.macro SYS syscall
    BRK
    .byte   syscall
.endmacro
    ; This two entries are garanteed to never change or be renamed!
    CB2K_SYSTEM_PANIC             := 0
    CB2K_SYSTEM_IDENTIFICATION    := 2 + CB2K_SYSTEM_PANIC

    ; The following entries can, but is unlikely to, change on MAJOR versions.
    CB2K_FILE_LOAD                := 2 + CB2K_SYSTEM_IDENTIFICATION
    CB2K_FILE_RUN                 := 2 + CB2K_FILE_LOAD
    CB2K_FINISH                   := 2 + CB2K_FILE_RUN
    CB2K_FILE_SET                 := 2 + CB2K_FINISH
    CB2K_FILE_QUERY               := 2 + CB2K_FILE_SET
    CB2K_FILE_GET                 := 2 + CB2K_FILE_QUERY
    CB2K_RAWFILE_SEEK             := 2 + CB2K_FILE_GET
    CB2K_RAWFILE_READ             := 2 + CB2K_RAWFILE_SEEK
    CB2K_HANDLER_SET              := 2 + CB2K_RAWFILE_READ
    CB2K_CONFIGURATION_SET        := 2 + CB2K_HANDLER_SET
    CB2K_CONFIGURATION_GET        := 2 + CB2K_CONFIGURATION_SET
    CB2K_SECTOR_READ              := 2 + CB2K_CONFIGURATION_GET

    ; The following entries (if any) can be added on MINOR versions
    ; CB2K_FUTURE_EXPANSION       := 2 + CB2K_SECTOR_READ
                                                                            48/89
Resultados
●   Footprint 3.75Kbytes
    –   Kernel, R*TS, Supervisor, buffers, tudo!
    –   E os buffers ainda são configuráveis (on the fly)
●   Melhor performance
    –   6 a 7 Kbytes/s – próximo do limite operacional do dispositivo
●   Usa discos formatados pelo Apple DOS 3.3
    –   Até o FID pode ser usado para povoar seus discos
        ●   Mas eu recomendo o CiderPress. :-)
●   Aplicações
    –   Game Loaders
    –   Demos
    –   Outros
                                                                        49/89
Resultados
●   Benchmark TK-2000
    –   Tempo entre ligar a máquina (com o disquete já no drive) e o Prompt
        do Applesoft :
        ●   DOS: ~31 Segundos (!!!!)
        ●   CB2k: 6 segundos
        ●   DOS + LBoot1: 7 segundos (!!!!)
    –   Tempo para carregar uma tela HGR:
        ●   DOS: 10 segundos
        ●
            CB2k: 4 segundos
    –   Espaço livre na RAM (MEMTOP - $800):
        ●   DOS: $9600 - $800 = $8E00 = 35.5Kb
        ●
            CB2k: $B000 - $800 = $A800 = 42Kb
●   Mas convêm lembrar:
    –   A CB2k faz pouca coisa mais que carregar binários
                                                                         50/89
Por que o DOS é tão lento?

●   Os “raw sectors” (342 bytes físicos) são lidos
    para um buffer intermediário
●   Este buffer é então decodificado para os 256
    bytes de dados, em um buffer auxiliar
●   Estes dados são, finalmente, copiados para o
    buffer de I/O para leitura pelo programa
    BASIC ou para a memória destino, se binário
●   E o disco continua virando

                                                     51/89
DOS:
                                 Modus Operandi
   Disk                                                  Trilha
             0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
        0    0                                               1A 15 31 47 62 78 0 15 23 102 109 116 120
        1    8                                                0 16 32 48 63 79 1 16 24 103 110 117 121
        2    1                            1                   1 17 33 49 64 80 2 17 25 104 111 118 122
        3    9                                                2 18 34 50 65 81 3 18 26 105 112 119 1B
        4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
        5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
        6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
Setor




        7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
        8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
        9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
        10   5                                                9 25 41 57 72 88 10 95   99 106 113   60 126
        11 13                         6                      10 26 42 58 73 89 11 96 100 107 114 61 127
        12   6                                             4 11 27 43 59 74 90 12 97 101 108 115 62 127
        13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
        14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
        15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65
                                                                                                             52/89
E por que a R*TS ficou tão
                    “rápida”?
●   Os raw sectors são decodificados on the fly, indo diretamente para a
    memória a que se destinam
    –   Sem buffers intermediários, sem memory moves
    –   Exceto o primeiro e o último setor de arquivos binários, que são carregados
        num buffer de I/O e então copiados para o target para não sobrescrever
        memória limítrofe
        ●   Era o mais perverso efeito colateral da CompatiBoot original, diga-se de passagem
●   Ela não espera pelo próximo setor, mas monta uma lista dos setores
    desejados e vai carregando na medida em que eles passam debaixo
    do cabeçote
    –   Não há espera pelo “próximo setor”
    –   Os gap bytes me dão tempo suficiente para recomeçar a leitura entre o fim de
        um setor e o começo do outro
    –   Mesmo o pior caso leva apenas uma revolução do disquete para ser lido.


                                                                                                53/89
CB2k:
                                 Modus Operandi
   Disk                                                  Trilha
             0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
        0    0                                               1A 15 31 47 62 78 0 15 23 102 109 116 120
        1    8                                                0 16 32 48 63 79 1 16 24 103 110 117 121
        2    1                            1                   1 17 33 49 64 80 2 17 25 104 111 118 122
        3    9                                                2 18 34 50 65 81 3 18 26 105 112 119 1B
        4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
        5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
        6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
Setor




        7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
        8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
        9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
        10   5                                                9 25 41 57 72 88 10 95   99 106 113   60 126
        11 13                         6                      10 26 42 58 73 89 11 96 100 107 114 61 127
        12   6                                             4 11 27 43 59 74 90 12 97 101 108 115 62 127
        13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
        14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
        15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65
                                                                                                             54/89
Mas então...
●   Por que não consertaram antes?
    –   Consertaram!
        ●   Apple
             –   ProDOS
        ●   Terceiros
             –   ProntoDOS
             –   DiversiDOS
             –   CP/M
    –   Mas nenhum deles foi portado para o TK-2000!
        ●   CB2k! :-)
    –   Nem implementaram leitura múltipla!
        ●   CB2k! ;-)



                                                       55/89
Hands on




           56/89
Check List
●   Café                        ●   Instruções de onde baixar e
                                    como instalar:
●   Salgadinhos                     –   MINGW
                                    –   CC65
●   Daft Punk na                    –   CiderPress
    vitrolinha :-)                  –   AppleWin
●   Estes Slides                    –   Emulador TK2000
                                ●   Os fontes do Hello Word
●   Imagem de disco                 –   Leia o READ.ME ! ;-)
    da CB2k (1.1r4a:Set/2012)           ●   Instruções:
                                             –   Para montagem do programa,
                                             –   Importação do binário para uma
                                                 imagem de disquete
                                             –   e execução em emulador.

                                                                                  57/89
Hello World
          .setcpu      "6502"                         :    lda           (PRINT_DATA),y
          .localchar   '@'                                 beq           :+
                                                           jsr           PRINT_ASCII
          .include "../hw.def"                             iny
          .include "../sys.def"                            bne           :-
          .include "../bios.def"                           inc           PRINT_DATA+1
                                                           bne           :-
          .include "../CB2k.def"                      :
                                                           jsr           ANYKEY
          .include "system.def"                            jsr           SYSTEM_HGR
                                                           SYS           CB2K_FILE_LOAD
          .org $800                                        jsr           ANYKEY

                                                      NO_FUN:
    jsr        SYSTEM_INIT                                  jmp          SYSTEM_APPLESOFT_START_COLD

    ldy        #CB2K_HANDLER_ERROR                    ANYKEY:
    lda        #<NO_FUN                                     PRINT        ANYKEY_TEXT
    ldx        #>NO_FUN                                     jmp          MON_RDKEY
    SYS        CB2K_HANDLER_SET
                                                      HEADER:
:                                                     HEADER_line_0:
    PRINT HEADER                                            .byte 22,0
    dec         HEADER_line_1                               textz "============ Hello World !! ============"
    dec         HEADER_line_0                         HEADER_line_1:
    bmi         :+                                          .byte 23,0
    lda         #90                                         textz "                                        "
    jsr         MON_WAIT                                    .byte 1,0,0
    beq         :-                 ; Branch always!         .byte -1
:
                                                      ANYKEY_TEXT:
    lda        #<MENSAGEM_TEXT                              .byte 23,0
    ldx        #>MENSAGEM_TEXT                              textz ":"
    sta        PRINT_DATA                                   .byte -1
    stx        PRINT_DATA+1
                                                           .include      "system.inc"
    ldy        #0
                                                      MENSAGEM_TEXT:
                                                            .include     "mensagem.txt"

                                                                                                        58/89
Hello World
          .setcpu      "6502"                                  :     lda           (PRINT_DATA),y
          .localchar   '@'                                           beq           :+
                                                                     jsr           PRINT_ASCII
          .include "../hw.def"                                       iny
          .include "../sys.def"                                      bne           :-
          .include "../bios.def"                                     inc           PRINT_DATA+1

          .include "../CB2k.def"
                                                ●     Configura dialeto do
                                                           :
                                                                     bne           :-


                                                      processador SYSTEM_HGR
                                                              jsr     ANYKEY
          .include "system.def"                               jsr
                                                              SYS     CB2K_FILE_LOAD
          .org $800                                                  jsr           ANYKEY
                                                ●     Configura prefixo para rótulos
                                                            NO_FUN:
                                                                  jmp SYSTEM_APPLESOFT_START_COLD
    jsr        SYSTEM_INIT

    ldy        #CB2K_HANDLER_ERROR
                                                      locaisANYKEY:
    lda        #<NO_FUN                                              PRINT         ANYKEY_TEXT
    ldx
    SYS
               #>NO_FUN
               CB2K_HANDLER_SET                 ●     Inclui HEADER:
                                                             cabeçalhos que
                                                                     jmp           MON_RDKEY


:
    PRINT HEADER                                      definem símbolos da
                                                             HEADER_line_0:
                                                                   .byte 22,0

                                                      plataforma 23,0
    dec         HEADER_line_1                                      textz "============ Hello World !! ============"
    dec         HEADER_line_0                                HEADER_line_1:
    bmi         :+                                                 .byte
    Lda         #90                                                  textz "                                      "


:
    jsr
    beq
                MON_WAIT
                :-
                                                ●
                                   ; Branch always!   Inclui o cabeçalho do Sistema
                                                                     .byte 1,0,0
                                                                     .byte -1


    lda        #<MENSAGEM_TEXT
                                                      Operacional 23,0
                                                             ANYKEY_TEXT:
                                                                   .byte
    ldx        #>MENSAGEM_TEXT                                       textz ":"
    sta
    stx
               PRINT_DATA
               PRINT_DATA+1                     ●     Inclui o cabeçalho da
                                                                     .byte -1

                                                                   .include "system.inc"
    ldy        #0
                                                      biblioteca de sistema
                                                             MENSAGEM_TEXT:
                                                                     .include      "mensagem.txt"

                                                                                                               59/89
Hello World
          .setcpu      "6502"                                  :    lda            (PRINT_DATA),y
          .localchar   '@'                                          beq            :+
                                                                    jsr            PRINT_ASCII
          .include "../hw.def"                                      iny
          .include "../sys.def"
          .include "../bios.def"
                                      ●   Onde começar o programa?  bne
                                                                    inc
                                                                                   :-
                                                                                   PRINT_DATA+1
                                                                    bne            :-
                                                               :
                                              Qual o tamanho do binário?
          .include "../CB2k.def"
                                          –               jsr   ANYKEY
          .include "system.def"                           jsr   SYSTEM_HGR
                                                                    SYS            CB2K_FILE_LOAD
          .org $800                            ●   Difícil preverjsr
                                                                  antes de começar, não?
                                                                         ANYKEY

                                                               NO_FUN:
    jsr        SYSTEM_INIT                –   Usa gráficos?
                                                          jmp                      SYSTEM_APPLESOFT_START_COLD

    ldy        #CB2K_HANDLER_ERROR                             ANYKEY:
    lda
    ldx
               #<NO_FUN
               #>NO_FUN
                                               ●   Num Apple?PRINT
                                                               jmp
                                                                                   ANYKEY_TEXT
                                                                                   MON_RDKEY
    SYS        CB2K_HANDLER_SET                ●   Num TK-2000?
                                                         HEADER:
:                                                              HEADER_line_0:
    PRINT HEADER
    dec         HEADER_line_1
                                                      –   Mas o TK sempre usa gráficos! World
                                                                   .byte 22,0
                                                                   textz "============ Hello           !! ============"
    dec
    bmi
    lda
                HEADER_line_0
                :+
                #90
                                          –   Modo texto?      HEADER_line_1:
                                                                     .byte 23,0
                                                                     textz "                                          "
    jsr         MON_WAIT                                             .byte 1,0,0
    beq         :-                              ●
                                   ; Branch always!Num Apple?        .byte -1
:

    lda        #<MENSAGEM_TEXT
                                               ●   Num TK-2000? 23,0
                                                         ANYKEY_TEXT:
                                                               .byte
    ldx        #>MENSAGEM_TEXT                                      textz ":"
    sta        PRINT_DATA                             –   Mas o TK não tem modo texto!
                                                                   .byte -1
    stx        PRINT_DATA+1

    ldy        #0                     ●   Onde é que tá a CB2k mesmo?
                                                                    .include

                                                               MENSAGEM_TEXT:
                                                                                   "system.inc"


                                                                     .include      "mensagem.txt"

                                                                                                                   60/89
Hello World                                                          Bloco II/A
                                                                                                                                                                                                         $FFFF
         $0000              Zero Page                                                                               Zero Page                         Extra RAM
         $0100                Stack                                                                                   Stack                                           Bloco I
                                                                                                                                                                                         ROM
          $0200
                                                                                                                              Bloco II/A P1          Bloco II/A P0   Extra RAM
                            I/O Buffer                                                                              I/O Buffer
                                                                                                                                                                                                         $D000

          $0300           Free RAM                                                                                   Free RAM
                        System Pointers                                                                            System Pointers
          $0400
                                                                                                                                                                                                         $C100
                             TEXT/GR                                                                               80TEXT/DGR                                                      Mem Map I/O           $C000
                              Page 1                                                                                  Page 1
                                                                                                                                               Bloco II/D




                                                  Sentiram
                                                                                                                                               Extra RAM
          $0800              TEXT/GR                                                                               80TEXT/ DGR                                                         HGR 2
                              Page 2                                                                                  Page 2
                                                                                                                    Bloco II/D P1             Bloco II/D P0
                                                                                                                                                                                                         $A000
         $1000
$0000      Zero Page Free RAM                                                                                       Free RAM
$0100        Stack
          $2000
$0200      Key Buffer




                                                  o drama?
                                                                                                                                                                                     Free RAM
            Free RAM         HGR 1                                                                                  DHGR 1                                                                               $4000
$0300     System Pointers
$0400    $4000                                                                                                                                                                         HGR 1
         TEXT/GR Page 1
                                                                                                                                                                                                         $4000

                             HGR 2                                                                                  DHGR 2
                                                                                                                                                                                                         $2000
$0800                                                                                                                                                                                  HGR 1
        TEXT/GR Page 2
         $6000
                                                                                                                                                                                                         $2000

$1000
           Free RAM
                                                                                                                                                                                     Free RAM
                            Free RAM                                                                                Free RAM
$2000                                                                                                                                                                                                    $0800
            HGR 1                                                                                                                                                                Some System Variables
                                                                                                                                                                                          &
                                                                                                                                                                                      Free RAM           $0400
         $C000                                                                         Mem Map I/O
$4000
                                                                                                                                                                                     System Pointers     $0300
                                                                                                                                                                                        Free RAM
         $C100                                                                         Expansion Slot
            HGR 2
                                                                                                                                                                                      I/O Buffer         $0200
                                                                                           ROM                                                                                          Stack            $0100
         $D000               L.C. P0               L.C. P1                                              L.C. P1      L.C. P0                                                         Zero Page           $0000
$6000
                     Language Card                     L.C. P0               L.C. P1       ROM                    Language Card
                         Main                                                                                         Main
         $FFFF RAM
          Free                                     Saturn Bank 7
                             Main                      Main                                                         AUX


$C000    Mem Map I/O                         L.C. P0               L.C. P1
$C100    Expansion Slot
             ROM                          Saturn Bank 1
                                               Main
$D000                                     L.C. P0            L.C. P1

             ROM                      Language Card
                                          Main
$FFFF
                                                                                                                                                                                                  61/89
Hello World
          .setcpu      "6502"                           :    lda         (PRINT_DATA),y
          .localchar   '@'                                   beq         :+
                                                             jsr         PRINT_ASCII
          .include "../hw.def"                               iny
                          ●
          .include "../sys.def"
          .include "../bios.def"
                                Algumas opções default       bne
                                                             inc
                                                                         :-
                                                                         PRINT_DATA+1
                                                             bne         :-
          .include "../CB2k.def"
                                –   Para programas pequenos (pequenos mesmo)
                                                   :
                                                      jsr    ANYKEY
          .include "system.def"                              jsr         SYSTEM_HGR

          .org $800
                                     ●   $800 - $1FFF (6 Kbytes)
                                                             SYS
                                                             jsr
                                                                         CB2K_FILE_LOAD
                                                                         ANYKEY


    jsr        SYSTEM_INIT
                                –   Para programas maiorzinhosSYSTEM_APPLESOFT_START_COLD
                                                   NO_FUN:
                                                         jmp

    ldy
    lda
               #CB2K_HANDLER_ERROR ●
               #<NO_FUN
                                         $4000 - $9FFF (~24 Kbytes)
                                                        ANYKEY:
                                                              PRINT      ANYKEY_TEXT
                                                             jmp         MON_RDKEY
                                Fora disto, e terá HEADER: montar versões
                                                   que
    ldx        #>NO_FUN
    SYS                  ●
               CB2K_HANDLER_SET

:
    PRINT HEADER                específicas para cada máquina Hello World !! ============"
                                                   HEADER_line_0:
                                                         .byte 22,0
                                                         textz "============
    dec         HEADER_line_1
    dec         HEADER_line_0                           HEADER_line_1:
    bmi
    lda
                :+
                #90
                                –   Use CB2K_CONFIGURATION_GET saber o limite "
                                                        .byte 23,0
                                                        textz "
    jsr
    beq
                MON_WAIT
                :-
                                    superior da memória .byte 1,0,0
                                    ; Branch always!
                                                        usável
                                                        .byte -1
:

    lda        #<MENSAGEM_TEXT
                                –   Nem sonhe em usar.byte 23,0 no TK-2000!
                                                        HGR2
                                                 ANYKEY_TEXT:

    ldx        #>MENSAGEM_TEXT                               textz ":"
    sta
    stx
               PRINT_DATA
               PRINT_DATA+1
                                     ●   Até a próxima versão da CB2k, lógico! :-)
                                                             .byte -1

                                                             .include    "system.inc"
    ldy        #0
                                                        MENSAGEM_TEXT:
                                                              .include   "mensagem.txt"

                                                                                            62/89
Hello World
                  .setcpu      "6502"                          :     lda          (PRINT_DATA),y
    ●
        Inicialização
                  .localchar   '@'                                   beq
                                                                     jsr
                                                                                  :+
                                                                                  PRINT_ASCII
                 .include "../hw.def"                                iny
        –   Biblioteca SYSTEM
                 .include "../sys.def"                               bne          :-
                  .include "../bios.def"                             inc          PRINT_DATA+1
    ●
        Configura manipulador de Erro                                bne          :-
                  .include "../CB2k.def"                       :
        –   Se algo der errado, inicializa o Applesoft e dá o prompt jsr          ANYKEY
                                                                     jsr          SYSTEM_HGR
            pro usuário "system.def"
                 .include
                                                                     SYS          CB2K_FILE_LOAD
                  .org $800                                          jsr          ANYKEY

                                                               NO_FUN:
            jsr        SYSTEM_INIT                                   jmp          SYSTEM_APPLESOFT_START_COLD

            ldy        #CB2K_HANDLER_ERROR                     ANYKEY:
            lda        #<NO_FUN                                      PRINT        ANYKEY_TEXT
            ldx        #>NO_FUN                                      jmp          MON_RDKEY
            SYS        CB2K_HANDLER_SET
                                                               HEADER:
:                                                              HEADER_line_0:
            PRINT HEADER                                             .byte 22,0
            dec         HEADER_line_1                                textz "============ Hello World !! ============"
            dec         HEADER_line_0                          HEADER_line_1:
            bmi         :+                                           .byte 23,0
            lda         #90                                          textz "                                        "
            jsr         MON_WAIT                                     .byte 1,0,0
            beq         :-                 ; Branch always!          .byte -1
:
                                                               ANYKEY_TEXT:
            lda        #<MENSAGEM_TEXT                               .byte 23,0
            ldx        #>MENSAGEM_TEXT                               textz ":"
            sta        PRINT_DATA                                    .byte -1
            stx        PRINT_DATA+1
                                                                     .include     "system.inc"
            ldy        #0
                                                               MENSAGEM_TEXT:
                                                                     .include     "mensagem.txt"

                                                                                                                 63/89
Hello World
    ●   LOOP (até "6502" a linha da primeira zString seja menor que 0)
          .setcpu que                          :    lda    (PRINT_DATA),y
               .localchar   '@'                                      beq          :+
                                                                     jsr          PRINT_ASCII
         –    PRINT (macro em SYSTEM.DEF)
               .include "../hw.def"                                  iny
               .include "../sys.def"                                 bne          :-
                 Imprime <n> zStrings
              .include
              ●         "../bios.def"      (terminada em 0,   C-style) em
                                                                     inc     posições específicas da tela
                                                                                PRINT_DATA+1
                                                                     bne          :-
              ●   (Rotina de SYSTEM.INC)
              .include  "../CB2k.def"                          :
                                                                     jsr          ANYKEY
         –    Pausa de ~25 mSecs
               .include "system.def"                                 jsr
                                                                     SYS
                                                                                  SYSTEM_HGR
                                                                                  CB2K_FILE_LOAD
               .org $800                                             jsr          ANYKEY
              ●   (Rotina na ROM)
                                                               NO_FUN:
          –
        jsr   NotarSYSTEM_INIT
                    que MON_WAIT sempre volta com ZeroFlag em 0.
                                                    jmp      SYSTEM_APPLESOFT_START_COLD

        ldy         #CB2K_HANDLER_ERROR                        ANYKEY:
    ● ldaNotar os branchs relativos anônimos!
        ldx
                #<NO_FUN
                #>NO_FUN
                                                                     PRINT
                                                                     jmp
                                                                                  ANYKEY_TEXT
                                                                                  MON_RDKEY
        SYS         CB2K_HANDLER_SET
                                                               HEADER:
:                                                              HEADER_line_0:
        PRINT HEADER                                                 .byte 22,0
        dec         HEADER_line_1                                    textz "============ Hello World !! ============"
        dec         HEADER_line_0                              HEADER_line_1:
        bmi         :+                                               .byte 23,0
        lda         #90                                              textz "                                        "
        jsr         MON_WAIT                                         .byte 1,0,0
        beq         :-                 ; Branch always!              .byte -1
:
                                                               ANYKEY_TEXT:
        lda         #<MENSAGEM_TEXT                                  .byte 23,0
        ldx         #>MENSAGEM_TEXT                                  textz ":"
        sta         PRINT_DATA                                       .byte -1
        stx         PRINT_DATA+1
                                                                    .include      "system.inc"
        ldy         #0
                                                               MENSAGEM_TEXT:
                                                                     .include     "mensagem.txt"

                                                                                                                 64/89
Hello World
●   Dois loops:
             .setcpu          "6502"                                :      lda
                                                                           beq
                                                                                        (PRINT_DATA),y
                                                                                        :+
                 .localchar   '@'
    –   O interno, “driven” pelo Y                                         jsr          PRINT_ASCII
                 .include "../hw.def"                                      iny
        ●   O INY “overflows” para 0 depois do 255.
                 .include "../sys.def"                                     bne          :-
        ●   BNE :.include último resultado da ULA não deu em zero
                  pula se o "../bios.def"                                  inc          PRINT_DATA+1
                                                                           bne          :-
    –   O externo, “driven” pelo último valor lido em Acc
               .include "../CB2k.def"                               :
                                                                           jsr          ANYKEY
        BEQ: .include "system.def" em Acc for zero, sai do
        ●     Se o último byte carregado                                   jsr          SYSTEM_HGR
        loop.                                                              SYS          CB2K_FILE_LOAD
              .org $800
    – BEQ/BNE e outros atuam em cima do Registrador                        jsr          ANYKEY
        de Status (P)                                               NO_FUN:
       jsr reflete o SYSTEM_INIT operação da ULA, ou da
        ●Que           status da última                                   jmp           SYSTEM_APPLESOFT_START_COLD
         última carga em registrador
       ldy            #CB2K_HANDLER_ERROR                           ANYKEY:
    – PRINT_ASCII#<NO_FUN
       lda                                                                PRINT         ANYKEY_TEXT
       ldx            #>NO_FUN                                            jmp           MON_RDKEY
       ● Imprime o caractere ASCII no Acc
       SYS            CB2K_HANDLER_SET                              ●   PRINT_DATA
                                                                    HEADER:
●
:
    Dirty and Tricky!                                               HEADER_line_0:
                                                                      – Duas posições na página zero (escolhidas à
         PRINT HEADER                                                     .byte 22,0
    –   Eu sei que a única forma do INC dar em zero é
         dec          HEADER_line_1
        PRINT_DATA HEADER_line_0
                      acabar apontando para a página zero
                                                                        dedo!) para servir deHello World !! ============"
                                                                          textz "============ ponteiro para o buffer do
         dec                                                        HEADER_line_1:
        –bmi nunca :+ armazena strings! ;-)
          onde        se                                                texto a 23,0 impresso
                                                                          .byte ser
         lda            #90                                               textz "                                       "
    –   Na prática, pula sempre!                                      – Estas instruções ocupam 2 bytes, e não 3!
                                                                          .byte 1,0,0
         jsr          MON_WAIT
         beq            :-                  ; Branch always!              .byte -1
:
                                                                    ●   Usaremos o Y como indexador no loop que
         lda            #<MENSAGEM_TEXT
                                                                        vem a seguir
                                                                    ANYKEY_TEXT:
                                                                          .byte 23,0
         ldx            #>MENSAGEM_TEXT                                   textz ":"
         sta            PRINT_DATA                                    – Inicializa em
                                                                          .byte -1      0!
         stx            PRINT_DATA+1
                                                                           .include     "system.inc"
         ldy            #0
                                                                    MENSAGEM_TEXT:
                                                                          .include      "mensagem.txt"

                                                                                                                      65/89
Hello World
                 .setcpu      "6502"                :    lda           (PRINT_DATA),y
                 .localchar   '@'                        beq           :+
                                                         jsr           PRINT_ASCII
                 .include "../hw.def"                    iny
●   Aguarda por"../sys.def"
           .include
                      uma tecla (não
           .include "../bios.def"
                                                         bne
                                                         inc
                                                                       :-
                                                                       PRINT_DATA+1

    importa qual"../CB2k.def"
           .include                                 :
                                                         bne

                                                         jsr
                                                                       :-

                                                                       ANYKEY
                 .include "system.def"                   jsr           SYSTEM_HGR
●   Entra em modo gráfico
           .org $800
                                                         SYS
                                                         jsr
                                                                       CB2K_FILE_LOAD
                                                                       ANYKEY

●   Carrega o SYSTEM_INIT arquivo
       jsr      próximo                             NO_FUN:
                                                          jmp          SYSTEM_APPLESOFT_START_COLD

    binário do #CB2K_HANDLER_ERROR
       ldy
       lda
               catálogo
               #<NO_FUN
                                                    ANYKEY:
                                                          PRINT        ANYKEY_TEXT
         ldx          #>NO_FUN                            jmp          MON_RDKEY
    –   É uma tela HGR
         SYS          CB2K_HANDLER_SET
                                                    HEADER:
    :                                               HEADER_line_0:
             EuHEADERHEADER_line_1 coloquei lá!
         PRINT
         ●
         dec
                sei, fui eu que                           .byte 22,0
                                                          textz "============ Hello World !! ============"
    –   A CB2k já o deixou 'na agulha'
         dec
         bmi
                 HEADER_line_0
                 :+
                                                    HEADER_line_1:
                                                          .byte 23,0
         lda     #90                                      textz "                                        "
        quando carregou o programa
         jsr     MON_WAIT                                 .byte 1,0,0
                                                          .byte -1
         beq     :-              ; Branch always!
    :   corrente, basta a chamada para              ANYKEY_TEXT:
        carregá-lo
         lda
         ldx
                 #<MENSAGEM_TEXT
                 #>MENSAGEM_TEXT
                                                          .byte 23,0
                                                          textz ":"
         sta          PRINT_DATA                          .byte -1
         ● Ver CB2K_FILE_SET se não é o que
         stx      PRINT_DATA+1
                                                         .include      "system.inc"
           você quer
         ldy      #0
                                                    MENSAGEM_TEXT:
                                                          .include     "mensagem.txt"

                                                                                                      66/89
Hello World
                  .setcpu      "6502"                         :    lda           (PRINT_DATA),y
                  .localchar   '@'                                 beq           :+
                                                                   jsr           PRINT_ASCII
                  .include "../hw.def"                             iny
                  .include "../sys.def"                            bne           :-
                  .include "../bios.def"                           inc           PRINT_DATA+1
                                                                   bne           :-
                  .include "../CB2k.def"                      :
●   Aguarda.include "system.def"
            por outra tecla                                        jsr
                                                                   jsr
                                                                                 ANYKEY
                                                                                 SYSTEM_HGR
                                                                   SYS           CB2K_FILE_LOAD
●   Encerra,.org $800
             inicializando o Applesoft.                            jsr           ANYKEY

                                                              NO_FUN:
    –   A CB2k ainda tá na memória, mas não dá
          jsr      SYSTEM_INIT                                      jmp          SYSTEM_APPLESOFT_START_COLD

        suporte ao BASIC
          ldy      #CB2K_HANDLER_ERROR                        ANYKEY:
            lda        #<NO_FUN                                     PRINT        ANYKEY_TEXT
    –   Mas você pode brincar no MiniAssembler!
            ldx
            SYS
                       #>NO_FUN
                       CB2K_HANDLER_SET
                                                                    jmp          MON_RDKEY

                                                              HEADER:
    :
        ●   Se você estiver num Apple //e ou num TK-          HEADER_line_0:
            PRINT HEADERa Tomato Board revisada
            2000 com HEADER_line_1                                  .byte 22,0
            dec                                                     textz "============ Hello World !! ============"
            dec        HEADER_line_0                          HEADER_line_1:
            bmi        :+                                           .byte 23,0
            lda        #90                                          textz "                                        "
            jsr        MON_WAIT                                     .byte 1,0,0
            beq        :-                  ; Branch always!         .byte -1
    :
                                                              ANYKEY_TEXT:
            lda        #<MENSAGEM_TEXT                              .byte 23,0
            ldx        #>MENSAGEM_TEXT                              textz ":"
            sta        PRINT_DATA                                   .byte -1
            stx        PRINT_DATA+1
                                                                   .include      "system.inc"
            ldy        #0
                                                              MENSAGEM_TEXT:
                                                                    .include     "mensagem.txt"

                                                                                                                67/89
Hello World
                .setcpu      "6502"                         :    lda           (PRINT_DATA),y
                .localchar   '@'                                 beq           :+
                                                                 jsr           PRINT_ASCII
                .include "../hw.def"                             iny
                .include "../sys.def"                            bne           :-
                .include "../bios.def"                           inc           PRINT_DATA+1
                                                                 bne           :-
                .include "../CB2k.def"                      :
●
    Dirty and Tricky! "system.def"
              .include
                                                                 jsr
                                                                 jsr
                                                                               ANYKEY
                                                                               SYSTEM_HGR
                                                                 SYS           CB2K_FILE_LOAD
    – A anykey, por ser uma subrotina, deveria
                .org $800                                        jsr           ANYKEY
      terminar com um RTS                                   NO_FUN:
          jsr         SYSTEM_INIT                                 jmp          SYSTEM_APPLESOFT_START_COLD
    – Mas ela por sua vez se vale de outra rotina
      na sua última#CB2K_HANDLER_ERROR
          ldy
          lda          instrução, economizei um byte
                      #<NO_FUN
                                                            ANYKEY:
                                                                  PRINT        ANYKEY_TEXT
      (2 duas posições da pilha) fazendo um JMP
          ldx
          SYS
                      #>NO_FUN
                      CB2K_HANDLER_SET
                                                                  jmp          MON_RDKEY

      pra dita cuja.                                        HEADER:
    :                                                       HEADER_line_0:
       ● O RTS dela é quem faz o retorno a quem
          PRINT HEADER                                            .byte 22,0
          dec         HEADER_line_1                               textz "============ Hello World !! ============"
         chamou a ANYKEY.
          dec         HEADER_line_0                         HEADER_line_1:
          bmi        :+                                           .byte 23,0
          lda        #90                                          textz "                                        "
          jsr        MON_WAIT                                     .byte 1,0,0
          beq        :-                  ; Branch always!         .byte -1
     :
                                                            ANYKEY_TEXT:
          lda        #<MENSAGEM_TEXT                              .byte 23,0
          ldx        #>MENSAGEM_TEXT                              textz ":"
          sta        PRINT_DATA                                   .byte -1
          stx        PRINT_DATA+1
                                                                 .include      "system.inc"
          ldy        #0
                                                            MENSAGEM_TEXT:
                                                                  .include     "mensagem.txt"

                                                                                                              68/89
Aplicações
●   Demos! :-)
    –   No arquivo de Distribuição da CB2k você encontrará o fonte
        para todos os programas de demonstração.
        ●   Console I/O independente de máquina
             –   Conversão automática para maiúsculas em máquinas sem caracteres minúsculos
        ●   Sintetização de SOM!
             –   Eletric Duet / Paul Lutus
●   Exemplos mais complexos da API da CB2k
    –   Carregamento e/ou execução de arquivos
    –   Leitura do Diretório
    –   Handlers de sistema
        ●   Tratamento te exceções
        ●   RESET
                                                                                        69/89
Aplicações
●   Agora:
    –   Beautiful Boot
        ●   Jogos! Yeay! :-)
        ●   Porte feito por Fábio Belavenuto
●   Na agulha:
    –   Basic.system para o TK-2000
        ●   Uma solução definitiva para a fragmentação da memória do
            BASIC no TK-2000
        ●   RDOS style
    –   Novas Demos para a CB2k
        ●   Técnicas de animação e sintetização de Som simultâneos
        ●   O TK-2000 pode, o TK-2000 faz! :-)
●   Futuro:
    –   Substituto para o RDOS no Apple II
        ●   Tão logo eu crie coragem e escreva as rotinas de gravação
            de setores...
    –   Suporte transparente para outras mídias
        ●   Enquanto a API for estável, tanto faz de onde vêm os bytes!
    –   Arquivos de “Overlay”
                                                                          70/89
$A000



                        Known Issues
                                                                 HGR 2


                                                       $C000   Mem Map I/O
                                                       $C100


                                                       $D000                 Extra RAM
                                                                  ROM
                                                                              Bloco I
●   Código não relocável dinamicamente
                                                       $FFFF

    –   O S.O. está amarrado ao topo da memória
        principal (pouco antes da área de I/O)
    –   Ruim para o TK-2000, pois sua segunda página
        de vídeo está lá.
        ●   Jogos que usam paginação vão matar o S.O.
    –   Desperdiça a Bloco I / Language Card
        ●   Menos memória “segura” para os programas
             –   Que pra começo de conversa não foram feitos para conviver
                 com um sistema operacional de disco! :-)

                                                                              71/89
Known Issues
●   Read Only
    –   A CB2k não grava.
    –   “By Design” =P
        ●   Um processo complicado e ainda mais time critical.
        ●   Até o momento, baixa demanda.
        ●   Implementar gravação vai aumentar o footprint na memória
●   No LIBS
    –   A “biblioteca” não passa de um include sofisticado
        ●   Raios, o S.O. todo tá pendurado assim!
    –   Uma LIB estática é uma demanda forte
        ●   LIB dinâmica é sonho de consumo!
●   Incompatibilidade com a CFFA 3000
    –   Ainda investigando...
                                                                       72/89
Considerações Finais
●   Lições (Re)Aprendidas
    –   Projetos pessoais ainda são Projetos!
    –   Realidade Comanda
    –   Wear Sun Screen! :-)
●   Onde aprender mais?
●   Onde obter ajuda?



                                                73/89
Projetos Pessoais
                        ainda são

                     Projetos
●   Boas práticas também não têm este nome à toa!
    –  Xtreme Programming!
    – Rubber Ducking! ;-)
●   Eu me estrepei muito por não ter seguido
    algumas destas práticas desde o começo
●   E tive meu traseiro poupado de trágico destino
    por ter seguido outras


                                                     74/89
Projetos Pessoais
                                     ainda são

                                 Projetos
●   Version Control System
    –   RCS, CVS, SVN, GIT, Mercurial, Bazaar
        ●   Qualquer um, qualquer um mesmo!
             –   Até copy&paste em diretórios no seu HD!
●   Gerência de Configuração
    –   Procure saber em quais ambientes (e configurações)
        o seu software vai rodar
        ●   Mesmo que não possa garantir o funcionamento em todos!
        ●
            Principalmente para poder garantir o funcionamento em
            alguns!


                                                                 75/89
Projetos Pessoais
                                         ainda são

                                     Projetos
●   Use Cases e Back Logs
    –   Formalismos não são necessários
        ●   mas se você não especifica o quê você quer resolver, você não
            resolve é nada...
             –   Gold-plating não é legal.
    –   Um arquivo texto com um parágrafo por Requisito / UC /
        Whatever já é suficiente, o importante é que todos os
        envolvidos saibam do que se trata
        ●   Principalmente quando “todos os envolvidos” é só você! :-)
             –   O tempo passa e não tem mais ninguém pra lhe lembrar do que você tem
                 que fazer!
        ●
            Versione! Versione!!
    –   Foco, ou você não termina esta joça!
                                                                                   76/89
Projetos Pessoais
                                        ainda são

                                    Projetos
●   Fail early, Fail often!
    –   Unit Tests
        ●   Imprescindíveis ! :-)
        ●
            Mas eles custam caro, não subestimem o impacto no
            “orçamento” .
             –   Alguns bugs são mais baratos de serem consertados (se ocorrerem) que
                 prevenidos
             –   Você não tem tempo (nem dinheiro) pra fazer tudo o que quer.
    –   Test Cases / Test Suites
        ●   Porque testes de unidade não são capazes de pegar erros de
            integração que teimam em ocorrer
             –   E sempre nos piores momentos possíveis! :-)
        ●   As aplicações de exemplo são meus Test Suites públicos!

                                                                                   77/89
Realidade Comanda


●   Eat your own dogfood!
    –   É só aplicando na vida real que você tem
        certeza se uma idéia realmente funciona.
        ●   Ou não! ¬¬
    –   Você é seu primeiro e primário beta-tester.
        ●    Use seu produto, encontre você mesmo seus
            erros
             –   Ou outros o farão por você
                                                         78/89
Realidade Comanda
●   Beta testers
    –   Eu não teria conseguido sem ajuda!
        ●   Sem eles, e você desenvolve no escuro
             –   Exceto se dispor de recursos financeiros para comprar tudo em que bate os
                 olhos! ;-)
    –   Mas eles não serão muito úteis se você não fizer seu dever de
        casa:
        ●   Use Cases
        ●   Test Cases
        ●   Gerência de Configuração
        ●   Versionamento de Código
    –   Foi aqui que eu percebi que estava atirando no meu próprio pé
        ao “agilizar” o desenvolvimento ao custo de algumas boas
        práticas...
                                                                                             79/89
Realidade Comanda
●
    Não subestimar a importância de um bom
    Error Report
    –   Porque você *NUNCA* pegará todos os
        erros.
         ●
           Principalmente os bobos
            – Erro grave explode logo, são os
              bobos que dão trabalho!




                                                80/89
Realidade Comanda




KDIFF3 é pra vida! :-)




                         81/89
Links Relacionados
●   CB2k
    –  Suite de Testes
    – Debut da CB2k (Apple //e)
    – Debut² =P no TK-2000
●   Slides da palestra
●   http://pt.wikipedia.org/wiki/Apple_II
●   http://pt.wikipedia.org/wiki/TK2000
●   http://retro.lisias.net/

                                            82/89
Links Úteis
●   http://www.6502.org
●   http://www.cc65.org/
●   http://applewin.berlios.de/
●   http://www.fabio.belavenuto.nom.br/tk2000/
●   http://www.datacassete.com.br/
●   ftp://ftp.apple.asimov.net/pub/apple_II/
●   http://www.applefritter.com/
●   http://www.extremeprogramming.org/
●   http://www.codinghorror.com/blog/2012/03/rubber-duck-problem-solving.html
●   Ajuda Especializada 0:-)


                                                                          83/89
Links Interessantes
●   Paul Langhton
    –   Consultor responsável pelo Apple DOS
●   Steve Wozniak
    –   Responsável por todo o resto! :-)
●   Apple II History
    –   História do Apple II, versão do usuário.
●   ASCII Express' Game Server
    –   “Servidor” de jogos, com download em formato de áudio
        otimizado
    –   Para máquinas “diskless”
                                                                84/89
Links “Interessantes” =P
●   Câmara de Torturas
    (ou: se Donatien Alphonse François fosse Analista de Sistemas)

     –   Restauro e 'Mods' do TK-2000
         ● E outras vítimas


     –   Outros clássicos
         ● Alguns poucos conhecidos por aqui


     –   Outros loucos
         ● Porque gostamos de companhia. O:-)




                                                                     85/89
(alguma)
              Literatura Recomendada
●   How to program the Apple II using    ●   Software Control of the Disk II or IWM
    6502 Assembly Language                   Controller
    –   DATAMOST, 1982                       –   Norman Leung
    –   Randy Hyde                           –   Apple Computer, 1984
    –   Featuring LISA Assembler
                                         ●   Andrew S. Tanenbaum
●   Beneath Apple DOS /                      –   Eternamente :-)
    Beneath Apple ProDOS                 ●   Microcomputadores e
                                             Microprocessadores
    –   Don Worth & Pieter Lechner
                                             –   Albert Paul Malvino
    –   Quality Software, 1982
                                             –   McGraw-Hill, 1985
●   Understanding the Apple II           ●   The Pragmatic Programmer: From
    –   James Fielding Sather                Journeyman to Master
    –   Quality Software, 1983               –   Andrew Hunt & David Thomas
    –   Com Introdução do Woz! :-)           –   Addison-Wesley Professional, 1999


                                                                                     86/89
Onde Obter Ajuda
●   Lista appleII_br
●   Newsgroup comp.sys.apple
    –   E os diversos subgrupos desta hierarquia
●   me@lisias.net ;-)
●   Ajuda Especializada 0:-)




                                                   87/89
Free Chat
●   Dúvidas?
●   Comentários?
●   Sugestões?
●   Apoio moral?
    –   (Piada interna da appleII_br)
    –   *<8o)




                                        88/89
Obrigado!




@lisias
me@lisias.net
http://tk2k.lisias.net/CB2k                       89/89

Boldly crashing what no man has crashed before!
Um Carregador Rápido para
   TK-2000 e Apple II
que virou Sistema Operacional




                        http://tk2k.lisias.net/CB2k
Premissa

            i.Restaurar um obscuro
        computador doméstico de quase 30
                  anos de idade
        ii.Escrever um sistema operacional
                     pro dito cujo
                     iii.?????
                  iv.PROFIT! :-)



Piadinha básica #Slashdot
@Lisias
         |
                                   http://lisias.net
                                                  3/89




Perfil profissional

Enfase na esperiência (porque se depender da
 competência... X-P)

Para o bem e para o mal, botei minhas patas sujas
 em várias áreas diferentes (e mesmo conflitantes)
 da Computação

Metade elas terem sido compradas pelos
 concorrentes não foi minha culpa! X-)
@Lisias
                              http://retro.lisias.net
                                                   4/89




Perfil pessoal

Maníaco da Chave de Fenda

Não tem nada aqui em casa que eu já não tenha
 desmontado. Ou destruído. =P

Breve histórico da minha iniciação na computação
     Apple II
     TK-2000 dos amigos
          MSX e Amiga de outros
As Vítimas
      ●   Scene Retrô brasileira de Apple II e Compatíveis (ou quase)
          –   Intensa movimentação nos últimos 18 meses
      ●   Inúmeras novidades
          –   engenharia reversa do Cartucho Controlador de Discos do TK-2000
          –   Tomato Board




                                                                           5/89




●Scene Retrô brasileira de Apple II e Compatíveis
  (ou quase)
  ● Intensa movimentação nos últimos 18 meses

    ● Não apenas ela, diga-se de passagem

●Inúmeras novidades

  ● engenharia reversa do

      Cartucho Controlador de Discos do TK-2000
    ● Atualmente raro e dispendioso

  ● Tomato Board, uma plaquinha adaptadora que

      permite usar interfaces Disk II do Apple no slot
      do TK-2000
    ● Ironia das ironias, o Cartucho de Disco do TK-

        2000 (ou do original, o MPF-II) foi
        desenvolvido através de engenharia reversa
        na Disk II :-)
O Motivo
         ●   Acesso à Hardware equivalente, mais barato e
             abundante, da linha Apple
         ●   Mas os jogos (e parte significativa dos demais
             softwares) ainda estavam em formato Cassete
         ●   Soluções (software) prontas, importadas do Apple II,
             eram
             –   Muito complexas para portar
                 ●   ProntoDOS, DiversiDOS, ProDOS
                      –   todos ótimos, mas sistemas operacionais completos!
             –   Overkill
             –   Over memory :-)
                                                                               6/89




●As Interfaces de Disco e Drives de Apple II são relativamente baratos
   ●   E, de um mês para outro, diversos TK-2000 ganharam acesso à disquetes!
●Mas os jogos (e parte significativa dos demais softwares) ainda estavam em formato

   Cassete
   ●   (ou equivalentes modernos como MP3 e CT2)
       ●  sendo carregados pela porta de Audio!
   ●   Convertê-los para formato de arquivo é relativamente fácil
       ●  ainda em andamento, na medida em que os títulos são resgatados
   ●   Fazê-los funcionar debaixo do TK-DOS nem tanto
       ●  E não enlouquecer esperando o boot acontecer ainda menos.
●Soluções importadas do Apple II não atendiam

   ●   As diferenças estruturais entre as máquinas não permitem um reuso direto
   ●   As soluções simples invariavelmente eram limitadas ou incômodas
       ●  Não extensíveis, não adaptáveis
       ●  Hacks interessantes e úteis, mas feitos por hackers para hackers e resolvem
              um problema específico com o menor custo
   ●   As soluções completas eram muito complexas para portar
       ●  ProntoDOS, DiversiDOS, ProDOS
          ●   todos ótimos, mas sistemas operacionais completos!
       ●  Overkill
       ●  Over memory :-)
Enquanto isto...
             ●   “lá fora” (news:comp.sys.apple)
                 –   CompatiBoot original (Raven/C700 Club)
                     ●   Rápida
                     ●   Prática
                     ●   Mas não adequada
                          –   Capenga no TK-2000
                          –   One shot only
                          –   Altas gambiarras pra convencer a dita cuja a fazer o que
                              precisávamos
                          –   Efeitos colaterais diversos e inesperados



                                                                                         7/89




●   Enquanto isto, “lá fora” (news:comp.sys.apple)
      ● Com problemas parecidos, soluções “quick & dirty” foram desenvolvidas e
           publicadas, dentre elas a CompatiBoot original (Raven/C700 Club)
      ● teve boa recepção na lista appleII_br
        ●  Hiper rápida
           ●   “Herdeira” das rotinas de disco usadas na eZine francesa Dox-a-gaz (circa
                   1988), de autoria de Max-a-gaz.
               ●   “Herdeira” do utilitário de cópias “Locksmith”, da Omega Microware (circa
                       1985)
        ●  Super prática
        ●  Basta copiar o binário para a primeira entrada do catálogo e dar boot.
      ● Mas capenga no TK-2000
        ●  One shot only
        ●  Altas gambiarras pra convencer a dita cuja a fazer o que queríamos
        ●  Efeitos colaterais diversos e inesperados
Indo direto ao ponto
         ●   Benchmark : TK-DOS 3.3
             –   Tempo entre ligar a máquina (com um disquete com boot no drive) e o Prompt do
                 Applesoft:
                 ●   31 segs.
             –   Tempo para carregar uma tela gráfica HGR:
                 ●   10 segs
             –   Espaço livre na RAM depois de carregado:
                 ●   ~ 24 Kbytes.
                      –   Não, não é Mega. É Kilo mesmo! :-)
         ●   Demais S.O.s
             –   Overkill
         ●   Outras Soluções
             –   Não são práticos nem flexíveis
             –   São perdulários
             –   Não funcionam, ou o fazem porcamente, no TK-2000

                                                                                                 8/89




●O Apple/TK DOS 3.3
   ●  É muito “grande”
   ●  É muito lerdo
●Demais S.O.s

   ●  Overkill
●Fast Loaders legados

   ●  Não são práticos nem flexíveis
      ●  um saco criar o disco de boot!
      ●  Armazenam dados controlando diretamente os setores do disco
         ●  Sem diretórios
         ●  Atualização/manutenção impraticável
   ●  São perdulários
      ●  Um disco por jogo, mesmo que 10 deles caibam no disquete
   ●  Não funcionam, ou o fazem porcamente, no TK-2000
O Crime


                 “Hummmm...”
                   Groo faz o que...

         “Eu acho que faço melhor!”


                                            9/89




As 5 palavrinhas que antecedem uma grande
 descoberta.

Ou um tremendo desastre...
Advertência
      O uso indiscriminado e                   Podem causar danos
      concomitante de                          irreversíveis à/ao
      –   Linguagem Assembler
                                               –   Sanidade mental
      –   Rotinas de Tempo Real
      –   Computadores Vintage
                                               –   Relacionamentos amorosos
      –   Conceitos (nem tão assim)            –   Vida social
          avançados de Arquitetura de
          Computadores e Sistemas
                                               –   Convivência familiar
          Operacionais                         –   Organização domiciliar
      –   Café, cerveja, pizzas, lanches e     –   Paz condominial
          snacks
      –   EL&P, Rick Wakeman, Jean Michel
                                               –   Perímetro da sua cintura :-)
          Jarre, Vangelis, Daft Punk e
          Kraftwerk

                        Depois não digam que a culpa é minha!! :-)
                                                                                  10/89




Porque não há prazer sem dor!
Planejando a ação
         ●   A CB2k deve:
             –   Carregar arquivos com a maior eficiência possível
             –   Permitir carregar programas que querem ocupar o
                 espaço onde normalmente ficaria o DOS
             –   Ser prática para criar/atualizar disquetes
             –   Oferecer uma API consistente para programação
             –   Fornecer exemplos de como desenvolver
                 aplicações


                                                                       11/89




●A CB2k deve:
   ● Carregar arquivos com a maior eficiência possível
     ●   Ninguém quer esperar pra brincar!
   ● Permitir carregar programas que querem ocupar o espaço onde normalmente
         ficaria o DOS
     ●   menor footprint possível na memória principal
         ●   (a mais concorrida)
     ●   deve permitir ser movida para diferentes posições de memória
         ●   Para se acomodar mesmo com aqueles jogos “mais chatos”
   ● Ser prática para criar/atualizar disquetes
     ●   Usar o formato do Apple DOS 3.3
         ●   Todo mundo conhece
         ●   Ferramentas conhecidas para suporte
●A CB2k também deve:

   ● Oferecer uma API consistente para programação
     ●   API deve proteger as aplicações de:
         ●   Mudanças nos endereços das rotinas do kernel
             ●   (assim eu posso movê-lo pra cima e pra baixo, de acordo com a
                    conveniência)
         ●   Mudanças de formato de mídia (e até mesmo de mídia!)
             ●   Disquetes estão ficando raros
     ●   Facilitar Novas Aplicações!
         ●   Jogos multi-partes (Karateka)
         ●   Jogos BASIC com mais memória disponível
             ●   Algo importante principalmente para o TK-2000
         ●   Menus para os jogos
         ●   Demos
   ● Fornecer exemplos de como desenvolver aplicações
     ●   Sistemas Operacionais não são nada sem aplicações!
Planejando a ação
        ●   A CB2k não pode deixar de:
            –   Ser extensível e portável
            –   Ficar pronta em umas 4 ou 5 semanas.
                ●   Férias acabam!
            –   Ser útil e agregar valor
        ●   Demais funcionalidades (rede, ambiente
            gráfico, co-processamento, etc.)
            –   são totalmente fora de escopo
                ●   Hoje! ;-)

                                                       12/89




●A CB2k não pode deixar de:
  ● Ser extensível e portável

    ● Outras arquiteturas baseadas em 6502 (porque

        não?)
    ● Outras mídias (porque não?)

  ● Ficar pronta em umas 4 ou 5 semanas.

    ● Férias acabam!

  ● Ser útil e agregar valor

    ● Na boa: ninguém precisa de ainda outra

        solução meia-boca pra ficar quebrando
        galho...
●Demais funcionalidades (rede, ambiente gráfico, co-

  processamento, etc.) são totalmente fora de
  escopo.
  ● Linus é um cara legal, não quero concorrer com

      ele! ;-)
    ●   Ele ganha...
It's coding time!




    ●   BELEZA!!
        Já sei o que quero fazer, agora é
        só ligar a máquina e... Oh, wait...
        –   Como se programa nesta joça?

                                           13/89
First Things First




                                             code
                         “One does not simply walk into Mordor!”
                                    Boromir, The Fellowship of the Ring

                                                                          14/89




Rapadura é doce, mas não é mole não!

Quando se programa um Sistema Operacional, por
 mais simples que seja, você passa a ser provedor
 de serviços, e não mais consumidor!

Você vira o juiz de futebol: tudo agora é sua culpa.

Uma bela mudança de paradigma...

(Comentei que sou paranóico?) X-D
Programação de Baixo Nível
                         Não tem este nome à toa...
     ●   O legendário 6502
     ●   Arquitetura dos Computadores
         –   Apple II+
         –   MPF-II/TK-2000
         –   Semelhanças e diferenças entre as máquinas target
     ●   Disquetes: um problema em tempo real
         –   A Shugart
         –   A Disk II do Woz
         –   Persistência de dados em mídias magnéticas


                                                                 15/89




Comumente chamada de “Programação de Baixo
 Calão” - vocês não imaginam o que se houve de
 um programador ASM estressado...
O 6502
●   Registradores
●   Instruções
●   Clock Cycle Time
    –   Cycle para os íntimos
        ●   T States
    –   A únidade básica de tempo do processador
    –   A únidade básica de ansiedade do programador
●   Os diferentes Endereçamentos à memória
    –   O segredo do sucesso!
    –   A Salvação da Pátria!
●   O primeiro RISC?
●   Sucessores
    –   65C02
    –   65816

                                                       16/89
$0000     Zero Page
    $0100       Stack
                                                             O 6502
                                        A
                             7 6 5 4 3 2 1 0

                                        X                          Y
                             7 6 5 4 3 2 1 0                 7 6 5 4 3 2 1 0

                                        S                          P
                             7 6 5 4 3 2 1 0                 N V 1 B D I Z C

                                                       PC
                             15 14 13 12 11 10 9 8           7 6 5 4 3 2 1 0


                                    ●   Load / Store                ●   Trasnfer                   ●   ROR, ROL, SHL, SHR
                                            –   Pero no mucho!          –   AX, XA                     –   A
            Free Addresses                                              –   AY, YA                             #imm
                                    ●   LD / ST                                                            ●

                                                                        –   XS, SX                         ●   Abs
                                            –   [A,X,Y] #imm        ●   Branchs                            ●   Abs,X
                                            –   A abs,X                 –   EQ / NE (Zero Flag)            ●
                                                                                                               Abs,Y
                                            –   A abs,Y                     MI / PO (Minus Flag)
                                                                        –                                  ●   (Indi,X)
                                            –   A (indi,X)              –   CS, CR (Carry)                 ●
                                                                                                               (Ind),Y
                                            –   A (indi),Y              –   VS, VC (Overflow)      ●   ADC, SBC
                                    ●   JMP                         ●   P (Status)                     –   A
                                            –   JMP abs                 –   SEC, CLC                       ●   #imm
                                                                        –   Etc                                Abs
                                            –   JMP (indi)                                                 ●

                                                                    ●   INC / DEC                          ●   Abs,X
                                    ●   JSR / RTS
                                                                        –   A, X, Y                        ●
                                                                                                               Abs,Y
                                    ●   Stack                           –   Abs                            ●   (Indi,X)
                                            –   PHA / PLA               –   Abs,X                              (Ind),Y
    $FF00                                                                                                  ●


                ROM                         –   PHP / PLP               –   Abs,Y                      Muito Mais!          17/89
    $FFFF                                                                                          ●




Ênfase no mapa de memória – todo computador
 baseado no 6502 tem este “jeitão”

Ênfase na importância dos modos de
 endereçamento, em particular, página 0
O Apple II+
●   Hardware
    –   Memory Mapped I/O
    –   Modos de vídeo
    –   Mapa da RAM
●   ROM
    –   Principais entry-points
    –   Uso da Página Zero
●   Console I/O
    –   Teclado
    –   Caracteres


                                         18/89
$0000      Zero Page


                                                O Apple II+
    $0100        Stack
    $0200      I/O Buffer
                Free RAM
    $0300     System Pointers
    $0400
             TEXT/GR Page 1                                           ●   Buffer de I/O
    $0800                                                                 – Usado pelo sistema (e pelo DOS) para
            TEXT/GR Page 2                                                  entrada e saída de dados
    $1000                                                                    ● Teclado
               Free RAM
                                                                             ● Disco

    $2000                                                                    ● Etc.

                HGR 1                                                 ●   2 Páginas de texto
                                                                          – 1 delas pode ser usada para programação
    $4000
                HGR 2
                                                                      ●   2 Páginas de gráficos
                                                                          – Ambas podem ser usadas para programação
    $6000                                                             ●  A ROM pode ser “sombreada” por um
                                                L.C. P0                  mecanismo chamado “Language Card”
                                                                      L.C. P1

               Free RAM                     Saturn Bank 7
                                                                          – A LC é dividida em 3 bancos
                                                Main                         ● 1 Principal


                                                                             ● 2 Secundários, que dividem o mesmo


    $C000    Mem Map I/O              L.C. P0               L.C. P1            endereço
    $C100                                                                 – A LC pode ser expandida através de bancos
             Expansion Slot
                 ROM               Saturn Bank 1                            de memória
                                        Main
    $D000                                                                    ● Saturn 128Kb.
                                   L.C. P0            L.C. P1

                 ROM            Language Card
                                    Main                                                                              19/89
    $FFFF




Notar o topo da memória livre, onde fica o DOS.

(Importante para entender alguns dilemas com
  relação ao TK-2000)
O Apple II+
●   Teclado “ASCII”
    –   Um uC faz o serviço sujo para você
    –   Curto e Grosso
        ●   E simples de ler!
    –   Mas um saco para os jogos
        ●   Control e Shift não são dectáveis sem mods
        ●   Combinações de teclas (que não envolvem as
            modificadoras acima) são impossíveis de
            serem detectadas
             –   A segunda sobrescreve a primeira, e ponto final
●   Caracteres
    –   ASCII
        ●   Alfanuméricos
        ●   Suporte à Minúsculas opcional (!!!)
    –   Inverso e Flash

                                                                   20/89
O MicroProfessor II
                                 e seu primo brasileiro

                                 TK-2000
     ●   Hardware
         –   Memory Mapped I/O
         –   Modos de vídeo
         –   Mapa da RAM
     ●   ROM
         –   Principais entry-points
         –   Uso da Página Zero
     ●   Console I/O
         –   Teclado
         –   Caracteres
                                                          21/89




Curiosidade.

O MPF-II foi concebido por uma empresa chamada
 Multitech – que mais tarde passou a se chamar
 Acer.

Por um acaso, a Acer fabricou o laptop que estou
 usando na palestra – coincidência interessante!
$0000
    $0100
                Zero Page
                   Stack
                                          O MicroProfessor II
                                                   e seu primo brasileiro
    $0200        I/O Buffer

                                                  TK-2000
                  Free RAM
    $0300       System Pointers
    $0400        Free RAM
                     &
            Some System Variables                          ●    2 páginas de gráficos
    $0800
                                                                –   Como não há modo texto, uma delas
                Free RAM                                            obrigatoriamente precisa estar em uso pelo
                                                                    sistema
    $2000                                                       –   O TK-DOS ocupa quase toda a página 2 :-(
                  HGR 1
                                                           ●    ROM pode ser programaticamente
    $4000         HGR 1                                         substituída pelas Extra RAM
                                                           ●    Bloco I : 15.75 Kbytes
                Free RAM                                   ●    Bloco II : 4 bancos de 16Kbytes
                                                                –   1 banco de 8 kbytes
    $A000                                                       – 2 sub-bancos de        4 kbytes
                                                       Bloco II/D P0     Bloco II/D P1
                  HGR 2                                         – Saturn 64Kb! :-)
                                                        Extra RAM ●   O meu tem 128Kb! :-)
    $C000     Mem Map I/O                               Bloco II/D
    $C100
                                                           ●    Apenas um Bloco pode estar ativo num
                                                                momento
    $D000                                       Bloco II/A P0         Bloco II/A P1
                   ROM
                                    Extra RAM                   –   Os bancos do Bloco II precisam escolher qual
                                     Bloco I
                                                 Extra RAM          página de 4 kbytes deve estar ativa
                                                 Bloco II/A
    $FFFF                                                                                                          22/89




Notar o topo da memória livre.

Agora ali tem uma página HGR, o que foi boa ideia
 porque expande o bloco de memória usável caso o
 programa decida por usar a página 2 como display.

Mas no Apple, esta memória era livre e foi ali que o
 DOS foi parar.

Moral: no TK-2000, não se pode ridar jogos com
 animação complexa (com paginação de vídeo).
O MicroProfessor II
                                           e seu primo brasileiro

                                           TK-2000
●
    Teclado com a Matriz exposta
    – Sem um MicroControlador pra fazer o serviço pesado
    – Vantagens
       ● Acesso individual (e múltiplo!) ao estado de cada tecla


          – permite algumas combinações interessantes para jogos
    – Desvantagens
       ● Gasto de processamento para ler o teclado


       ● Principal e maior motivo da “má fama” do TK-2000


          – A rotina do fabricante, oferecida no Manual Técnico
            como alternativa à leitura do teclado do Apple II era
            porca – simples assim
          – Um dos principais artefatos secundários do projeto:
             ●
               Uma rotina rápida de leitura de teclado! :-)
    – Caracteres
       ● ASCII


          – Alfanuméricos
          – Sem suporte às minúsculas (!!!)
       ● Semigráficos                                               Fonte: pág.21 TK2000/II Manual Técnico
                                                                                Microdigital Eletrônica LTDA


                                                                                                               23/89
$0000
    $0100
              Zero Page
                Stack
                                     O Apple //e & //c                                             Zero Page
                                                                                                     Stack
    $0200
    $0300
              I/O Buffer
               Free RAM
             System Pointers
                                         (porque todo castigo...)                                  I/O Buffer
                                                                                                    Free RAM
                                                                                                  System Pointers
    $0400      TEXT/GR                                                                            80TEXT/DGR
                Page 1                                                                               Page 1

    $0800
                               ●   Revisões
               TEXT/GR                                                                            80TEXT/ DGR
                Page 2              –   Apple // Extended                                            Page 2

    $1000
              Free RAM                  ●    6502                                                  Free RAM

    $2000                           –   Apple //c, //e Enhanced e Platinum
               HGR 1                                                                               DHGR 1
                                        ●    65C02
    $4000                               ●    “Mouse Chars”
               HGR 2                    ●    DTEXT (80 COLs), DGR & DHGR                           DHGR 2


    $6000
                               ●   128Kb
                                    –   Mas num esquema totalmente diferente
              Free RAM                                                                             Free RAM
                                    –   Descreve isto, Lisias!
                                        ●    Nah... Deixa quieto! =D
    $C000                                                     Mem Map I/O
    $C100                                           Expansion Slot         Extension
                                                        ROM                  ROM
    $D000      L.C. P0             L.C. P1                                             L.C. P1      L.C. P0

            Language Card                                            ROM                         Language Card
                Main                                                                                 Main
    $FFFF                                                                                                           24/89
                Main                                                                               AUX




Sem chance de dar suporte nativo ao Apple //e.

Uma versão específica para ele teria que ser feita,
 mas esta máquina simplesmente não precisa de
 mais um carregador rápido – muito menos, de um
 sistema operacional.

Manter a coisa rodando nele é interessante, mas
 fazer algo pra ele é chover no molhado – não sou
 necessário aqui.
Resumo da Ópera
        ●   As diferenças da ROM enchem o saco
            –   Oferecer uma camada de “abstração” da ROM seria bacana, mas
                exigiria mais memória
                ●   Mas não sai de graça
        ●   As diferenças na memória principal são facilmente gerenciáveis
            –   Mas o mesmo não acontece com os bancos de memória estendida
                ●   E lá se vão funcionalidades pela janela
        ●   O 65C02 têm instruções extras que seriam (muito) úteis
            –   Maior densidade de código e mais “semântica” por ciclo de clock
                ●   TXY (1 byte, 2 Ciclos)
                     –   PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!)
                     –   STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma posição da ZP)
                     –   STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos)
            –   Mas alienaria o TK-2000 e o Apple II+
                                                                                                    25/89




●As diferenças da ROM enchem o saco
   ●   Oferecer uma camada de “abstração” da ROM seria bacana, mas exigiria mais
          memória
       ●  Mas Consumir memória sem apelar para a memória estendida compromete a
             compatibilidade com software legado (os jogos!)
       ●  Dar suporte à memória estendida exigiria código específico para esta tarefa
          ●  E cada máquina usa uma arquitetura diferente...
             ●  Então cada máquina tem seu próprio código de gerenciamento de
                    memória
                ●   Então eu tenho que praticamente escrever 3 S.O.s diferentes!
●As diferenças na memória principal são facilmente gerenciáveis

   ●   Mas o mesmo não acontece com os bancos de memória estendida
       ●  O que limita a quantidade de código que eu posso socar no Kernel
          ●  O que limita as funcionalidades do Kernel!
●O 65C02 têm instruções extras que seriam (muito) úteis

   ●   Maior densidade de código e mais “semântica” por ciclo de clock
       ●  TXY (1 byte, 2 Ciclos)
          ●  PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!)
          ●  STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma
                posição da ZP)
          ●  STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos)
   ●   Mas alienaria o TK-2000 e o Apple II+
Mas não é só isso!




                                    26/89




Nunca é! :-)
Mídias Magnéticas
     ●   Revoluções Por Minuto
         Mas sem as louras geladas... =/
         –   Densidade Magnética
             ●   Coerção
             ●   Histeresys
         –   Velocidade Angular “constante” versus
             Velocidade Linear “constante”
             ●   (Constante, o escambau! O motor não é estável...)
         –   Largura de Banda
         –   Desgaste físico!
                                                                     27/89




O mundo analogico não é “limpo”.

Da mesma forma que pra toda ação corresponde
 uma reação, para cada atitude temos um efeito
 colateral que precisa ser considerado.

Quanto mais densa a mídia magnética, mais coerção
 eletromagnética você sofre, demandando mais
 energia no cabeçote ou menor velodicade de
 rotação (ou ambos).

A histerese é outro problema, pois ela dá um “delay”
  no tempo necessário para se transmitir a energia
  no meio ferro-magnético – e ainda deixa resíduo
  para quem vem atrás.

Ajustar a velocidade do motor é equilibrar este
  castelo de cartas, está mais para magia negra que
  engenharia. :-)
Discos Magnéticos
●   As trilhas não têm todas o mesmo tamanho físico.
    –   Perímetro é função do raio!
●   Mas tem o mesmo tamanho lógico...
    –   Velocidade angular constante
        ●   Densidade dos dados varia em função da trilha
●   Pragmatismo
    –   A Shugart ajustou o mecanismo para ser confiável na trilha
        mais interna, e desperdiçou densidade nas mais externas
    –   Drives mais sofisticados (e caros) variam a velocidade do
        motor em função da trilha
        ●   aproveitar melhor a densidade da mídia

                                                                    28/89
Discos Magnéticos
         ●   Os dados são gravados (re)alinhando polaridade na
             superfície da camada de óxido de ferro
             –   Descobriu-se não ser eficiente usar uma polaridade para o bit 1,
                 e outra para o bit 0
                 ●   Mudança de polaridade na linha do tempo indica bit 1
                 ●   Não mudança de polaridade na linha do tempo indica bit 0
         ●   Mas o motor não consegue fornecer uma velocidade
             constante ao nível do microsegundo
             –   Pequenas variações no motor “distorcem” o comprimento de um
                 bit
             –   Dada uma distância longa o suficiente sem inversão de
                 polaridade, o hardware não sabe mais quantos bits '0' foram
                 lidos... 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ?
                 ●   As inversões de fase, então, são usadas como “clock” para a leitura dos
                     dados
                                                                                          29/89




●Logo, não posso gravar qualquer byte no disco, pois algumas combinações de bits não
   são legíveis
   ●   Boa parte dos bits são “desperdiçados”, pois têm que ficar obrigatoriamente em '1'
       ●  Para gerar a inversão de fase, que serve de clock para a identificação dos
             bits...
●Codificações usadas pela indústria:

   ●   GCR – Group Code Recording
       ●  Adotada pelo Apple
          ●  Originalmente, a interface Disk II não conseguia ler dois bits '0' seguidos
             ●   Codificação 5x3 – 5 bits de dados intercalados com 3 bits '1' de clock
          ●  Numa revisão posterior do hardware, o hardware passou a ser capaz de
                 detectar 2 bits 0 seguidos (mas apenas uma vez por byte)
             ●   Codificação 6x2 – 6 bits de dados intercalados com 2 bits '1' de clock,
   ●   MFM – Modified Frequency Modulation
   ●   RLL - Run Lenght Limited
   ●   EFM – Eight to Fourteen Modulation
   ●   Outras
Discos Magnéticos
●   Mas isto tudo foi problema da Shugart!
    –   E do Woz...
        ●   E do Langhton!
             –   Quem? :-)
●   Qual foi o meu problema?
    –   32 * 1 / 1.023 MHz
        ●   0,0000031280547409579667644183773216031 Segundos
        ●   É o tempo que se tem para ler um raw byte do disquete, salvar
            na memória e estar pronto para ler o próximo!
        ●   3196 a 12787 bytes lidos a cada piscar de olhos
             –   E eu só preciso perder UM para causar o infame I/O Error!


                                                                             30/89
Discos Magnéticos




1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ?
             32 T states
                                  31/89
Algoritmos de Tempo Real
           ●   Quediaboéisso?
               –   São algoritmos em que o tempo de resposta faz parte do
                   resultado do processamento
                   ●
                       Não é o mesmo que “fazer rapidinho”
                        –   “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo.
                        –   “Entregar” antes do prazo é desperdício de processamento
           ●   E o Kiko? Kiko'eu tenho a ver com isto?
               –   Acessar disco é uma tarefa de tempo real
                   ●
                       Missão Crítica!
               –   Computadores modernos possui um micro controlador
                   especializado para lidar com disco
                   ●   O Apple II não.
                        –   Welcome to hell...

                                                                                                       32/89




●Quediaboéisso?
   ●  São algoritmos em que o tempo de resposta faz parte do resultado do
         processamento
      ●  Não é o mesmo que “fazer rapidinho”
         ●  Um determiado processamento pode precisar ficar pronto só em 24 horas
         ●  Ou 24 milisegundos...
      ●  “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo.
      ●  “Entregar” antes do prazo é desperdício de processamento
         ●  Que pode ser necessário para entregar outra tarefa que está vencendo
                antes
●E o Kiko? Kiko'eu tenho a ver com isto?

   ●  Acessar disco é uma tarefa de tempo real
      ●  Missão Crítica!
         ●  Se você não ler a porta de I/O no milisegundo correto, você não leu nada.
         ●  Se você não gravar na porta de I/O no millisegundo adequado, você
                destruiu os dados que estavam no disquete!
   ●  Computadores modernos possui um micro controlador especializado para lidar
         com disco
      ●  O Apple II não.
         ●  Welcome to hell...
Tá ficando complicado




                        33/89
Reavaliação
●   Riscos
    –   Gravar setores dá mais trabalho que ler
        ●   E eu nem tinha certeza de que iria conseguir ler...
    –   Não vou conseguir fazer tudo!
        ●   Muitas diferenças entre cada target, praticamente um
            software diferente pra cada um
●   Prioridades
    –   BOOT eficiente
    –   Carga rápida de Binários
    –   Serviços (mínimos) de diretório
    –   (nice) API
        ●   Sólida
    –   Abrir mão da memória extra, e focar na principal
        ●   E economizar onde der
                                                                   34/89
Reação
●   Começar prototipando as rotinas básicas de disco
    –   Se eu não estabilizar a rotina de leitura de setores, o resto
        não serve de nada
    –   Um terço do esforço total do projeto foi gasto só nelas
●   Redução de escopo
    –   Serviços de “Console I/O” pelo Kernel :-|
    –   Cache de disco (em especial, do CATALOG) :-|
    –   Gravação de Dados ¬¬
    –   Gerenciamento da memória ¬¬
    –   Relocação em memória X-(
    –   Suporte à programas BASIC X-(
                                                                        35/89
Resolução
         ●   “Internalizar” algumas funções da ROM para o S.O.
             –   Não sem conseqüências... ¬¬
         ●   Delegar à aplicação gerenciar o resto do hardware
             –   O S.O. identifica para você a máquina em que está rodando
             –   “Bibliotecas” padrão no “User Space”
             –   E cada um que se vire!
         ●   BASIC.SYSTEM
             –   Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no
                 User Space.
         ●
             “Forkar” o Kernel para casos especiais
             –   Versões especializadas para cada arquitetura e/ou funcionalidade
                 específica
             –   Gerência de Configuração to the rescue! :-)
                                                                                    36/89




●“Internalizar” algumas funções da ROM para o S.O.
    ●  Me livrou de dependências externas
       ●   Comeu uns bytes preciosos
       ●   Mas viabilizou um binário único para todas as plataformas
    ●  Facilitará aproveitar as extensões de memória no futuro
●Delegar à aplicação gerenciar o resto do hardware

    ●  O S.O. identifica para você a máquina em que está rodando
    ●  “Bibliotecas” padrão no “User Space”
    ●  E cada um que se vire!
●BASIC.SYSTEM

    ●  Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no User
           Space.
●“Forkar” o Kernel para casos especiais

    ●  Versões especializadas para cada arquitetura e/ou funcionalidade específica
       ●   Versionar a API
       ●   Congelar um subset mínimo da API com garantias de funcionamento em todas
              as versões futuras
       ●   Oferecer à aplicação um mecanismo para que ela saiba o que o Kernel
              corrente é capaz de oferecer
    ●  Gerência de Configuração to the rescue! :-)
E o inesperado
                                      (porque todo castigo...)

     ●   O uso da Página Zero me mordeu o traseiro.
         –   Feio. :-(
         –   Quase assassinou o projeto no berço
              ●   Quando a R*TS não matava o resto da máquina, o resto da máquina
                  matava a R*TS
              ●   Cerca de 20% do esforço de desenvolvimento foi gasto mapeando e
                  documentando, corretamente, o uso da Z.P.
                   –   No TK-2000 e no Apple II
                   –   Um esforço com o qual eu não contava
         –   Não havia mais o que fazer exceto desistir ou pagar o pato e
             seguir adiante
              ●   5 dias de trabalho indo pelo ralo.
                   –   E as férias, digo, o prazo acabando! =]
              ●   A única documentação formal do projeto.
                                                                                37/89




Único momento em que tive vontade de desistir

Impotência, meus esforços submetidos à forças que
  das quais não tenho controle.

Mas depois que passou a depressão (e a ressaca),
 umas 80 horas =P foram suficientes para mapear
 quais endereços podiam ser usados pela CB2k.

Ver o programa zp_profile , nos discos de testes da
 CB2k (em attic, no reposítório)
; Depends on rwts.def.
     ; Updates zp_profile.s
     ;                                             Apple II Zero Page Usage
     ;
     ;                                             Lo Nibble of Address
     ;     Hi
     ;     Nib 0      1     2      3      4     5      6     7    8     9   A    B    C     D     E     F
     ;      ----- ----- ------ ------ ----- ------ ----- ---- ---- ---- ---- ---- ----- ----- ----- -----
     ;      0 | A~    A~    A      A      A     A      -     -    -     -   A    A    A     AI    A     A
     ;      1 | A     A     A      A      A     A      A     A    A     A   A    A    A     A     -     M*
     ;      2 | M     M     M      M      M3    M      MA3   MA3 M3     M3  M3   M3   MA3   MA3   M3    MA3
     ;      3 | MA    M     MA     MA3    M     M3     M3B   M3B M3B M3B M~      M~   MA3~^ MA3~^ MA3~^ MA3~^
     ;      4 | M3~+^ M3~+^ M3~@^ M3~@^ M3~@^ M3~@     M3~   M3~ M3~ M3~ I3~ I3~ I3~        I3~   M~@# M@#
     ;      5 | MA    MA    MA     MA     MA*   MAI*   AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
     ;      6 | AI+   AI+   AI@    AI@    AI@   AI@    AI@# AI3 AI3 AI3 AI3 AI        AI    AI    AI    AI3
     ;      7 | AI3   AI    AI     AI3    AI3   AI     AI3   AI   AI    AI  AI   AI   AI    AI    AI    AI
     ;      8 | AI    AI    AI     AI     AI    AI     AI    AI@ AI@ AI     AI   AI   AI    AI    AI    AI
     ;      9 | AI    AI    AI     AI     AI    AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
     ;      A | AI    AI    AI     AI     AI    AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI3
     ;      B | AI3   AI    AI     AI     AI    AI     AI    AI   AI    AI  AI   AI   AI    AI    AI    AI
     ;      C | AI    AI    AI     AI     AI    AI     AI    AI   AI    AI  AI3 AI3 AI3     AI3   I#    I#
     ;      D | AI    AI    AI     AI     AI    AI     AI3   I!   AI3 AI3 AI     AI   AI    AI    AI3   AI
     ;      E | A     A     A      A      A     A      A     A    A     A   A    ?    -     -     -     -
     ;      F | A     A     A      A      A     A      A     A    A     A   -    -    -     -     Ik    AI
     ;
     ;
     ;     M = Used by Monitor; * used in early Apple IIe ROMs-- now free
     ;     A = Used by Applesoft BASIC
     ;     I = Used by Integer BASIC
     ;     3 = Used by DOS 3.3
     ;     ~ = Used by ProDOS ($40-$4E is saved before and restored after use)
     ;     B = Used by ProDOS BASIC.SYSTEM (also uses all Applesoft locations)
     ;     - = Free; not used
     ;
     ;     k = Used by TK-2000 / MPF-II
     ;
     ;     + = RWTS, Comunicação com "Cliente"
     ;     @ = RWTS, Conteúdo descartável.
     ;     ! = RWTS, Posição Chave: não pode ser mudada nem destruída!
     ;
     ;     ^ = CompatiBoot 2k, Comunicação com "Cliente"
     ;     # = CompatiBoot 2K, Conteúdo descartável.
     ;     ? = CompatiBoot 2K, Posição Chave: não pode ser mudada nem destruída!
     ;
     ;     --Bryan Dunphy, Michael J. Mahon, Rubywand, CompatiBoot 2k
                                                                                                                38/89




Vale comentar que sem os esforços de dois outros
 caras da Scene mundial, as 80 hora de pesquisa
 facilmente se transformariam nas 300 do projeto
 inteiro!
E quando tudo o mais falhar...




                   “How many times do I have to tell you,
                          the right tool for the right job!”
                                       Montgomery Scott (Scotty)
                      Chief Engineer, NCC-1701-A USS Enterprise
                                                                   39/89




Aquela ferramenta mágica que resolve todos os
 problemas! ;-)

Pausa rápida para comentários.

Aqui encerram-se as lamúrias :-), e começa a se
 descrever os problemas que foram resolvidos.

Para então descrever as soluções.
Anatomia de um
                    Disquete




                                      40/89




Trilhas concentricas, blablabla :-)
Anatomia de um
                                                              Disquete
                                                         35 Trilhas
                              0         1         2                   …                           35
                                                                                                       Address Field
                            gapzão    gapzão    gapzão                                          gapzão
                                                                                                                14
                            Addr_0    Addr_0    Addr_0                3              2            Addr_0
                                                                                                       2                 2               2              3
                             gap       gap       gap               Prologo       Volume            gap
                                                                                                    Track             Sector         Chk Sum         Epilogo
                             Data      Data      Data            'D5 AA 96   '4 & 4 encoding   '4 & 4 encoding '4 & 4 encoding
                                                                                                   Data                          '4 & 4 encoding   'DE AA EB
    =4096 bytes (lógicos)



                             gap       gap       gap                                               gap
                            Addr_1    Addr_1    Addr_1                                            Addr_1
      ~48000 bits (raw)




                             gap       gap       gap                                               gap Data Field
                             Data      Data      Data                                              Data        349
                             gap       gap       gap                 3                             gap
                                                                                                     342                               1                3
                            Addr_2    Addr_2    Addr_2            Prologo                         Addr_2
                                                                                                     Data                           ChkSum           Epilogo
                             gap       gap       gap            'D5 AA AD                      6 & gap
                                                                                                    2 encoding                        'XX          'DE AA EB
                             Data      Data      Data                                              Data
                             gap       gap       gap                                               gap
                            Addr_3    Addr_3    Addr_3                …         “gapzãp”          Addr_3“Self Sync bytes”             gap
                             gap       gap       gap                             48 a 100          gap                               5 a 60
                             Data      Data      Data                         'FF FF FF …          Data 1 1 1 1 1 1 1 0 0
                                                                                                       '1                          'FF FF FF
                             gap       gap       gap                                               gap
                            Addr_4    Addr_4    Addr_4                                            Addr_4
                             gap       gap       gap                                               gap
                             Data      Data      Data                                              Data
                             gap       gap       gap                                               gap


                              …         …         …                                                …


                            Addr_15   Addr_15   Addr_15                                         Addr_15
                              gap       gap       gap                                             gap
                             Data      Data      Data                                            Data


                                                                                                                                                    41/89




Raw bytes , logical bytes (payload).

What you see is not what you get! ;-)
Anatomia de um
                                        Disco DOS 3.3
         Disk                                                  Trilha
                   0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
              0    0                                               1A 15 31 47 62 78 0 15 23    102 109 116 120

              1    8                                                0 16 32 48 63 79 1 16 24    103 110 117 121

              2    1                            1                   1 17 33 49 64 80 2 17 25    104 111 118 122

              3    9                                                2 18 34 50 65 81 3 18 26    105 112 119   1B
              4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
              5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
              6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
      Setor




              7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
              8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
              9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
              10   5                                                9 25 41 57 72 88 10 95   99 106 113   60 126
              11 13                         6                      10 26 42 58 73 89 11 96 100 107 114 61 127
              12   6                                             4 11 27 43 59 74 90 12 97 101 108 115 62 127
              13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
              14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
              15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65

                                                                                                                   42/89




Breve exemplo de 4 arquivos num disquete.

Notar que a ordem dos setores foi “simplificada” para melhorar a
  didática, a ordem correta está na trilha zero

Notar que são necessárias 2 rotações para ler uma trilha inteira,
  pela ordenação do DOS

As trilhas 1 e 2 estão livres na CB2k, mas não com o DOS

Setor de Boot (T0,S0)

Tabela de alocação (T17, S0)

Catalogo (T17, o resto)
       4 Arquivos (notar que não é 1 arquivo por setor!)

Track/Sector List
Boot
●   Power On RESET
    –   RESET Vector
●   Autostart ROM (BOOT 0)
    –   Busca por uma placa DISK II na ROM de expansão
●   BOOT 1 (second stage)
    –   Trilha 0, Setor 0
    –   L-Boot1
●   BOOT 2 (third stage)
    –   Sistema Operacional
        Ou outro payload qualquer...


                                                         43/89
A L-Boot1
●   Fornece a melhor performance possível para carga
    sequêncial
    –   Multi trilha
●   Serviços independentes de “plataforma”
    –   Impressão em tela
    –   Carga de setores
    –   Descompressão de dados
●   Também foi usada com sucesso:
    –   Boot do TK-DOS 3.3
    –   Boot do Apple DOS 3.3
    –   Jogos stand-alone
                                                       44/89
Finalmente: CB2k
             ●   R*TS
             ●   Kernel
                 –   Serviços de Diretório
                 –   Serviços “Raw Files”
                 –   Serviços Binary Files
                 –   Serviços de House Keeping




                                                                                          45/89




Kernel:
Quem coordena toda esta bagunça

É quem dá cara à CB2k

Diretório:
             Mínimos
             Não liga pra nome de arquivo, o que interessa é o índice relativo dele.
             0, 1, 2, etc.

RAW Files:
             Notar que é a única parte da CB2k que:
                     É responsável pela alta performance ao acesso ao disco
                     Aliás, é a única parte que faz acesso ao disco
             Granularidade: um setor
                     256 bytes, para DOS 3.3
                     Impossível acessar qualquer informação sem ser por múltiplos de um setor
             Acesso sequencial ou randômico
                     Endereçamento por setor relativo

             Teoricamente pode ser substituída por qualquer outra coisa, como:
                    Acessar HD
                    Acessar servidor de arquivos em REDE
                    Raios, telepatia que seja! :-)

BIN Files:
Especialização do Raw Files
           Permite carregar arquivos cujo tamanho não seja múltiplo de um setor
           Resguarda memória adjascente
           Não tem acesso parcial, é tudo ou nada.

House Keeping:
          Identificação da Máquina
          Relocação dos buffers
          Configuração dos handlers
                   Exceção
                   Reset
O Inferno das Entry-Points
       00B3D5 2                KERNEL__ADDR_START:
       00B3D5 2                        ; Prevents accidental running
       00B3D5 2 00                     BRK
       00B3D6 2 1E                     .byte    __WARM_BOOT - __KERNEL_SERVICES_TABLE
       00B3D7 2
       00B3D7 2                __KERNEL_SERVICES_TABLE:
       00B3D7 2 F8 B3                  .word    __PANIC
       00B3D9 2 59 B5                  .word    KERNEL_SYSTEM_IDENTIFICATION
       00B3DB 2 F4 B8                  .word    KERNEL_FILE_LOAD
       00B3DD 2 21 B9                  .word    KERNEL_FILE_RUN
       00B3DF 2 61 B5                  .word    KERNEL_SESSION_FINISH
       00B3E1 2 10 B6                  .word    KERNEL_CATALOG_ENTRY_SET
       00B3E3 2 33 B6                  .word    KERNEL_CATALOG_ENTRY_QUERY
       00B3E5 2 92 B6                  .word    KERNEL_CATALOG_ENTRY_GET
       00B3E7 2 F7 B6                  .word    KERNEL_RAWFILE_SEEK
       00B3E9 2 82 B7                  .word    KERNEL_RAWFILE_READ
       00B3EB 2 23 B5                  .word    KERNEL_HANDLER_SET
       00B3ED 2 9E B5                  .word    KERNEL_CONFIGURATION_SET
       00B3EF 2 DB B5                  .word    KERNEL_CONFIGURATION_GET
       00B3F1 2 F9 B4                  .word    KERNEL_SECTOR_READ
       00B3F3 2 F5 B3                  .word    __WARM_BOOT
       00B3F5 2                __KERNEL_SERVICES_TABLE_end:
       00B3F5 2
       00B3F5 2                __WARM_BOOT:
       00B3F5 2 4C 5A BA               jmp      KERNEL__WARMBOOT
       00B3F8 2
       00B3F8 2                __PANIC:
       00B3F8 2                        ; System is unstable. The next reset will reboot from the
       same slot the CB2K was rebooted last time.
       00B3F8 2 20 9D BA               jsr      KERNEL__HW_RESET_HANDLER_REBOOT_SET
       00B3FB 2 A9 80                  lda      #KERNEL_ERR_PANIC
       00B3FD 2 A6 EB                  ldx      KERNEL_SUPERVISOR__STACKPOINT                 46/89




Ao passo que o kernel cresce, os pontos de entrada das rotinas
  mudam de endereço.

Não é problema para o kernel, o Linker automaticamente faz as
  correções

Mas como os clientes vão se virar? Não é razoável recompilar todos
  os aplicativos a cada vez que muda a versão do kernel!

O DOS 3.3 cagou pro problema.
       ProntoDOS e DiversiDOS precisaram fazer malabarismos pra
  reusar os entry-points conhecidos.
       Que nem eram oficiais

ProDOS criou uma chamada fixa em $BF00. Dali em diante tudo podia
  mudar, mas a entry-point oferecia uma interface padrão.
       Foi minha abordagem inicial, mas oferecia um problema: eu
  queria ser capaz de mover o Kernel inteiro pra cima ou pra baixo de
  acordo com a conveniência do momento, não podia amarrar um
  endereço de entry-point
       A entry point então iria estar registrada num endereço da
  página 0 (como se as coisas lá já não estivessem complicadas!).
O Supervisor
         ●   A instrução mágica
              –    BRK
         KERNEL_SUPERVISOR:
                   cli        ; Desativamos interrupções.
                              ; O Kernel não sabe ser interrompido, e a R*TS *NÃO PODE* ser interrompida!
                              ; A RTI abaixo restaurará o Status, e se a IRQ estava ativada, ela voltará a
         estar.

         .ifndef   LANGUAGE_CARD
                   jsr       MON_RESTORE              ;   Pois é... A ROM do Apple IIe faz o favor de,
                                                      ;   trabalho fodástico de resetar o estado da
                                                      ;   anterior para permitir restauro!), tirar da
                                                      ;   (o que eu não queria), e *não manter* o
                                                      ;   virtualmente fodendo com o conceito de
                                                      ;
                                                      ;   TODO: Mover a CB2K para Language Card, escrever
         .endif
                   jsr        __SAVE_THE_WORLD

                   ldx        KERNEL_SUPERVISOR__STACKPOINT ; O Supervisor *NÃO É* reentrante.
                   bne        @PANIC

                   lda        __REG_P
                   and        #%00010000              ; Checa se o BRK STATUS está ativo
                   beq        @PANIC                  ; Se não está, a máquina tá despirocada e o PC caiu
                                                      ; aqui por acidente!
                                                                                                            47/89




CP/M e MS-DOS foram por este caminho.

Usar as interrupções de software para fazer o serviço.

O Kernel pode ir pra onde quiser, contanto que ele ajuste o vetor
  de interrupção para seu handler interno ao mudar de endereço.

Clean.

Lean.

Lindo! :-)

Absolutamente nenhum problema de linkagem estática

Mas é um mecanismo um pouquinho caro para se usar em
 bibliotecas
A (nice) API
       .define VERSION_MAJOR 1
       .define VERSION_MINOR 1
       .define VERSION_RELEASE   "2012.0901"

       .macro SYS syscall
           BRK
           .byte   syscall
       .endmacro
           ; This two entries are garanteed to never change or be renamed!
           CB2K_SYSTEM_PANIC             := 0
           CB2K_SYSTEM_IDENTIFICATION    := 2 + CB2K_SYSTEM_PANIC

           ; The following entries can, but is unlikely to, change on MAJOR versions.
           CB2K_FILE_LOAD                := 2 + CB2K_SYSTEM_IDENTIFICATION
           CB2K_FILE_RUN                 := 2 + CB2K_FILE_LOAD
           CB2K_FINISH                   := 2 + CB2K_FILE_RUN
           CB2K_FILE_SET                 := 2 + CB2K_FINISH
           CB2K_FILE_QUERY               := 2 + CB2K_FILE_SET
           CB2K_FILE_GET                 := 2 + CB2K_FILE_QUERY
           CB2K_RAWFILE_SEEK             := 2 + CB2K_FILE_GET
           CB2K_RAWFILE_READ             := 2 + CB2K_RAWFILE_SEEK
           CB2K_HANDLER_SET              := 2 + CB2K_RAWFILE_READ
           CB2K_CONFIGURATION_SET        := 2 + CB2K_HANDLER_SET
           CB2K_CONFIGURATION_GET        := 2 + CB2K_CONFIGURATION_SET
           CB2K_SECTOR_READ              := 2 + CB2K_CONFIGURATION_GET

           ; The following entries (if any) can be added on MINOR versions
           ; CB2K_FUTURE_EXPANSION       := 2 + CB2K_SECTOR_READ
                                                                                   48/89




E finalmente, a cara da CB2k para seus clientes.
Resultados
       ●   Footprint 3.75Kbytes
           –   Kernel, R*TS, Supervisor, buffers, tudo!
           –   E os buffers ainda são configuráveis (on the fly)
       ●   Melhor performance
           –   6 a 7 Kbytes/s – próximo do limite operacional do dispositivo
       ●   Usa discos formatados pelo Apple DOS 3.3
           –   Até o FID pode ser usado para povoar seus discos
               ●   Mas eu recomendo o CiderPress. :-)
       ●   Aplicações
           –   Game Loaders
           –   Demos
           –   Outros
                                                                               49/89




●Footprint 3.75Kbytes
  ●  Kernel, R*TS, Supervisor, buffers, tudo!
  ●  E os buffers ainda são configuráveis
     ● Você pode movê-los on the fly durante a execução do seu
          programa, caso precise justamente daqueles endereços
          num determinado momento
●Melhor performance

  ●  6 a 7 Kbytes/s – próximo do limite operacional do dispositivo
●CATALOG

  ●  Usa discos formatado pelo Apple DOS 3.3
     ● Até o FID pode ser usado para povoar seus discos
     ● Mas eu recomendo o CiderPress. :-)
●Aplicações

  ●  Beautiful Boot
  ●  Game Loaders
     ● Karateka do TK-2000
     ● Loader para jogos grandes no TK-2000
Resultados
      ●   Benchmark TK-2000
          –   Tempo entre ligar a máquina (com o disquete já no drive) e o Prompt
              do Applesoft :
              ●   DOS: ~31 Segundos (!!!!)
              ●   CB2k: 6 segundos
              ●   DOS + LBoot1: 7 segundos (!!!!)
          –   Tempo para carregar uma tela HGR:
              ●   DOS: 10 segundos
              ●
                  CB2k: 4 segundos
          –   Espaço livre na RAM (MEMTOP - $800):
              ●   DOS: $9600 - $800 = $8E00 = 35.5Kb
              ●
                  CB2k: $B000 - $800 = $A800 = 42Kb
      ●   Mas convêm lembrar:
          –   A CB2k faz pouca coisa mais que carregar binários
                                                                               50/89




E é possível aumentar em ¾ de kbyte a memória
  livre movendo os buffers para posições de
  memória alternativas
       Mas isto é altamente dependente de máquina]
          No TK-2000 eu tenho algumas boas
  oportunidades


(I know how to cook or what?)
Por que o DOS é tão lento?

      ●   Os “raw sectors” (342 bytes físicos) são lidos
          para um buffer intermediário
      ●   Este buffer é então decodificado para os 256
          bytes de dados, em um buffer auxiliar
      ●   Estes dados são, finalmente, copiados para o
          buffer de I/O para leitura pelo programa
          BASIC ou para a memória destino, se binário
      ●   E o disco continua virando

                                                           51/89




●Os “raw sectors” (342 bytes físicos) são lidos para
  um buffer intermediário
●Este buffer é então decodificado para os 256 bytes

  de dados, em um buffer auxiliar
●Estes dados são, finalmente, copiados para o buffer

  de I/O para leitura pelo programa BASIC ou para a
  memória destino, se binário
●Como o disco continua virando, até o DOS poder ler

  novamente um setor, já pode ter passado vários
  (no mínimo 1) debaixo do cabeçote (incluindo,
  talvez, o que deveria ser o próximo setor lógico)
  ● De forma que poderia ser necessário esperar a

      trilha “dar a volta” para ler o próximo setor
      desejado
  ● Por esta razão existe o tal do Skewing

    ● os setores físicos eram remapeados para

         setores lógicos, e estes últimos eram
         endereçados pelo DOS na Track/Sector List
DOS:
                                      Modus Operandi
        Disk                                                  Trilha
                  0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
             0    0                                               1A 15 31 47 62 78 0 15 23    102 109 116 120

             1    8                                                0 16 32 48 63 79 1 16 24    103 110 117 121

             2    1                            1                   1 17 33 49 64 80 2 17 25    104 111 118 122

             3    9                                                2 18 34 50 65 81 3 18 26    105 112 119   1B
             4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
             5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
             6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
     Setor




             7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
             8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
             9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
             10   5                                                9 25 41 57 72 88 10 95   99 106 113   60 126
             11 13                         6                      10 26 42 58 73 89 11 96 100 107 114 61 127
             12   6                                             4 11 27 43 59 74 90 12 97 101 108 115 62 127
             13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
             14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
             15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65
                                                                                                                  52/89




Mover o cabeçote é um evento traumático para o
 drive, ele leva centenas de millisegudos para se
 recuperar, estabilizar a leitura do cabeçote e voltar
 a ler dados.

Se eu estou lendo sequencialmente, ao mover o
 cabeçote o drive fica “cego” por algus setores – de
 forma que é inevitável que eu perca a seqüência e
 precise esperar a trilha dar uma volta inteira para
 recomeçar a ler (ver a área 'cega', esbranquiçada,
 no desenho acima.

Esta insistência em ler os setores em seqüência
 também causa delays desnecessários quando os
 arquivos estão espalhados
E por que a R*TS ficou tão
                          “rápida”?
      ●   Os raw sectors são decodificados on the fly, indo diretamente para a
          memória a que se destinam
          –   Sem buffers intermediários, sem memory moves
          –   Exceto o primeiro e o último setor de arquivos binários, que são carregados
              num buffer de I/O e então copiados para o target para não sobrescrever
              memória limítrofe
              ●   Era o mais perverso efeito colateral da CompatiBoot original, diga-se de passagem
      ●   Ela não espera pelo próximo setor, mas monta uma lista dos setores
          desejados e vai carregando na medida em que eles passam debaixo
          do cabeçote
          –   Não há espera pelo “próximo setor”
          –   Os gap bytes me dão tempo suficiente para recomeçar a leitura entre o fim de
              um setor e o começo do outro
          –   Mesmo o pior caso leva apenas uma revolução do disquete para ser lido.


                                                                                                      53/89




●O DOS foi o PRIMEIRO sistema operacional de
  disco para Micro Computadores
  ● Nunca ninguém havia feito isto antes!

  ● O único “concorrente” funcionava em

       mainframes, e tinha megabytes de tamanho
     ● O Apple DOS tinha menos de 10 Kbytes...

●Todos os erros ainda estavam por ser cometidos

  ● Os melhores videntes não sabem programar

  ● Os programadores insistem em usar teclados, e

       não bolas de cristal...
●Dificuldades técnicas inerentes ao período

  ● Os binários eram alimentados na máquina de

       desenvolvimento usado fita perfurada
     ● Usando um hardware feito à mão pelo Woz

  ● Ao menos eu tinha um PC com emulador para

       testar a bagaça
     ● Mas usei a porta cassete na hora de testar no

         bares metal! =P
CB2k:
                                       Modus Operandi
         Disk                                                  Trilha
                   0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
              0    0                                               1A 15 31 47 62 78 0 15 23    102 109 116 120

              1    8                                                0 16 32 48 63 79 1 16 24    103 110 117 121

              2    1                            1                   1 17 33 49 64 80 2 17 25    104 111 118 122

              3    9                                                2 18 34 50 65 81 3 18 26    105 112 119   1B
              4    2                    8                           3 19 35 51 66 82 4 19 27 36 45 54 123
              5    10                               3               4 20 36 52 67 83 5 3 28 37 46 55 124
              6    3                    10 5                        5 21 37 53 68 84 6 0 29 38 47 56 124
      Setor




              7    11                               2               6 22 38 54 69 85 7 1 30 39 48 57 125
              8    4               4    9                           7 23 39 55 70 86 8 2 31 40 49 58 125
              9    12                           4                   8 24 40 56 71 87 9 20 32 41 50 59 126
              10   5                                                9 25 41 57 72 88 10 95   99 106 113   60 126
              11 13                         6                      10 26 42 58 73 89 11 96 100 107 114 61 127
              12   6                                             4 11 27 43 59 74 90 12 97 101 108 115 62 127
              13 14                     7                        3 12 28 44 60 75 91 13 21 33 42 51 63
              14   7                                             2 13 29 45 2 76 92 14 22 34 43 52 64
              15 15                                              1 14 30 46 61 77 93 94 98 35 44 53 65
                                                                                                                   54/89




A CB2k não espera por um setor, mas faz uma lista dos setores
  desejados para cada trilha.

Quando a mudança de trilha estabiliza, para cada setor que passa
  no cabeçote eu checo se ele tá na wish-list. Se estivar, ele é lido
  e ponto final.

Quando a wish-list tá vazia, é hora de trocar de trilha e o processo
  recomeça.

Não há esperas por um setor específico – todos os setores
  desejados vão, eventualmente, aparecer debaixo do cabeçote.

As rotinas de leitura de setores serem otimizadas também ajudam,
  pois eu sou capaz de ser setores contínuamente (sem precisar
  de pausas para decodificar nada). Então, além da otimização
  acima, eu sou capaz de ler uma trilha em apenas uma revolução
  – poi eu sou capaz de ler 16 setores continuos.
Mas então...
      ●   Por que não consertaram antes?
          –   Consertaram!
              ●   Apple
                   –   ProDOS
              ●   Terceiros
                   –   ProntoDOS
                   –   DiversiDOS
                   –   CP/M
          –   Mas nenhum deles foi portado para o TK-2000!
              ●   CB2k! :-)
          –   Nem implementaram leitura múltipla!
              ●   CB2k! ;-)



                                                             55/89




Em condições normais de uso (que efetivamente acontecia
 na época), os arquvos tendem a se fragmentar com o
 tempo, se aproximando gradativamente ao pior caso do
 exemplo dado.

A CB2k se aproveita de uma particularidade dos tempos
  modernos: os disquetes não são mais usados para
  trabalhos ordinários – mas sim para uma função
  específica e normalmente read/only – no nosso caso,
  armazerar e carregar jogos.

As extreme optimizations da CB2k não renderiam os
  mesmos benefícios num ambiente “normal”, e
  aumentaria em muito a complexidade (e o risco de erros)
  nas demais rotinas de um Sistema Operacional comum

O que o Dick Vigarista tá fazendo aí? ;-)
      Breve histórico da Apple patinando com o Apple III
  enquanto deixava o Apple II à míngua.
Hands on




                             56/89




Finalmente! :-)
Check List
      ●   Café                        ●   Instruções de onde baixar e
                                          como instalar:
      ●   Salgadinhos                     –   MINGW
                                          –   CC65
      ●   Daft Punk na                    –   CiderPress
          vitrolinha :-)                  –   AppleWin
      ●   Estes Slides                    –   Emulador TK2000
                                      ●   Os fontes do Hello Word
      ●   Imagem de disco                 –   Leia o READ.ME ! ;-)
          da CB2k (1.1r4a:Set/2012)           ●   Instruções:
                                                   –   Para montagem do programa,
                                                   –   Importação do binário para uma
                                                       imagem de disquete
                                                   –   e execução em emulador.

                                                                                        57/89




Programar em ASM é fácil.

Mas da mesma forma que é difícil montar algo
 interessante com um LEGO de apenas 3
 bloquinhos, o mesmo acontece quando você tem
 só 3 registradores: você precisa rebolar pra realizar
 as tarefas de pouquinho em pouquinho.

A CB2k por sua vez também ajuda – as tarefas
  básicas ganharam rotinas prontas (o fato de tais
  rotinas saberem sozinhas quando estão num TK-
  2000 ou num Apple também ajuda um bocado!).

Este Hello World pode ser compreendido por um
 leigo no assunto em meia hora, sério.

Você vai gastar mais tempo baixando e instalando o
 ambiente de produção que aprendendo como
 funciona o Hello World.
Hello World
          .setcpu      "6502"                         :    lda           (PRINT_DATA),y
          .localchar   '@'                                 beq           :+
                                                           jsr           PRINT_ASCII
          .include "../hw.def"                             iny
          .include "../sys.def"                            bne           :-
          .include "../bios.def"                           inc           PRINT_DATA+1
                                                           bne           :-
          .include "../CB2k.def"                      :
                                                           jsr           ANYKEY
          .include "system.def"                            jsr           SYSTEM_HGR
                                                           SYS           CB2K_FILE_LOAD
          .org $800                                        jsr           ANYKEY

                                                      NO_FUN:
    jsr        SYSTEM_INIT                                  jmp          SYSTEM_APPLESOFT_START_COLD

    ldy        #CB2K_HANDLER_ERROR                    ANYKEY:
    lda        #<NO_FUN                                     PRINT        ANYKEY_TEXT
    ldx        #>NO_FUN                                     jmp          MON_RDKEY
    SYS        CB2K_HANDLER_SET
                                                      HEADER:
:                                                     HEADER_line_0:
    PRINT HEADER                                            .byte 22,0
    dec         HEADER_line_1                               textz "============ Hello World !! ============"
    dec         HEADER_line_0                         HEADER_line_1:
    bmi         :+                                          .byte 23,0
    lda         #90                                         textz "                                        "
    jsr         MON_WAIT                                    .byte 1,0,0
    beq         :-                 ; Branch always!         .byte -1
:
                                                      ANYKEY_TEXT:
    lda        #<MENSAGEM_TEXT                              .byte 23,0
    ldx        #>MENSAGEM_TEXT                              textz ":"
    sta        PRINT_DATA                                   .byte -1
    stx        PRINT_DATA+1
                                                           .include      "system.inc"
    ldy        #0
                                                      MENSAGEM_TEXT:
                                                            .include     "mensagem.txt"

                                                                                                        58/89
Hello World
          .setcpu      "6502"                                  :     lda         (PRINT_DATA),y
          .localchar   '@'                                           beq         :+
                                                                     jsr         PRINT_ASCII
          .include "../hw.def"                                       iny
          .include "../sys.def"                                      bne         :-
          .include "../bios.def"                                     inc         PRINT_DATA+1

          .include "../CB2k.def"
                                                ●     Configura dialeto do
                                                           :
                                                                     bne
                                                                      :-


                                                      processador SYSTEM_HGR
                                                              jsr     ANYKEY
          .include "system.def"                               jsr
                                                              SYS     CB2K_FILE_LOAD
          .org $800                                                  jsr         ANYKEY


    jsr        SYSTEM_INIT
                                                ●     Configura prefixo para rótulos
                                                            NO_FUN:
                                                                  jmp SYSTEM_APPLESOFT_START_COLD

    ldy        #CB2K_HANDLER_ERROR
                                                      locaisANYKEY:
    lda        #<NO_FUN                                              PRINT       ANYKEY_TEXT
    ldx
    SYS
               #>NO_FUN
               CB2K_HANDLER_SET                 ●     Inclui HEADER:
                                                             cabeçalhos que
                                                                   jmp         MON_RDKEY


:
    PRINT HEADER                                      definem símbolos da
                                                             HEADER_line_0:
                                                                   .byte 22,0

                                                      plataforma 23,0
    dec         HEADER_line_1                                      textz "============ Hello World !! ============"
    dec         HEADER_line_0                                HEADER_line_1:
    bmi         :+                                                 .byte
    Lda         #90                                                  textz "                                      "


:
    jsr
    beq
                MON_WAIT
                :-
                                                ●
                                   ; Branch always!   Inclui o cabeçalho do Sistema
                                                                   .byte 1,0,0
                                                                   .byte -1


    lda        #<MENSAGEM_TEXT
                                                      Operacional 23,0
                                                             ANYKEY_TEXT:
                                                                   .byte
    ldx        #>MENSAGEM_TEXT                                       textz ":"
    sta
    stx
               PRINT_DATA
               PRINT_DATA+1                     ●     Inclui o cabeçalho da
                                                                   .byte -1

                                                                   .include "system.inc"
    ldy        #0
                                                      biblioteca de sistema
                                                             MENSAGEM_TEXT:
                                                                     .include    "mensagem.txt"

                                                                                                                59/89
Hello World
          .setcpu      "6502"                                  :    lda           (PRINT_DATA),y
          .localchar   '@'                                          beq           :+
                                                                    jsr           PRINT_ASCII
          .include "../hw.def"                                      iny
          .include "../sys.def"
          .include "../bios.def"
                                      ●   Onde começar o programa?  bne
                                                                    inc
                                                                                  :-
                                                                                  PRINT_DATA+1
                                                                    bne           :-
          .include "../CB2k.def"                               :

          .include "system.def"
                                          –   Qual o tamanho do binário?
                                                          jsr
                                                          jsr
                                                                ANYKEY
                                                                SYSTEM_HGR
                                                                    SYS           CB2K_FILE_LOAD
          .org $800                            ●   Difícil preverjsr
                                                                  antes de começar, não?
                                                                         ANYKEY

                                                               NO_FUN:
    jsr        SYSTEM_INIT                –   Usa gráficos?
                                                          jmp                     SYSTEM_APPLESOFT_START_COLD

    ldy        #CB2K_HANDLER_ERROR                             ANYKEY:
    lda
    ldx
               #<NO_FUN
               #>NO_FUN
                                               ●   Num Apple?        PRINT
                                                                     jmp
                                                                                  ANYKEY_TEXT
                                                                                  MON_RDKEY
    SYS        CB2K_HANDLER_SET                ●   Num TK-2000?
                                                         HEADER:
:                                                              HEADER_line_0:
    PRINT HEADER
    dec         HEADER_line_1
                                                      –   Mas o TK sempre usa gráficos! World
                                                                   .byte 22,0
                                                                   textz "============ Hello          !! ============"
    dec
    bmi
    lda
                HEADER_line_0
                :+
                #90
                                          –   Modo texto? .byte 23,0
                                                       HEADER_line_1:

                                                             textz "                                                "
    jsr         MON_WAIT                                            .byte 1,0,0
    beq         :-                              ●
                                   ; Branch always!Num Apple?.byte -1
:

    lda        #<MENSAGEM_TEXT
                                               ●   Num TK-2000? 23,0
                                                         ANYKEY_TEXT:
                                                               .byte
    ldx        #>MENSAGEM_TEXT                                      textz ":"
    sta        PRINT_DATA                             –   Mas o TK não tem modo texto!
                                                                   .byte -1
    stx        PRINT_DATA+1

    ldy        #0                     ●   Onde é que tá a CB2k mesmo?
                                                                    .include

                                                               MENSAGEM_TEXT:
                                                                                  "system.inc"


                                                                     .include     "mensagem.txt"

                                                                                                                  60/89
Hello World                                                          Bloco II/A
                                                                                                                                                                                                          $FFFF
         $0000              Zero Page                                                                                Zero Page                         Extra RAM
         $0100                Stack                                                                                    Stack                                            Bloco I
                                                                                                                                                                                          ROM
         $0200                                                                                                                 Bloco II/A P1          Bloco II/A P0   Extra RAM
                            I/O Buffer                                                                               I/O Buffer
                                                                                                                                                                                                          $D000

         $0300            Free RAM                                                                                    Free RAM
                        System Pointers                                                                             System Pointers
         $0400
                                                                                                                                                                                                          $C100
                             TEXT/GR                                                                                80TEXT/DGR                                                      Mem Map I/O           $C000
                              Page 1                                                                                   Page 1
                                                                                                                                                Bloco II/D




                                                  Sentiram
                                                                                                                                                Extra RAM
         $0800               TEXT/GR                                                                                80TEXT/ DGR                                                          HGR 2
                              Page 2                                                                                   Page 2
                                                                                                                      Bloco II/D P1            Bloco II/D P0
                                                                                                                                                                                                          $A000
         $1000
$0000      Zero Page Free RAM                                                                                        Free RAM
$0100        Stack
         $2000
$0200      Key Buffer




                                                  o drama?
                                                                                                                                                                                      Free RAM
            Free RAM         HGR 1                                                                                   DHGR 1                                                                               $4000
$0300     System Pointers
$0400    $4000                                                                                                                                                                          HGR 1
         TEXT/GR Page 1
                                                                                                                                                                                                          $4000

                             HGR 2                                                                                   DHGR 2
                                                                                                                                                                                                          $2000
$0800                                                                                                                                                                                   HGR 1
        TEXT/GR Page 2
         $6000
                                                                                                                                                                                                          $2000

$1000
           Free RAM
                                                                                                                                                                                      Free RAM
                            Free RAM                                                                                 Free RAM
$2000                                                                                                                                                                                                     $0800
            HGR 1                                                                                                                                                                 Some System Variables
                                                                                                                                                                                           &
                                                                                                                                                                                       Free RAM           $0400
         $C000                                                                          Mem Map I/O
$4000
                                                                                                                                                                                      System Pointers     $0300
                                                                                                                                                                                         Free RAM
         $C100                                                                          Expansion Slot
            HGR 2
                                                                                                                                                                                       I/O Buffer         $0200
                                                                                            ROM                                                                                          Stack            $0100
         $D000               L.C. P0               L.C. P1                                               L.C. P1      L.C. P0                                                         Zero Page           $0000
$6000
                     Language Card                     L.C. P0                L.C. P1       ROM                    Language Card
                         Main                                                                                          Main
         $FFFF RAM
          Free                                     Saturn Bank 7
                             Main                      Main                                                          AUX


$C000    Mem Map I/O                         L.C. P0                L.C. P1
$C100    Expansion Slot
             ROM                          Saturn Bank 1
                                               Main
$D000                                     L.C. P0                L.C. P1

             ROM                      Language Card
                                          Main
$FFFF
                                                                                                                                                                                                   61/89
Hello World
          .setcpu      "6502"                            :    lda         (PRINT_DATA),y
          .localchar   '@'                                    beq         :+
                                                              jsr         PRINT_ASCII
          .include "../hw.def"                                iny
                          ●
          .include "../sys.def"
          .include "../bios.def"
                                Algumas opções default        bne
                                                              inc
                                                                          :-
                                                                          PRINT_DATA+1
                                                              bne         :-
          .include "../CB2k.def"
                                –   Para programas pequenos (pequenos mesmo)
                                                   :
                                                      jsr    ANYKEY
          .include "system.def"                               jsr         SYSTEM_HGR

          .org $800
                                     ●   $800 - $1FFF (6 Kbytes)
                                                             SYS
                                                             jsr
                                                                          CB2K_FILE_LOAD
                                                                          ANYKEY


    jsr        SYSTEM_INIT
                                –   Para programas maiorzinhosSYSTEM_APPLESOFT_START_COLD
                                                   NO_FUN:
                                                         jmp

    ldy
    lda
               #CB2K_HANDLER_ERROR ●
               #<NO_FUN
                                         $4000 - $9FFF (~24 Kbytes)
                                                        ANYKEY:
                                                              PRINT       ANYKEY_TEXT
                                                              jmp         MON_RDKEY
                                Fora disto, e terá HEADER: montar versões
                                                   que
    ldx        #>NO_FUN
    SYS                  ●
               CB2K_HANDLER_SET

:
    PRINT HEADER                específicas para cada máquina Hello World !! ============"
                                                   HEADER_line_0:
                                                         .byte 22,0
                                                         textz "============
    dec         HEADER_line_1
    dec         HEADER_line_0                            HEADER_line_1:
    bmi
    lda
                :+
                #90
                                –   Use CB2K_CONFIGURATION_GET saber o limite "
                                                        .byte 23,0
                                                        textz "
    jsr
    beq
                MON_WAIT
                :-
                                    superior da memória .byte 1,0,0
                                    ; Branch always!
                                                        usável
                                                        .byte -1
:

    lda        #<MENSAGEM_TEXT
                                –   Nem sonhe em usar.byte 23,0 no TK-2000!
                                                        HGR2
                                                 ANYKEY_TEXT:

    ldx        #>MENSAGEM_TEXT                                textz ":"
    sta
    stx
               PRINT_DATA
               PRINT_DATA+1
                                     ●
                                         Até a próxima versão da-1CB2k, lógico! :-)
                                                            .byte

                                                              .include    "system.inc"
    ldy        #0
                                                         MENSAGEM_TEXT:
                                                               .include   "mensagem.txt"

                                                                                            62/89
Hello World
                  .setcpu     "6502"                           :     lda          (PRINT_DATA),y
    ●
        Inicialização
                .localchar    '@'                                    beq
                                                                     jsr
                                                                                  :+
                                                                                  PRINT_ASCII
                 .include "../hw.def"                                iny
        –   Biblioteca SYSTEM
                 .include "../sys.def"                               bne          :-
                  .include "../bios.def"                             inc          PRINT_DATA+1
    ●
        Configura manipulador de Erro                                bne          :-
                  .include "../CB2k.def"                       :
        –   Se algo der errado, inicializa o Applesoft e dá o prompt jsr          ANYKEY
                                                                     jsr          SYSTEM_HGR
            pro usuário "system.def"
                 .include
                                                                     SYS          CB2K_FILE_LOAD
                  .org $800                                          jsr          ANYKEY

                                                               NO_FUN:
            jsr        SYSTEM_INIT                                   jmp          SYSTEM_APPLESOFT_START_COLD

            ldy        #CB2K_HANDLER_ERROR                     ANYKEY:
            lda        #<NO_FUN                                      PRINT        ANYKEY_TEXT
            ldx        #>NO_FUN                                      jmp          MON_RDKEY
            SYS        CB2K_HANDLER_SET
                                                               HEADER:
:                                                              HEADER_line_0:
            PRINT HEADER                                             .byte 22,0
            dec         HEADER_line_1                                textz "============ Hello World !! ============"
            dec         HEADER_line_0                          HEADER_line_1:
            bmi         :+                                           .byte 23,0
            lda         #90                                          textz "                                        "
            jsr         MON_WAIT                                     .byte 1,0,0
            beq         :-                 ; Branch always!          .byte -1
:
                                                               ANYKEY_TEXT:
            lda        #<MENSAGEM_TEXT                               .byte 23,0
            ldx        #>MENSAGEM_TEXT                               textz ":"
            sta        PRINT_DATA                                    .byte -1
            stx        PRINT_DATA+1
                                                                     .include     "system.inc"
            ldy        #0
                                                               MENSAGEM_TEXT:
                                                                     .include     "mensagem.txt"

                                                                                                                 63/89
Hello World
    ●   LOOP (até "6502" a linha da primeira zString seja menor que 0)
          .setcpu que                          :    lda    (PRINT_DATA),y
               .localchar   '@'                                      beq          :+
                                                                     jsr          PRINT_ASCII
         –    PRINT (macro em SYSTEM.DEF)
               .include "../hw.def"                                  iny
               .include "../sys.def"                                 bne          :-
                 Imprime <n> zStrings
              .include
              ●         "../bios.def"      (terminada em 0,   C-style) em
                                                                     inc     posições específicas da tela
                                                                                PRINT_DATA+1
                                                                     bne          :-
              ●   (Rotina de SYSTEM.INC)
              .include  "../CB2k.def"                          :
                                                                     jsr          ANYKEY
         –    Pausa de ~25 mSecs
               .include "system.def"                                 jsr
                                                                     SYS
                                                                                  SYSTEM_HGR
                                                                                  CB2K_FILE_LOAD
               .org $800                                             jsr          ANYKEY
              ●
                  (Rotina na ROM)
                                                               NO_FUN:
          –
        jsr   NotarSYSTEM_INIT
                    que MON_WAIT sempre volta com ZeroFlag em 0.
                                                    jmp      SYSTEM_APPLESOFT_START_COLD

        ldy         #CB2K_HANDLER_ERROR                        ANYKEY:
        Notar os branchs relativos anônimos!
    ● lda
        ldx
               #<NO_FUN
               #>NO_FUN
                                                                     PRINT
                                                                     jmp
                                                                                  ANYKEY_TEXT
                                                                                  MON_RDKEY
        SYS         CB2K_HANDLER_SET
                                                               HEADER:
:                                                              HEADER_line_0:
        PRINT HEADER                                                 .byte 22,0
        dec         HEADER_line_1                                    textz "============ Hello World !! ============"
        dec         HEADER_line_0                              HEADER_line_1:
        bmi         :+                                               .byte 23,0
        lda         #90                                              textz "                                        "
        jsr         MON_WAIT                                         .byte 1,0,0
        beq         :-                 ; Branch always!              .byte -1
:
                                                               ANYKEY_TEXT:
        lda         #<MENSAGEM_TEXT                                  .byte 23,0
        ldx         #>MENSAGEM_TEXT                                  textz ":"
        sta         PRINT_DATA                                       .byte -1
        stx         PRINT_DATA+1
                                                                    .include      "system.inc"
        ldy         #0
                                                               MENSAGEM_TEXT:
                                                                     .include     "mensagem.txt"

                                                                                                                 64/89
Hello World
●   Dois loops:
             .setcpu            "6502"                              :      lda
                                                                           beq
                                                                                        (PRINT_DATA),y
                                                                                        :+
                 .localchar     '@'
    –   O interno, “driven” pelo Y                                         jsr          PRINT_ASCII
                 .include "../hw.def"                                      iny
        ●   O INY “overflows” para 0 depois do 255.
                 .include "../sys.def"                                     bne          :-
        ●
            BNE :.include último resultado da ULA não deu em zero
                  pula se o "../bios.def"                                  inc          PRINT_DATA+1
                                                                           bne          :-
    –   O externo, “driven” pelo último valor lido em Acc
               .include "../CB2k.def"                               :
                                                                           jsr          ANYKEY
        ●   BEQ: .include "system.def" em Acc for zero, sai do
                  Se o último byte carregado                               jsr          SYSTEM_HGR
            loop.                                                          SYS          CB2K_FILE_LOAD
    –          .org $800
        BEQ/BNE e outros atuam em cima do Registrador                      jsr          ANYKEY
        de Status (P)                                               NO_FUN:
        ●jsr reflete o SYSTEM_INIT operação da ULA, ou da
           Que         status da última                                   jmp           SYSTEM_APPLESOFT_START_COLD
            última carga em registrador
       ldy           #CB2K_HANDLER_ERROR                            ANYKEY:
    – PRINT_ASCII#<NO_FUN
       lda                                                                PRINT         ANYKEY_TEXT
       ldx           #>NO_FUN                                             jmp           MON_RDKEY
       ● Imprime o caractere ASCII no Acc
       SYS           CB2K_HANDLER_SET                               ● PRINT_DATA
                                                                    HEADER:
●
:
    Dirty and Tricky!                                               HEADER_line_0:
                                                                      – Duas posições na página zero (escolhidas à
                                                                          .byte 22,0
    –    PRINT HEADER
        Eu sei que a única forma do INC dar em zero é
         dec          HEADER_line_1
        PRINT_DATA HEADER_line_0
                      acabar apontando para a página zero
                                                                        dedo!) para servir deHello World !! ============"
                                                                          textz "============ ponteiro para o buffer do
         dec                                                        HEADER_line_1:
        –bmi nunca :+ armazena strings! ;-)
          onde        se                                                texto a 23,0 impresso
                                                                          .byte ser
         lda            #90                                               textz "                                       "
    –   Na prática, pula sempre!                                      – Estas instruções ocupam 2 bytes, e não 3!
                                                                          .byte 1,0,0
         jsr          MON_WAIT
         beq            :-                  ; Branch always!              .byte -1
:
                                                                    ●   Usaremos o Y como indexador no loop que
         lda            #<MENSAGEM_TEXT
                                                                        vem a seguir
                                                                    ANYKEY_TEXT:
                                                                          .byte 23,0
         ldx            #>MENSAGEM_TEXT                                   textz ":"
         sta            PRINT_DATA                                    – Inicializa em
                                                                          .byte -1      0!
         stx            PRINT_DATA+1
                                                                           .include     "system.inc"
         ldy            #0
                                                                    MENSAGEM_TEXT:
                                                                          .include      "mensagem.txt"

                                                                                                                      65/89
Hello World
                 .setcpu      "6502"                :    lda           (PRINT_DATA),y
                 .localchar   '@'                        beq           :+
                                                         jsr           PRINT_ASCII
                 .include "../hw.def"                    iny
●   Aguarda por"../sys.def"
           .include
                      uma tecla (não
           .include "../bios.def"
                                                         bne
                                                         inc
                                                                       :-
                                                                       PRINT_DATA+1

    importa qual"../CB2k.def"
           .include                                 :
                                                         bne

                                                         jsr
                                                                       :-

                                                                       ANYKEY
                 .include "system.def"                   jsr           SYSTEM_HGR
●   Entra em modo gráfico
           .org $800
                                                         SYS
                                                         jsr
                                                                       CB2K_FILE_LOAD
                                                                       ANYKEY

●   Carrega o SYSTEM_INIT arquivo
       jsr      próximo                             NO_FUN:
                                                          jmp          SYSTEM_APPLESOFT_START_COLD

    binário do #<NO_FUN
       ldy
       lda
               catálogo
               #CB2K_HANDLER_ERROR                  ANYKEY:
                                                          PRINT        ANYKEY_TEXT
         ldx          #>NO_FUN                            jmp          MON_RDKEY
    –   ÉSYS
          uma tela HGR
                CB2K_HANDLER_SET
                                                    HEADER:
    :                                               HEADER_line_0:
           EuHEADER fui eu que coloquei lá!
         PRINT
         ●    sei,                                        .byte 22,0
                                                          textz "============ Hello World !! ============"
         dec          HEADER_line_1
    –   Adec
          CB2k já o deixou 'na agulha'
         bmi
                 HEADER_line_0
                 :+
                                                    HEADER_line_1:
                                                          .byte 23,0
         lda     #90                                      textz "                                        "
        quando carregou o programa
         jsr     MON_WAIT                                 .byte 1,0,0
                                                          .byte -1
         beq     :-              ; Branch always!
    :   corrente, basta a chamada para              ANYKEY_TEXT:
        carregá-lo
         lda
         ldx
                 #<MENSAGEM_TEXT
                 #>MENSAGEM_TEXT
                                                          .byte 23,0
                                                          textz ":"
         sta          PRINT_DATA                          .byte -1
         ● Ver CB2K_FILE_SET se não é o que
         stx      PRINT_DATA+1
                                                         .include      "system.inc"
           você quer
         ldy      #0
                                                    MENSAGEM_TEXT:
                                                          .include     "mensagem.txt"

                                                                                                      66/89
Hello World
                  .setcpu      "6502"                    :    lda           (PRINT_DATA),y
                  .localchar   '@'                            beq           :+
                                                              jsr           PRINT_ASCII
                  .include "../hw.def"                        iny
                  .include "../sys.def"                       bne           :-
                  .include "../bios.def"                      inc           PRINT_DATA+1
                                                              bne           :-
                  .include "../CB2k.def"                 :
●   Aguarda.include "system.def"
            por outra tecla                                   jsr
                                                              jsr
                                                                            ANYKEY
                                                                            SYSTEM_HGR
                                                              SYS           CB2K_FILE_LOAD
●   Encerra,.org $800
             inicializando o Applesoft.                       jsr           ANYKEY

                                                         NO_FUN:
    –   A CB2k ainda tá na memória, mas não dá
          jsr      SYSTEM_INIT                                 jmp          SYSTEM_APPLESOFT_START_COLD

        suporte ao BASIC
          ldy      #CB2K_HANDLER_ERROR                   ANYKEY:
            lda        #<NO_FUN                                PRINT        ANYKEY_TEXT
    –   Mas você pode brincar no MiniAssembler!
         ldx
         SYS
                  #>NO_FUN
                  CB2K_HANDLER_SET
                                                               jmp          MON_RDKEY

                                                         HEADER:
    :
        ●   Se você estiver num Apple //e ou num TK-     HEADER_line_0:
            PRINT HEADERa Tomato Board revisada
            2000 com HEADER_line_1                             .byte 22,0
            dec                                                textz "============ Hello World !! ============"
            dec         HEADER_line_0                    HEADER_line_1:
            bmi         :+                                     .byte 23,0
            lda         #90                                    textz "                                        "
            jsr         MON_WAIT                               .byte 1,0,0
            beq         :-            ; Branch always!         .byte -1
    :
                                                         ANYKEY_TEXT:
            lda        #<MENSAGEM_TEXT                         .byte 23,0
            ldx        #>MENSAGEM_TEXT                         textz ":"
            sta        PRINT_DATA                              .byte -1
            stx        PRINT_DATA+1
                                                              .include      "system.inc"
            ldy        #0
                                                         MENSAGEM_TEXT:
                                                               .include     "mensagem.txt"

                                                                                                           67/89
Hello World
                .setcpu      "6502"                         :    lda           (PRINT_DATA),y
                .localchar   '@'                                 beq           :+
                                                                 jsr           PRINT_ASCII
                .include "../hw.def"                             iny
                .include "../sys.def"                            bne           :-
                .include "../bios.def"                           inc           PRINT_DATA+1
                                                                 bne           :-
                .include "../CB2k.def"                      :
●   Dirty and Tricky! "system.def"
              .include
                                                                 jsr
                                                                 jsr
                                                                               ANYKEY
                                                                               SYSTEM_HGR
                                                                 SYS           CB2K_FILE_LOAD
    – A anykey, por ser uma subrotina, deveria
                .org $800                                        jsr           ANYKEY
      terminar com um RTS                                   NO_FUN:
          jsr         SYSTEM_INIT                                 jmp          SYSTEM_APPLESOFT_START_COLD
    – Mas ela por sua vez se vale de outra rotina
      na sua última#CB2K_HANDLER_ERROR
          ldy
          lda          instrução, economizei um byte
                      #<NO_FUN
                                                            ANYKEY:
                                                                  PRINT        ANYKEY_TEXT
      (2 duas posições da pilha) fazendo um JMP
          ldx
          SYS
                      #>NO_FUN
                      CB2K_HANDLER_SET
                                                                  jmp          MON_RDKEY

      pra dita cuja.                                        HEADER:
    :                                                       HEADER_line_0:
       ● O RTS dela é quem faz o retorno a quem
          PRINT HEADER                                            .byte 22,0
          dec         HEADER_line_1                               textz "============ Hello World !! ============"
         chamou a ANYKEY.
          dec         HEADER_line_0                         HEADER_line_1:
                                                                  .byte 23,0
          bmi        :+
          lda        #90                                          textz "                                        "
          jsr        MON_WAIT                                     .byte 1,0,0
          beq        :-                  ; Branch always!         .byte -1
     :
                                                            ANYKEY_TEXT:
          lda        #<MENSAGEM_TEXT                              .byte 23,0
          ldx        #>MENSAGEM_TEXT                              textz ":"
          sta        PRINT_DATA                                   .byte -1
          stx        PRINT_DATA+1
                                                                 .include      "system.inc"
          ldy        #0
                                                            MENSAGEM_TEXT:
                                                                  .include     "mensagem.txt"

                                                                                                              68/89
Aplicações
●   Demos! :-)
    –   No arquivo de Distribuição da CB2k você encontrará o fonte
        para todos os programas de demonstração.
        ●   Console I/O independente de máquina
             –   Conversão automática para maiúsculas em máquinas sem caracteres minúsculos
        ●   Sintetização de SOM!
             –   Eletric Duet / Paul Lutus
●   Exemplos mais complexos da API da CB2k
    –   Carregamento e/ou execução de arquivos
    –   Leitura do Diretório
    –   Handlers de sistema
        ●   Tratamento te exceções
        ●   RESET
                                                                                         69/89
Aplicações
●   Agora:
    –   Beautiful Boot
        ●   Jogos! Yeay! :-)
        ●   Porte feito por Fábio Belavenuto
●   Na agulha:
    –   Basic.system para o TK-2000
        ●   Uma solução definitiva para a fragmentação da memória do
            BASIC no TK-2000
        ●   RDOS style
    –   Novas Demos para a CB2k
        ●   Técnicas de animação e sintetização de Som simultâneos
        ●   O TK-2000 pode, o TK-2000 faz! :-)
●   Futuro:
    –   Substituto para o RDOS no Apple II
        ●   Tão logo eu crie coragem e escreva as rotinas de gravação
            de setores...
    –   Suporte transparente para outras mídias
        ●   Enquanto a API for estável, tanto faz de onde vêm os bytes!
    –   Arquivos de “Overlay”
                                                                          70/89
HGR 1


                                                       $4000     HGR 1


                                                                Free RAM




                                                       $A000
                                                                                                Bloco II/D P0


                        Known Issues
                                                                 HGR 2
                                                                                                 Extra RAM
                                                       $C000   Mem Map I/O                       Bloco II/D
                                                       $C100


                                                       $D000                 Extra RAM   Bloco II/A P0          Bloco
                                                                  ROM
                                                                              Bloco I
●   Código não relocável dinamicamente                                                    Extra RAM
                                                                                          Bloco II/A
                                                       $FFFF

    –   O S.O. está amarrado ao topo da memória
        principal (pouco antes da área de I/O)
    –   Ruim para o TK-2000, pois sua segunda página
        de vídeo está lá.
        ●   Jogos que usam paginação vão matar o S.O.
    –   Desperdiça a Bloco I / Language Card
        ●   Menos memória “segura” para os programas
             –   Que pra começo de conversa não foram feitos para conviver
                 com um sistema operacional de disco! :-)

                                                                              71/89
Known Issues
●   Read Only
    –   A CB2k não grava.
    –   “By Design” =P
        ●   Um processo complicado e ainda mais time critical.
        ●   Até o momento, baixa demanda.
        ●   Implementar gravação vai aumentar o footprint na memória
●   No LIBS
    –   A “biblioteca” não passa de um include sofisticado
        ●   Raios, o S.O. todo tá pendurado assim!
    –   Uma LIB estática é uma demanda forte
        ●   LIB dinâmica é sonho de consumo!
●   Incompatibilidade com a CFFA 3000
    –   Ainda investigando...
                                                                       72/89
Considerações Finais
●   Lições (Re)Aprendidas
    –   Projetos pessoais ainda são Projetos!
    –   Realidade Comanda
    –   Wear Sun Screen! :-)
●   Onde aprender mais?
●   Onde obter ajuda?



                                                73/89
Projetos Pessoais
                        ainda são

                     Projetos
●   Boas práticas também não têm este nome à toa!
    –  Xtreme Programming!
    – Rubber Ducking! ;-)
●   Eu me estrepei muito por não ter seguido
    algumas destas práticas desde o começo
●   E tive meu traseiro poupado de trágico destino
    por ter seguido outras


                                                     74/89
Projetos Pessoais
                                     ainda são

                                 Projetos
●   Version Control System
    –   RCS, CVS, SVN, GIT, Mercurial, Bazaar
        ●   Qualquer um, qualquer um mesmo!
             –   Até copy&paste em diretórios no seu HD!
●   Gerência de Configuração
    –   Procure saber em quais ambientes (e configurações)
        o seu software vai rodar
        ●   Mesmo que não possa garantir o funcionamento em todos!
        ●
            Principalmente para poder garantir o funcionamento em
            alguns!


                                                                75/89
Projetos Pessoais
                                         ainda são

                                     Projetos
●   Use Cases e Back Logs
    –   Formalismos não são necessários
        ●   mas se você não especifica o quê você quer resolver, você não
            resolve é nada...
             –   Gold-plating não é legal.
    –   Um arquivo texto com um parágrafo por Requisito / UC /
        Whatever já é suficiente, o importante é que todos os
        envolvidos saibam do que se trata
        ●   Principalmente quando “todos os envolvidos” é só você! :-)
             –   O tempo passa e não tem mais ninguém pra lhe lembrar do que você tem
                 que fazer!
        ●
            Versione! Versione!!
    –   Foco, ou você não termina esta joça!
                                                                                   76/89
Projetos Pessoais
                                        ainda são

                                    Projetos
●   Fail early, Fail often!
    –   Unit Tests
        ●   Imprescindíveis ! :-)
        ●
            Mas eles custam caro, não subestimem o impacto no
            “orçamento” .
             –   Alguns bugs são mais baratos de serem consertados (se ocorrerem) que
                 prevenidos
             –   Você não tem tempo (nem dinheiro) pra fazer tudo o que quer.
    –   Test Cases / Test Suites
        ●   Porque testes de unidade não são capazes de pegar erros de
            integração que teimam em ocorrer
             –   E sempre nos piores momentos possíveis! :-)
        ●   As aplicações de exemplo são meus Test Suites públicos!

                                                                                   77/89
Realidade Comanda


●   Eat your own dogfood!
    –   É só aplicando na vida real que você tem
        certeza se uma idéia realmente funciona.
        ●   Ou não! ¬¬
    –   Você é seu primeiro e primário beta-tester.
        ●    Use seu produto, encontre você mesmo seus
            erros
             –   Ou outros o farão por você
                                                         78/89
Realidade Comanda
●   Beta testers
    –   Eu não teria conseguido sem ajuda!
        ●   Sem eles, e você desenvolve no escuro
             –   Exceto se dispor de recursos financeiros para comprar tudo em que bate os
                 olhos! ;-)
    –   Mas eles não serão muito úteis se você não fizer seu dever de
        casa:
        ●   Use Cases
        ●   Test Cases
        ●   Gerência de Configuração
        ●   Versionamento de Código
    –   Foi aqui que eu percebi que estava atirando no meu próprio pé
        ao “agilizar” o desenvolvimento ao custo de algumas boas
        práticas...
                                                                                             79/89
Realidade Comanda
●
    Não subestimar a importância de um bom
    Error Report
    –   Porque você *NUNCA* pegará todos os
        erros.
         ●
           Principalmente os bobos
            – Erro grave explode logo, são os
              bobos que dão trabalho!




                                                80/89
Realidade Comanda




KDIFF3 é pra vida! :-)




                         81/89
Links Relacionados
●   CB2k
    –  Suite de Testes
    – Debut da CB2k (Apple //e)
    – Debut² =P no TK-2000
●   Slides da palestra
●   http://pt.wikipedia.org/wiki/Apple_II
●   http://pt.wikipedia.org/wiki/TK2000
●   http://retro.lisias.net/

                                            82/89
Links Úteis
●   http://www.6502.org
●   http://www.cc65.org/
●   http://applewin.berlios.de/
●   http://www.fabio.belavenuto.nom.br/tk2000/
●   http://www.datacassete.com.br/
●   ftp://ftp.apple.asimov.net/pub/apple_II/
●
    http://www.applefritter.com/
●
    http://www.extremeprogramming.org/
●   http://www.codinghorror.com/blog/2012/03/rubber-duck-problem-solving.html
●   Ajuda Especializada 0:-)


                                                                          83/89
Links Interessantes
●   Paul Langhton
    –   Consultor responsável pelo Apple DOS
●   Steve Wozniak
    –   Responsável por todo o resto! :-)
●   Apple II History
    –   História do Apple II, versão do usuário.
●   ASCII Express' Game Server
    –   “Servidor” de jogos, com download em formato de áudio
        otimizado
    –   Para máquinas “diskless”
                                                                84/89
Links “Interessantes” =P
●   Câmara de Torturas
    (ou: se Donatien Alphonse François fosse Analista de Sistemas)

     –   Restauro e 'Mods' do TK-2000
         ● E outras vítimas


     –   Outros clássicos
         ● Alguns poucos conhecidos por aqui


     –   Outros loucos
         ● Porque gostamos de companhia. O:-)




                                                                     85/89
(alguma)
                   Literatura Recomendada
     ●   How to program the Apple II using    ●   Software Control of the Disk II or IWM
         6502 Assembly Language                   Controller
         –   DATAMOST, 1982                       –   Norman Leung
         –   Randy Hyde                           –   Apple Computer, 1984
         –   Featuring LISA Assembler
                                              ●   Andrew S. Tanenbaum
     ●   Beneath Apple DOS /                      –   Eternamente :-)
         Beneath Apple ProDOS                 ●   Microcomputadores e
                                                  Microprocessadores
         –   Don Worth & Pieter Lechner
                                                  –   Albert Paul Malvino
         –   Quality Software, 1982
                                                  –   McGraw-Hill, 1985
     ●   Understanding the Apple II           ●   The Pragmatic Programmer: From
         –   James Fielding Sather                Journeyman to Master
         –   Quality Software, 1983               –   Andrew Hunt & David Thomas
         –   Com Introdução do Woz! :-)           –   Addison-Wesley Professional, 1999


                                                                                          86/89




Na falta de qualquer outro critério, foram estes que
 eu usei desde a primeira vez que me propuz a
 aprender Assembler, em 1980 e vovó de bicicleta!
Onde Obter Ajuda
●   Lista appleII_br
●   Newsgroup comp.sys.apple
    –   E os diversos subgrupos desta hierarquia
●   me@lisias.net ;-)
●   Ajuda Especializada 0:-)




                                                   87/89
Free Chat
     ●   Dúvidas?
     ●   Comentários?
     ●   Sugestões?
     ●   Apoio moral?
         –   (Piada interna da appleII_br)
         –   *<8o)




                                             88/89




Aproveitar para agradecer blah, blah, blah e ETC.

E demonstrar a Karateka CB2k do Fábio Belavenuto,
  que foi meu primeiro cliente! :-)
Obrigado!




     @lisias
     me@lisias.net
     http://tk2k.lisias.net/CB2k                       89/89

     Boldly crashing what no man has crashed before!



Nos momentos difícieis em que nem o pato de
 borracha pôde me ajudar, fazia parte do processo
 de superação =P fantasiar em jogar meu TK-2000
 pela janela e transformá-lo no mais novo satélite
 artificial brasileiro.

A piada faz algum sucesso na lista apple_II. :-)

Nota: o micrinho é uma GIF animada (sou retrô ou
 what?), mas o slideshare não dá suporte a esta
 feature.

Mais conteúdo relacionado

DOC
A EVOLUÇÃO DOS SISTEMAS OPERACIONAIS
ODT
Sociologia
KEY
Cibercultura2k10web
PDF
Decreto De Madri - 2002
PDF
Rolima 63b
PPS
Apresentação Lux Laserterapia e Spa Capilar
PDF
122091768 revistapodologia-com-028pt
PPTX
Geografia da Europa 2015/2016 - Artes - Música
A EVOLUÇÃO DOS SISTEMAS OPERACIONAIS
Sociologia
Cibercultura2k10web
Decreto De Madri - 2002
Rolima 63b
Apresentação Lux Laserterapia e Spa Capilar
122091768 revistapodologia-com-028pt
Geografia da Europa 2015/2016 - Artes - Música

Destaque (20)

PPTX
Geografia da Europa - Geografia Humana - Artes - Música
PDF
Ozonioterapia - Plenária CFM - Nov 2013 - Emilia Serra
PPTX
Bruno Rego - Techno
PDF
Ozonioterapia em feridas e osteomielite maria emilia gadelha serra
PDF
Ozonioterapia - Plenária CFM nov 2013 - Emilia Serra
PPTX
Avanços na Medicina: Medicina Regenerativa, Ortomolecular, Ozonioterapia e A...
PPT
Hidro ozonio terapia
PPTX
Cultura e Sistemas de Saúde
PDF
Musica: Arte e Tecnologia (www.sheetmusic-violin.blogspot.com)
PPTX
Estudo da Medicina Antienvelhecimento no Mundo
PDF
Ozonioterapia Nova antiga ferramenta - Maria Emilia Gadelha Serra
PDF
Ozonioterapia - Basics - Maria Emilia Gadelha Serra
PDF
Ozonioterapia em oncologia 2015 - maria emilia gadelha serra
PDF
Sintetizador -slide
PPT
A Cibercultura no Cotidiano
PDF
Cibercultura
PDF
Rio Sport and Health 2015 - Ozonioterapia em atletas - Dra. Maria Emilia Gade...
PDF
Cibercultura
PDF
Revista 2
PDF
Declaração de madrid sobre ozonoterapia
Geografia da Europa - Geografia Humana - Artes - Música
Ozonioterapia - Plenária CFM - Nov 2013 - Emilia Serra
Bruno Rego - Techno
Ozonioterapia em feridas e osteomielite maria emilia gadelha serra
Ozonioterapia - Plenária CFM nov 2013 - Emilia Serra
Avanços na Medicina: Medicina Regenerativa, Ortomolecular, Ozonioterapia e A...
Hidro ozonio terapia
Cultura e Sistemas de Saúde
Musica: Arte e Tecnologia (www.sheetmusic-violin.blogspot.com)
Estudo da Medicina Antienvelhecimento no Mundo
Ozonioterapia Nova antiga ferramenta - Maria Emilia Gadelha Serra
Ozonioterapia - Basics - Maria Emilia Gadelha Serra
Ozonioterapia em oncologia 2015 - maria emilia gadelha serra
Sintetizador -slide
A Cibercultura no Cotidiano
Cibercultura
Rio Sport and Health 2015 - Ozonioterapia em atletas - Dra. Maria Emilia Gade...
Cibercultura
Revista 2
Declaração de madrid sobre ozonoterapia

Semelhante a Slides CB2k DevInSampa 2012 (20)

PDF
Programação para Atari 2600
PDF
Programação para Atari 2600
PDF
Augusto loureiro sistemas microprocessados
PPT
CMG Brasil 2012 - Uso de Lines nos z196
PDF
Minibook Fábio&Isabel- seleção de vocabulário
PDF
Mini book isabel&fábio
PDF
Minibook
DOCX
Fichas tic pedro amorim e gonçalo mouzinho
PPT
Informática e Windows
PDF
6915516 introducao-ao-processamento-de-dados
PDF
Aula 05-entrada e-saida
PPTX
Aula 4
PPTX
Aula 4
PDF
Pequeno caderno com recolha de vocabulário específico da área da informática
PDF
Hardware de sistemas
PDF
Minibook
PDF
Apostila informática básica e windows
PDF
Uma breve história no tempo...da computação
PDF
Programacão para não programadores
PDF
Sistemas operacionais prof
Programação para Atari 2600
Programação para Atari 2600
Augusto loureiro sistemas microprocessados
CMG Brasil 2012 - Uso de Lines nos z196
Minibook Fábio&Isabel- seleção de vocabulário
Mini book isabel&fábio
Minibook
Fichas tic pedro amorim e gonçalo mouzinho
Informática e Windows
6915516 introducao-ao-processamento-de-dados
Aula 05-entrada e-saida
Aula 4
Aula 4
Pequeno caderno com recolha de vocabulário específico da área da informática
Hardware de sistemas
Minibook
Apostila informática básica e windows
Uma breve história no tempo...da computação
Programacão para não programadores
Sistemas operacionais prof

Último (19)

PPTX
Aula 18 - Manipulacao De Arquivos python
PDF
Custos e faturamento no SAP S/4HANA Transportation Management, S4TM3 Col26
PDF
20250805_ServiceNow e a Arquitetura Orientada a Serviços (SOA) A Base para Ap...
PPTX
Aula16ManipulaçãoDadosssssssssssssssssssssssssssss
PDF
Processos na gestão de transportes, TM100 Col18
PDF
Gestão de transportes básica no SAP S/4HANA, S4611 Col20
PDF
Fundamentos de gerenciamento de ordens e planejamento no SAP TransportationMa...
PDF
Mergulho profundo técnico para gestão de transportes no SAP S/4HANA, S4TM6 Col14
PPTX
Como-se-implementa-um-softwareeeeeeeeeeeeeeeeeeeeeeeee.pptx
PPTX
Gestao-de-Bugs-em-Software-Introducao.pptxxxxxxxx
PDF
Apple Pippin Uma breve introdução. - David Glotz
PDF
Custos e liquidação no SAP Transportation Management, TM130 Col18
PPTX
Informática Aplicada Informática Aplicada Plano de Ensino - estudo de caso NR...
PDF
Otimizador de planejamento e execução no SAP Transportation Management, TM120...
PDF
Fullfilment AI - Forum ecommerce 2025 // Distrito e Total Express
PDF
Aula04-Academia Heri- Tecnologia Geral 2025
PPTX
Programação - Linguagem C - Variáveis, Palavras Reservadas, tipos de dados, c...
PPTX
BANCO DE DADOS - AULAS INICIAIS-sgbd.pptx
PDF
COBITxITIL-Entenda as diferença em uso governança TI
Aula 18 - Manipulacao De Arquivos python
Custos e faturamento no SAP S/4HANA Transportation Management, S4TM3 Col26
20250805_ServiceNow e a Arquitetura Orientada a Serviços (SOA) A Base para Ap...
Aula16ManipulaçãoDadosssssssssssssssssssssssssssss
Processos na gestão de transportes, TM100 Col18
Gestão de transportes básica no SAP S/4HANA, S4611 Col20
Fundamentos de gerenciamento de ordens e planejamento no SAP TransportationMa...
Mergulho profundo técnico para gestão de transportes no SAP S/4HANA, S4TM6 Col14
Como-se-implementa-um-softwareeeeeeeeeeeeeeeeeeeeeeeee.pptx
Gestao-de-Bugs-em-Software-Introducao.pptxxxxxxxx
Apple Pippin Uma breve introdução. - David Glotz
Custos e liquidação no SAP Transportation Management, TM130 Col18
Informática Aplicada Informática Aplicada Plano de Ensino - estudo de caso NR...
Otimizador de planejamento e execução no SAP Transportation Management, TM120...
Fullfilment AI - Forum ecommerce 2025 // Distrito e Total Express
Aula04-Academia Heri- Tecnologia Geral 2025
Programação - Linguagem C - Variáveis, Palavras Reservadas, tipos de dados, c...
BANCO DE DADOS - AULAS INICIAIS-sgbd.pptx
COBITxITIL-Entenda as diferença em uso governança TI

Slides CB2k DevInSampa 2012

  • 1. Um Carregador Rápido para TK-2000 e Apple II que virou Sistema Operacional http://tk2k.lisias.net/CB2k
  • 2. Premissa i.Restaurar um obscuro computador doméstico de quase 30 anos de idade ii.Escrever um sistema operacional pro dito cujo iii.????? iv.PROFIT! :-)
  • 3. @Lisias | http://lisias.net 3/89
  • 5. As Vítimas ● Scene Retrô brasileira de Apple II e Compatíveis (ou quase) – Intensa movimentação nos últimos 18 meses ● Inúmeras novidades – engenharia reversa do Cartucho Controlador de Discos do TK-2000 – Tomato Board 5/89
  • 6. O Motivo ● Acesso à Hardware equivalente, mais barato e abundante, da linha Apple ● Mas os jogos (e parte significativa dos demais softwares) ainda estavam em formato Cassete ● Soluções (software) prontas, importadas do Apple II, eram – Muito complexas para portar ● ProntoDOS, DiversiDOS, ProDOS – todos ótimos, mas sistemas operacionais completos! – Overkill – Over memory :-) 6/89
  • 7. Enquanto isto... ● “lá fora” (news:comp.sys.apple) – CompatiBoot original (Raven/C700 Club) ● Rápida ● Prática ● Mas não adequada – Capenga no TK-2000 – One shot only – Altas gambiarras pra convencer a dita cuja a fazer o que precisávamos – Efeitos colaterais diversos e inesperados 7/89
  • 8. Indo direto ao ponto ● Benchmark : TK-DOS 3.3 – Tempo entre ligar a máquina (com um disquete com boot no drive) e o Prompt do Applesoft: ● 31 segs. – Tempo para carregar uma tela gráfica HGR: ● 10 segs – Espaço livre na RAM depois de carregado: ● ~ 24 Kbytes. – Não, não é Mega. É Kilo mesmo! :-) ● Demais S.O.s – Overkill ● Outras Soluções – Não são práticos nem flexíveis – São perdulários – Não funcionam, ou o fazem porcamente, no TK-2000 8/89
  • 9. O Crime “Hummmm...” Groo faz o que... “Eu acho que faço melhor!” 9/89
  • 10. Advertência O uso indiscriminado e Podem causar danos concomitante de irreversíveis à/ao – Linguagem Assembler – Sanidade mental – Rotinas de Tempo Real – Computadores Vintage – Relacionamentos amorosos – Conceitos (nem tão assim) – Vida social avançados de Arquitetura de Computadores e Sistemas – Convivência familiar Operacionais – Organização domiciliar – Café, cerveja, pizzas, lanches e – Paz condominial snacks – EL&P, Rick Wakeman, Jean Michel – Perímetro da sua cintura :-) Jarre, Vangelis, Daft Punk e Kraftwerk Depois não digam que a culpa é minha!! :-) 10/89
  • 11. Planejando a ação ● A CB2k deve: – Carregar arquivos com a maior eficiência possível – Permitir carregar programas que querem ocupar o espaço onde normalmente ficaria o DOS – Ser prática para criar/atualizar disquetes – Oferecer uma API consistente para programação – Fornecer exemplos de como desenvolver aplicações 11/89
  • 12. Planejando a ação ● A CB2k não pode deixar de: – Ser extensível e portável – Ficar pronta em umas 4 ou 5 semanas. ● Férias acabam! – Ser útil e agregar valor ● Demais funcionalidades (rede, ambiente gráfico, co-processamento, etc.) – são totalmente fora de escopo ● Hoje! ;-) 12/89
  • 13. It's coding time! ● BELEZA!! Já sei o que quero fazer, agora é só ligar a máquina e... Oh, wait... – Como se programa nesta joça? 13/89
  • 14. First Things First code “One does not simply walk into Mordor!” Boromir, The Fellowship of the Ring 14/89
  • 15. Programação de Baixo Nível Não tem este nome à toa... ● O legendário 6502 ● Arquitetura dos Computadores – Apple II+ – MPF-II/TK-2000 – Semelhanças e diferenças entre as máquinas target ● Disquetes: um problema em tempo real – A Shugart – A Disk II do Woz – Persistência de dados em mídias magnéticas 15/89
  • 16. O 6502 ● Registradores ● Instruções ● Clock Cycle Time – Cycle para os íntimos ● T States – A únidade básica de tempo do processador – A únidade básica de ansiedade do programador ● Os diferentes Endereçamentos à memória – O segredo do sucesso! – A Salvação da Pátria! ● O primeiro RISC? ● Sucessores – 65C02 – 65816 16/89
  • 17. $0000 Zero Page $0100 Stack O 6502 A 7 6 5 4 3 2 1 0 X Y 7 6 5 4 3 2 1 0 7 6 5 4 3 2 1 0 S P 7 6 5 4 3 2 1 0 N V 1 B D I Z C PC 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ● Load / Store ● Trasnfer ● ROR, ROL, SHL, SHR – Pero no mucho! – AX, XA – A Free Addresses – AY, YA #imm ● LD / ST ● – XS, SX ● Abs – [A,X,Y] #imm ● Branchs ● Abs,X – A abs,X – EQ / NE (Zero Flag) ● Abs,Y – A abs,Y MI / PO (Minus Flag) – ● (Indi,X) – A (indi,X) – CS, CR (Carry) ● (Ind),Y – A (indi),Y – VS, VC (Overflow) ● ADC, SBC ● JMP ● P (Status) – A – JMP abs – SEC, CLC ● #imm – Etc Abs – JMP (indi) ● ● INC / DEC ● Abs,X ● JSR / RTS – A, X, Y ● Abs,Y ● Stack – Abs ● (Indi,X) – PHA / PLA – Abs,X (Ind),Y $FF00 ● ROM – PHP / PLP – Abs,Y Muito Mais! 17/89 $FFFF ●
  • 18. O Apple II+ ● Hardware – Memory Mapped I/O – Modos de vídeo – Mapa da RAM ● ROM – Principais entry-points – Uso da Página Zero ● Console I/O – Teclado – Caracteres 18/89
  • 19. $0000 Zero Page O Apple II+ $0100 Stack $0200 I/O Buffer Free RAM $0300 System Pointers $0400 TEXT/GR Page 1 ● Buffer de I/O $0800 – Usado pelo sistema (e pelo DOS) para TEXT/GR Page 2 entrada e saída de dados ● Teclado $1000 Free RAM ● Disco $2000 ● Etc. HGR 1 ● 2 Páginas de texto $4000 – 1 delas pode ser usada para programação HGR 2 ● 2 Páginas de gráficos – Ambas podem ser usadas para programação $6000 ● A ROM pode ser “sombreada” por um L.C. P0 mecanismo chamado “Language Card” L.C. P1 Free RAM Saturn Bank 7 – A LC é dividida em 3 bancos Main ● 1 Principal ● 2 Secundários, que dividem o mesmo $C000 Mem Map I/O L.C. P0 L.C. P1 endereço $C100 – A LC pode ser expandida através de bancos Expansion Slot ROM Saturn Bank 1 de memória Main $D000 ● Saturn 128Kb. L.C. P0 L.C. P1 ROM Language Card Main 19/89 $FFFF
  • 20. O Apple II+ ● Teclado “ASCII” – Um uC faz o serviço sujo para você – Curto e Grosso ● E simples de ler! – Mas um saco para os jogos ● Control e Shift não são dectáveis sem mods ● Combinações de teclas (que não envolvem as modificadoras acima) são impossíveis de serem detectadas – A segunda sobrescreve a primeira, e ponto final ● Caracteres – ASCII ● Alfanuméricos ● Suporte à Minúsculas opcional (!!!) – Inverso e Flash 20/89
  • 21. O MicroProfessor II e seu primo brasileiro TK-2000 ● Hardware – Memory Mapped I/O – Modos de vídeo – Mapa da RAM ● ROM – Principais entry-points – Uso da Página Zero ● Console I/O – Teclado – Caracteres 21/89
  • 22. $0000 $0100 Zero Page Stack O MicroProfessor II e seu primo brasileiro $0200 I/O Buffer TK-2000 Free RAM $0300 System Pointers $0400 Free RAM & Some System Variables ● 2 páginas de gráficos $0800 – Como não há modo texto, uma delas Free RAM obrigatoriamente precisa estar em uso pelo sistema $2000 – O TK-DOS ocupa quase toda a página 2 :-( HGR 1 ● ROM pode ser programaticamente $4000 HGR 1 substituída pelas Extra RAM ● Bloco I : 15.75 Kbytes Free RAM ● Bloco II : 4 bancos de 16Kbytes – 1 banco de 8 kbytes $A000 – 2 sub-bancos de 4 kbytes Bloco II/D P0 Bloco II/D P1 HGR 2 – Saturn 64Kb! :-) Extra RAM ● O meu tem 128Kb! :-) $C000 Mem Map I/O Bloco II/D $C100 ● Apenas um Bloco pode estar ativo num momento $D000 Bloco II/A P0 Bloco II/A P1 ROM Extra RAM – Os bancos do Bloco II precisam escolher qual Bloco I Extra RAM página de 4 kbytes deve estar ativa Bloco II/A $FFFF 22/89
  • 23. O MicroProfessor II e seu primo brasileiro TK-2000 ● Teclado com a Matriz exposta – Sem um MicroControlador pra fazer o serviço pesado – Vantagens ● Acesso individual (e múltiplo!) ao estado de cada tecla – permite algumas combinações interessantes para jogos – Desvantagens ● Gasto de processamento para ler o teclado ● Principal e maior motivo da “má fama” do TK-2000 – A rotina do fabricante, oferecida no Manual Técnico como alternativa à leitura do teclado do Apple II era porca – simples assim – Um dos principais artefatos secundários do projeto: ● Uma rotina rápida de leitura de teclado! :-) – Caracteres ● ASCII – Alfanuméricos – Sem suporte às minúsculas (!!!) ● Semigráficos Fonte: pág.21 TK2000/II Manual Técnico Microdigital Eletrônica LTDA 23/89
  • 24. $0000 $0100 Zero Page Stack O Apple //e & //c Zero Page Stack $0200 $0300 I/O Buffer Free RAM System Pointers (porque todo castigo...) I/O Buffer Free RAM System Pointers $0400 TEXT/GR 80TEXT/DGR Page 1 Page 1 $0800 ● Revisões TEXT/GR 80TEXT/ DGR Page 2 – Apple // Extended Page 2 $1000 Free RAM ● 6502 Free RAM $2000 – Apple //c, //e Enhanced e Platinum HGR 1 DHGR 1 ● 65C02 $4000 ● “Mouse Chars” HGR 2 ● DTEXT (80 COLs), DGR & DHGR DHGR 2 $6000 ● 128Kb – Mas num esquema totalmente diferente Free RAM Free RAM – Descreve isto, Lisias! ● Nah... Deixa quieto! =D $C000 Mem Map I/O $C100 Expansion Slot Extension ROM ROM $D000 L.C. P0 L.C. P1 L.C. P1 L.C. P0 Language Card ROM Language Card Main Main $FFFF 24/89 Main AUX
  • 25. Resumo da Ópera ● As diferenças da ROM enchem o saco – Oferecer uma camada de “abstração” da ROM seria bacana, mas exigiria mais memória ● Mas não sai de graça ● As diferenças na memória principal são facilmente gerenciáveis – Mas o mesmo não acontece com os bancos de memória estendida ● E lá se vão funcionalidades pela janela ● O 65C02 têm instruções extras que seriam (muito) úteis – Maior densidade de código e mais “semântica” por ciclo de clock ● TXY (1 byte, 2 Ciclos) – PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!) – STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma posição da ZP) – STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos) – Mas alienaria o TK-2000 e o Apple II+ 25/89
  • 26. Mas não é só isso! 26/89
  • 27. Mídias Magnéticas ● Revoluções Por Minuto Mas sem as louras geladas... =/ – Densidade Magnética ● Coerção ● Histeresys – Velocidade Angular “constante” versus Velocidade Linear “constante” ● (Constante, o escambau! O motor não é estável...) – Largura de Banda – Desgaste físico! 27/89
  • 28. Discos Magnéticos ● As trilhas não têm todas o mesmo tamanho físico. – Perímetro é função do raio! ● Mas tem o mesmo tamanho lógico... – Velocidade angular constante ● Densidade dos dados varia em função da trilha ● Pragmatismo – A Shugart ajustou o mecanismo para ser confiável na trilha mais interna, e desperdiçou densidade nas mais externas – Drives mais sofisticados (e caros) variam a velocidade do motor em função da trilha ● aproveitar melhor a densidade da mídia 28/89
  • 29. Discos Magnéticos ● Os dados são gravados (re)alinhando polaridade na superfície da camada de óxido de ferro – Descobriu-se não ser eficiente usar uma polaridade para o bit 1, e outra para o bit 0 ● Mudança de polaridade na linha do tempo indica bit 1 ● Não mudança de polaridade na linha do tempo indica bit 0 ● Mas o motor não consegue fornecer uma velocidade constante ao nível do microsegundo – Pequenas variações no motor “distorcem” o comprimento de um bit – Dada uma distância longa o suficiente sem inversão de polaridade, o hardware não sabe mais quantos bits '0' foram lidos... 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ? ● As inversões de fase, então, são usadas como “clock” para a leitura dos dados 29/89
  • 30. Discos Magnéticos ● Mas isto tudo foi problema da Shugart! – E do Woz... ● E do Langhton! – Quem? :-) ● Qual foi o meu problema? – 32 * 1 / 1.023 MHz ● 0,0000031280547409579667644183773216031 Segundos ● É o tempo que se tem para ler um raw byte do disquete, salvar na memória e estar pronto para ler o próximo! ● 3196 a 12787 bytes lidos a cada piscar de olhos – E eu só preciso perder UM para causar o infame I/O Error! 30/89
  • 31. Discos Magnéticos 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ? 32 T states 31/89
  • 32. Algoritmos de Tempo Real ● Quediaboéisso? – São algoritmos em que o tempo de resposta faz parte do resultado do processamento ● Não é o mesmo que “fazer rapidinho” – “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo. – “Entregar” antes do prazo é desperdício de processamento ● E o Kiko? Kiko'eu tenho a ver com isto? – Acessar disco é uma tarefa de tempo real ● Missão Crítica! – Computadores modernos possui um micro controlador especializado para lidar com disco ● O Apple II não. – Welcome to hell... 32/89
  • 34. Reavaliação ● Riscos – Gravar setores dá mais trabalho que ler ● E eu nem tinha certeza de que iria conseguir ler... – Não vou conseguir fazer tudo! ● Muitas diferenças entre cada target, praticamente um software diferente pra cada um ● Prioridades – BOOT eficiente – Carga rápida de Binários – Serviços (mínimos) de diretório – (nice) API ● Sólida – Abrir mão da memória extra, e focar na principal ● E economizar onde der 34/89
  • 35. Reação ● Começar prototipando as rotinas básicas de disco – Se eu não estabilizar a rotina de leitura de setores, o resto não serve de nada – Um terço do esforço total do projeto foi gasto só nelas ● Redução de escopo – Serviços de “Console I/O” pelo Kernel :-| – Cache de disco (em especial, do CATALOG) :-| – Gravação de Dados ¬¬ – Gerenciamento da memória ¬¬ – Relocação em memória X-( – Suporte à programas BASIC X-( 35/89
  • 36. Resolução ● “Internalizar” algumas funções da ROM para o S.O. – Não sem conseqüências... ¬¬ ● Delegar à aplicação gerenciar o resto do hardware – O S.O. identifica para você a máquina em que está rodando – “Bibliotecas” padrão no “User Space” – E cada um que se vire! ● BASIC.SYSTEM – Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no User Space. ● “Forkar” o Kernel para casos especiais – Versões especializadas para cada arquitetura e/ou funcionalidade específica – Gerência de Configuração to the rescue! :-) 36/89
  • 37. E o inesperado (porque todo castigo...) ● O uso da Página Zero me mordeu o traseiro. – Feio. :-( – Quase assassinou o projeto no berço ● Quando a R*TS não matava o resto da máquina, o resto da máquina matava a R*TS ● Cerca de 20% do esforço de desenvolvimento foi gasto mapeando e documentando, corretamente, o uso da Z.P. – No TK-2000 e no Apple II – Um esforço com o qual eu não contava – Não havia mais o que fazer exceto desistir ou pagar o pato e seguir adiante ● 5 dias de trabalho indo pelo ralo. – E as férias, digo, o prazo acabando! =] ● A única documentação formal do projeto. 37/89
  • 38. ; Depends on rwts.def. ; Updates zp_profile.s ; Apple II Zero Page Usage ; ; Lo Nibble of Address ; Hi ; Nib 0 1 2 3 4 5 6 7 8 9 A B C D E F ; ----- ----- ------ ------ ----- ------ ----- ---- ---- ---- ---- ---- ----- ----- ----- ----- ; 0 | A~ A~ A A A A - - - - A A A AI A A ; 1 | A A A A A A A A A A A A A A - M* ; 2 | M M M M M3 M MA3 MA3 M3 M3 M3 M3 MA3 MA3 M3 MA3 ; 3 | MA M MA MA3 M M3 M3B M3B M3B M3B M~ M~ MA3~^ MA3~^ MA3~^ MA3~^ ; 4 | M3~+^ M3~+^ M3~@^ M3~@^ M3~@^ M3~@ M3~ M3~ M3~ M3~ I3~ I3~ I3~ I3~ M~@# M@# ; 5 | MA MA MA MA MA* MAI* AI AI AI AI AI AI AI AI AI AI ; 6 | AI+ AI+ AI@ AI@ AI@ AI@ AI@# AI3 AI3 AI3 AI3 AI AI AI AI AI3 ; 7 | AI3 AI AI AI3 AI3 AI AI3 AI AI AI AI AI AI AI AI AI ; 8 | AI AI AI AI AI AI AI AI@ AI@ AI AI AI AI AI AI AI ; 9 | AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI ; A | AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI3 ; B | AI3 AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI ; C | AI AI AI AI AI AI AI AI AI AI AI3 AI3 AI3 AI3 I# I# ; D | AI AI AI AI AI AI AI3 I! AI3 AI3 AI AI AI AI AI3 AI ; E | A A A A A A A A A A A ? - - - - ; F | A A A A A A A A A A - - - - Ik AI ; ; ; M = Used by Monitor; * used in early Apple IIe ROMs-- now free ; A = Used by Applesoft BASIC ; I = Used by Integer BASIC ; 3 = Used by DOS 3.3 ; ~ = Used by ProDOS ($40-$4E is saved before and restored after use) ; B = Used by ProDOS BASIC.SYSTEM (also uses all Applesoft locations) ; - = Free; not used ; ; k = Used by TK-2000 / MPF-II ; ; + = RWTS, Comunicação com "Cliente" ; @ = RWTS, Conteúdo descartável. ; ! = RWTS, Posição Chave: não pode ser mudada nem destruída! ; ; ^ = CompatiBoot 2k, Comunicação com "Cliente" ; # = CompatiBoot 2K, Conteúdo descartável. ; ? = CompatiBoot 2K, Posição Chave: não pode ser mudada nem destruída! ; ; --Bryan Dunphy, Michael J. Mahon, Rubywand, CompatiBoot 2k 38/89
  • 39. E quando tudo o mais falhar... “How many times do I have to tell you, the right tool for the right job!” Montgomery Scott (Scotty) Chief Engineer, NCC-1701-A USS Enterprise 39/89
  • 40. Anatomia de um Disquete 40/89
  • 41. Anatomia de um Disquete 35 Trilhas 0 1 2 … 35 Address Field gapzão gapzão gapzão gapzão 14 Addr_0 Addr_0 Addr_0 3 2 Addr_0 2 2 2 3 gap gap gap Prologo Volume gap Track Sector ChkSum Epilogo Data Data Data 'D5 AA 96 '4 & 4 encoding '4 &Data 4 encoding '4 & 4 encoding '4 & 4 encoding 'DE AA EB =4096 bytes (lógicos) gap gap gap gap Addr_1 Addr_1 Addr_1 Addr_1 ~48000 bits (raw) gap gap gap gap Data Field Data Data Data Data 349 gap gap gap 3 gap 342 1 3 Addr_2 Addr_2 Addr_2 Prologo Addr_2 Data ChkSum Epilogo gap gap gap 'D5 AA AD gap 6 & 2 encoding 'XX 'DE AA EB Data Data Data Data gap gap gap gap Addr_3 Addr_3 Addr_3 … “gapzãp” Addr_3“Self Sync bytes” gap gap gap gap 48 a 100 gap 5 a 60 Data Data Data 'FF FF FF … Data 1 1 1 1 1 1 1 0 0 '1 'FF FF FF gap gap gap gap Addr_4 Addr_4 Addr_4 Addr_4 gap gap gap gap Data Data Data Data gap gap gap gap … … … … Addr_15 Addr_15 Addr_15 Addr_15 gap gap gap gap Data Data Data Data 41/89
  • 42. Anatomia de um Disco DOS 3.3 Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 42/89
  • 43. Boot ● Power On RESET – RESET Vector ● Autostart ROM (BOOT 0) – Busca por uma placa DISK II na ROM de expansão ● BOOT 1 (second stage) – Trilha 0, Setor 0 – L-Boot1 ● BOOT 2 (third stage) – Sistema Operacional Ou outro payload qualquer... 43/89
  • 44. A L-Boot1 ● Fornece a melhor performance possível para carga sequêncial – Multi trilha ● Serviços independentes de “plataforma” – Impressão em tela – Carga de setores – Descompressão de dados ● Também foi usada com sucesso: – Boot do TK-DOS 3.3 – Boot do Apple DOS 3.3 – Jogos stand-alone 44/89
  • 45. Finalmente: CB2k ● R*TS ● Kernel – Serviços de Diretório – Serviços “Raw Files” – Serviços Binary Files – Serviços de House Keeping 45/89
  • 46. O Inferno das Entry-Points 00B3D5 2 KERNEL__ADDR_START: 00B3D5 2 ; Prevents accidental running 00B3D5 2 00 BRK 00B3D6 2 1E .byte __WARM_BOOT - __KERNEL_SERVICES_TABLE 00B3D7 2 00B3D7 2 __KERNEL_SERVICES_TABLE: 00B3D7 2 F8 B3 .word __PANIC 00B3D9 2 59 B5 .word KERNEL_SYSTEM_IDENTIFICATION 00B3DB 2 F4 B8 .word KERNEL_FILE_LOAD 00B3DD 2 21 B9 .word KERNEL_FILE_RUN 00B3DF 2 61 B5 .word KERNEL_SESSION_FINISH 00B3E1 2 10 B6 .word KERNEL_CATALOG_ENTRY_SET 00B3E3 2 33 B6 .word KERNEL_CATALOG_ENTRY_QUERY 00B3E5 2 92 B6 .word KERNEL_CATALOG_ENTRY_GET 00B3E7 2 F7 B6 .word KERNEL_RAWFILE_SEEK 00B3E9 2 82 B7 .word KERNEL_RAWFILE_READ 00B3EB 2 23 B5 .word KERNEL_HANDLER_SET 00B3ED 2 9E B5 .word KERNEL_CONFIGURATION_SET 00B3EF 2 DB B5 .word KERNEL_CONFIGURATION_GET 00B3F1 2 F9 B4 .word KERNEL_SECTOR_READ 00B3F3 2 F5 B3 .word __WARM_BOOT 00B3F5 2 __KERNEL_SERVICES_TABLE_end: 00B3F5 2 00B3F5 2 __WARM_BOOT: 00B3F5 2 4C 5A BA jmp KERNEL__WARMBOOT 00B3F8 2 00B3F8 2 __PANIC: 00B3F8 2 ; System is unstable. The next reset will reboot from the same slot the CB2K was rebooted last time. 00B3F8 2 20 9D BA jsr KERNEL__HW_RESET_HANDLER_REBOOT_SET 00B3FB 2 A9 80 lda #KERNEL_ERR_PANIC 00B3FD 2 A6 EB ldx KERNEL_SUPERVISOR__STACKPOINT 46/89
  • 47. O Supervisor ● A instrução mágica – BRK KERNEL_SUPERVISOR: cli ; Desativamos interrupções. ; O Kernel não sabe ser interrompido, e a R*TS *NÃO PODE* ser interrompida! ; A RTI abaixo restaurará o Status, e se a IRQ estava ativada, ela voltará a estar. .ifndef LANGUAGE_CARD jsr MON_RESTORE ; Pois é... A ROM do Apple IIe faz o favor de, ; trabalho fodástico de resetar o estado da ; anterior para permitir restauro!), tirar da ; (o que eu não queria), e *não manter* o ; virtualmente fodendo com o conceito de ; ; TODO: Mover a CB2K para Language Card, escrever .endif jsr __SAVE_THE_WORLD ldx KERNEL_SUPERVISOR__STACKPOINT ; O Supervisor *NÃO É* reentrante. bne @PANIC lda __REG_P and #%00010000 ; Checa se o BRK STATUS está ativo beq @PANIC ; Se não está, a máquina tá despirocada e o PC caiu ; aqui por acidente! 47/89
  • 48. A (nice) API .define VERSION_MAJOR 1 .define VERSION_MINOR 1 .define VERSION_RELEASE "2012.0901" .macro SYS syscall BRK .byte syscall .endmacro ; This two entries are garanteed to never change or be renamed! CB2K_SYSTEM_PANIC := 0 CB2K_SYSTEM_IDENTIFICATION := 2 + CB2K_SYSTEM_PANIC ; The following entries can, but is unlikely to, change on MAJOR versions. CB2K_FILE_LOAD := 2 + CB2K_SYSTEM_IDENTIFICATION CB2K_FILE_RUN := 2 + CB2K_FILE_LOAD CB2K_FINISH := 2 + CB2K_FILE_RUN CB2K_FILE_SET := 2 + CB2K_FINISH CB2K_FILE_QUERY := 2 + CB2K_FILE_SET CB2K_FILE_GET := 2 + CB2K_FILE_QUERY CB2K_RAWFILE_SEEK := 2 + CB2K_FILE_GET CB2K_RAWFILE_READ := 2 + CB2K_RAWFILE_SEEK CB2K_HANDLER_SET := 2 + CB2K_RAWFILE_READ CB2K_CONFIGURATION_SET := 2 + CB2K_HANDLER_SET CB2K_CONFIGURATION_GET := 2 + CB2K_CONFIGURATION_SET CB2K_SECTOR_READ := 2 + CB2K_CONFIGURATION_GET ; The following entries (if any) can be added on MINOR versions ; CB2K_FUTURE_EXPANSION := 2 + CB2K_SECTOR_READ 48/89
  • 49. Resultados ● Footprint 3.75Kbytes – Kernel, R*TS, Supervisor, buffers, tudo! – E os buffers ainda são configuráveis (on the fly) ● Melhor performance – 6 a 7 Kbytes/s – próximo do limite operacional do dispositivo ● Usa discos formatados pelo Apple DOS 3.3 – Até o FID pode ser usado para povoar seus discos ● Mas eu recomendo o CiderPress. :-) ● Aplicações – Game Loaders – Demos – Outros 49/89
  • 50. Resultados ● Benchmark TK-2000 – Tempo entre ligar a máquina (com o disquete já no drive) e o Prompt do Applesoft : ● DOS: ~31 Segundos (!!!!) ● CB2k: 6 segundos ● DOS + LBoot1: 7 segundos (!!!!) – Tempo para carregar uma tela HGR: ● DOS: 10 segundos ● CB2k: 4 segundos – Espaço livre na RAM (MEMTOP - $800): ● DOS: $9600 - $800 = $8E00 = 35.5Kb ● CB2k: $B000 - $800 = $A800 = 42Kb ● Mas convêm lembrar: – A CB2k faz pouca coisa mais que carregar binários 50/89
  • 51. Por que o DOS é tão lento? ● Os “raw sectors” (342 bytes físicos) são lidos para um buffer intermediário ● Este buffer é então decodificado para os 256 bytes de dados, em um buffer auxiliar ● Estes dados são, finalmente, copiados para o buffer de I/O para leitura pelo programa BASIC ou para a memória destino, se binário ● E o disco continua virando 51/89
  • 52. DOS: Modus Operandi Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 52/89
  • 53. E por que a R*TS ficou tão “rápida”? ● Os raw sectors são decodificados on the fly, indo diretamente para a memória a que se destinam – Sem buffers intermediários, sem memory moves – Exceto o primeiro e o último setor de arquivos binários, que são carregados num buffer de I/O e então copiados para o target para não sobrescrever memória limítrofe ● Era o mais perverso efeito colateral da CompatiBoot original, diga-se de passagem ● Ela não espera pelo próximo setor, mas monta uma lista dos setores desejados e vai carregando na medida em que eles passam debaixo do cabeçote – Não há espera pelo “próximo setor” – Os gap bytes me dão tempo suficiente para recomeçar a leitura entre o fim de um setor e o começo do outro – Mesmo o pior caso leva apenas uma revolução do disquete para ser lido. 53/89
  • 54. CB2k: Modus Operandi Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 54/89
  • 55. Mas então... ● Por que não consertaram antes? – Consertaram! ● Apple – ProDOS ● Terceiros – ProntoDOS – DiversiDOS – CP/M – Mas nenhum deles foi portado para o TK-2000! ● CB2k! :-) – Nem implementaram leitura múltipla! ● CB2k! ;-) 55/89
  • 56. Hands on 56/89
  • 57. Check List ● Café ● Instruções de onde baixar e como instalar: ● Salgadinhos – MINGW – CC65 ● Daft Punk na – CiderPress vitrolinha :-) – AppleWin ● Estes Slides – Emulador TK2000 ● Os fontes do Hello Word ● Imagem de disco – Leia o READ.ME ! ;-) da CB2k (1.1r4a:Set/2012) ● Instruções: – Para montagem do programa, – Importação do binário para uma imagem de disquete – e execução em emulador. 57/89
  • 58. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : jsr ANYKEY .include "system.def" jsr SYSTEM_HGR SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 58/89
  • 59. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 .include "../CB2k.def" ● Configura dialeto do : bne :- processador SYSTEM_HGR jsr ANYKEY .include "system.def" jsr SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY ● Configura prefixo para rótulos NO_FUN: jmp SYSTEM_APPLESOFT_START_COLD jsr SYSTEM_INIT ldy #CB2K_HANDLER_ERROR locaisANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx SYS #>NO_FUN CB2K_HANDLER_SET ● Inclui HEADER: cabeçalhos que jmp MON_RDKEY : PRINT HEADER definem símbolos da HEADER_line_0: .byte 22,0 plataforma 23,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte Lda #90 textz " " : jsr beq MON_WAIT :- ● ; Branch always! Inclui o cabeçalho do Sistema .byte 1,0,0 .byte -1 lda #<MENSAGEM_TEXT Operacional 23,0 ANYKEY_TEXT: .byte ldx #>MENSAGEM_TEXT textz ":" sta stx PRINT_DATA PRINT_DATA+1 ● Inclui o cabeçalho da .byte -1 .include "system.inc" ldy #0 biblioteca de sistema MENSAGEM_TEXT: .include "mensagem.txt" 59/89
  • 60. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" .include "../bios.def" ● Onde começar o programa? bne inc :- PRINT_DATA+1 bne :- : Qual o tamanho do binário? .include "../CB2k.def" – jsr ANYKEY .include "system.def" jsr SYSTEM_HGR SYS CB2K_FILE_LOAD .org $800 ● Difícil preverjsr antes de começar, não? ANYKEY NO_FUN: jsr SYSTEM_INIT – Usa gráficos? jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda ldx #<NO_FUN #>NO_FUN ● Num Apple?PRINT jmp ANYKEY_TEXT MON_RDKEY SYS CB2K_HANDLER_SET ● Num TK-2000? HEADER: : HEADER_line_0: PRINT HEADER dec HEADER_line_1 – Mas o TK sempre usa gráficos! World .byte 22,0 textz "============ Hello !! ============" dec bmi lda HEADER_line_0 :+ #90 – Modo texto? HEADER_line_1: .byte 23,0 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ● ; Branch always!Num Apple? .byte -1 : lda #<MENSAGEM_TEXT ● Num TK-2000? 23,0 ANYKEY_TEXT: .byte ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA – Mas o TK não tem modo texto! .byte -1 stx PRINT_DATA+1 ldy #0 ● Onde é que tá a CB2k mesmo? .include MENSAGEM_TEXT: "system.inc" .include "mensagem.txt" 60/89
  • 61. Hello World Bloco II/A $FFFF $0000 Zero Page Zero Page Extra RAM $0100 Stack Stack Bloco I ROM $0200 Bloco II/A P1 Bloco II/A P0 Extra RAM I/O Buffer I/O Buffer $D000 $0300 Free RAM Free RAM System Pointers System Pointers $0400 $C100 TEXT/GR 80TEXT/DGR Mem Map I/O $C000 Page 1 Page 1 Bloco II/D Sentiram Extra RAM $0800 TEXT/GR 80TEXT/ DGR HGR 2 Page 2 Page 2 Bloco II/D P1 Bloco II/D P0 $A000 $1000 $0000 Zero Page Free RAM Free RAM $0100 Stack $2000 $0200 Key Buffer o drama? Free RAM Free RAM HGR 1 DHGR 1 $4000 $0300 System Pointers $0400 $4000 HGR 1 TEXT/GR Page 1 $4000 HGR 2 DHGR 2 $2000 $0800 HGR 1 TEXT/GR Page 2 $6000 $2000 $1000 Free RAM Free RAM Free RAM Free RAM $2000 $0800 HGR 1 Some System Variables & Free RAM $0400 $C000 Mem Map I/O $4000 System Pointers $0300 Free RAM $C100 Expansion Slot HGR 2 I/O Buffer $0200 ROM Stack $0100 $D000 L.C. P0 L.C. P1 L.C. P1 L.C. P0 Zero Page $0000 $6000 Language Card L.C. P0 L.C. P1 ROM Language Card Main Main $FFFF RAM Free Saturn Bank 7 Main Main AUX $C000 Mem Map I/O L.C. P0 L.C. P1 $C100 Expansion Slot ROM Saturn Bank 1 Main $D000 L.C. P0 L.C. P1 ROM Language Card Main $FFFF 61/89
  • 62. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny ● .include "../sys.def" .include "../bios.def" Algumas opções default bne inc :- PRINT_DATA+1 bne :- .include "../CB2k.def" – Para programas pequenos (pequenos mesmo) : jsr ANYKEY .include "system.def" jsr SYSTEM_HGR .org $800 ● $800 - $1FFF (6 Kbytes) SYS jsr CB2K_FILE_LOAD ANYKEY jsr SYSTEM_INIT – Para programas maiorzinhosSYSTEM_APPLESOFT_START_COLD NO_FUN: jmp ldy lda #CB2K_HANDLER_ERROR ● #<NO_FUN $4000 - $9FFF (~24 Kbytes) ANYKEY: PRINT ANYKEY_TEXT jmp MON_RDKEY Fora disto, e terá HEADER: montar versões que ldx #>NO_FUN SYS ● CB2K_HANDLER_SET : PRINT HEADER específicas para cada máquina Hello World !! ============" HEADER_line_0: .byte 22,0 textz "============ dec HEADER_line_1 dec HEADER_line_0 HEADER_line_1: bmi lda :+ #90 – Use CB2K_CONFIGURATION_GET saber o limite " .byte 23,0 textz " jsr beq MON_WAIT :- superior da memória .byte 1,0,0 ; Branch always! usável .byte -1 : lda #<MENSAGEM_TEXT – Nem sonhe em usar.byte 23,0 no TK-2000! HGR2 ANYKEY_TEXT: ldx #>MENSAGEM_TEXT textz ":" sta stx PRINT_DATA PRINT_DATA+1 ● Até a próxima versão da CB2k, lógico! :-) .byte -1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 62/89
  • 63. Hello World .setcpu "6502" : lda (PRINT_DATA),y ● Inicialização .localchar '@' beq jsr :+ PRINT_ASCII .include "../hw.def" iny – Biblioteca SYSTEM .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 ● Configura manipulador de Erro bne :- .include "../CB2k.def" : – Se algo der errado, inicializa o Applesoft e dá o prompt jsr ANYKEY jsr SYSTEM_HGR pro usuário "system.def" .include SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 63/89
  • 64. Hello World ● LOOP (até "6502" a linha da primeira zString seja menor que 0) .setcpu que : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII – PRINT (macro em SYSTEM.DEF) .include "../hw.def" iny .include "../sys.def" bne :- Imprime <n> zStrings .include ● "../bios.def" (terminada em 0, C-style) em inc posições específicas da tela PRINT_DATA+1 bne :- ● (Rotina de SYSTEM.INC) .include "../CB2k.def" : jsr ANYKEY – Pausa de ~25 mSecs .include "system.def" jsr SYS SYSTEM_HGR CB2K_FILE_LOAD .org $800 jsr ANYKEY ● (Rotina na ROM) NO_FUN: – jsr NotarSYSTEM_INIT que MON_WAIT sempre volta com ZeroFlag em 0. jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: ● ldaNotar os branchs relativos anônimos! ldx #<NO_FUN #>NO_FUN PRINT jmp ANYKEY_TEXT MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 64/89
  • 65. Hello World ● Dois loops: .setcpu "6502" : lda beq (PRINT_DATA),y :+ .localchar '@' – O interno, “driven” pelo Y jsr PRINT_ASCII .include "../hw.def" iny ● O INY “overflows” para 0 depois do 255. .include "../sys.def" bne :- ● BNE :.include último resultado da ULA não deu em zero pula se o "../bios.def" inc PRINT_DATA+1 bne :- – O externo, “driven” pelo último valor lido em Acc .include "../CB2k.def" : jsr ANYKEY BEQ: .include "system.def" em Acc for zero, sai do ● Se o último byte carregado jsr SYSTEM_HGR loop. SYS CB2K_FILE_LOAD .org $800 – BEQ/BNE e outros atuam em cima do Registrador jsr ANYKEY de Status (P) NO_FUN: jsr reflete o SYSTEM_INIT operação da ULA, ou da ●Que status da última jmp SYSTEM_APPLESOFT_START_COLD última carga em registrador ldy #CB2K_HANDLER_ERROR ANYKEY: – PRINT_ASCII#<NO_FUN lda PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY ● Imprime o caractere ASCII no Acc SYS CB2K_HANDLER_SET ● PRINT_DATA HEADER: ● : Dirty and Tricky! HEADER_line_0: – Duas posições na página zero (escolhidas à PRINT HEADER .byte 22,0 – Eu sei que a única forma do INC dar em zero é dec HEADER_line_1 PRINT_DATA HEADER_line_0 acabar apontando para a página zero dedo!) para servir deHello World !! ============" textz "============ ponteiro para o buffer do dec HEADER_line_1: –bmi nunca :+ armazena strings! ;-) onde se texto a 23,0 impresso .byte ser lda #90 textz " " – Na prática, pula sempre! – Estas instruções ocupam 2 bytes, e não 3! .byte 1,0,0 jsr MON_WAIT beq :- ; Branch always! .byte -1 : ● Usaremos o Y como indexador no loop que lda #<MENSAGEM_TEXT vem a seguir ANYKEY_TEXT: .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA – Inicializa em .byte -1 0! stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 65/89
  • 66. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny ● Aguarda por"../sys.def" .include uma tecla (não .include "../bios.def" bne inc :- PRINT_DATA+1 importa qual"../CB2k.def" .include : bne jsr :- ANYKEY .include "system.def" jsr SYSTEM_HGR ● Entra em modo gráfico .org $800 SYS jsr CB2K_FILE_LOAD ANYKEY ● Carrega o SYSTEM_INIT arquivo jsr próximo NO_FUN: jmp SYSTEM_APPLESOFT_START_COLD binário do #CB2K_HANDLER_ERROR ldy lda catálogo #<NO_FUN ANYKEY: PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY – É uma tela HGR SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: EuHEADERHEADER_line_1 coloquei lá! PRINT ● dec sei, fui eu que .byte 22,0 textz "============ Hello World !! ============" – A CB2k já o deixou 'na agulha' dec bmi HEADER_line_0 :+ HEADER_line_1: .byte 23,0 lda #90 textz " " quando carregou o programa jsr MON_WAIT .byte 1,0,0 .byte -1 beq :- ; Branch always! : corrente, basta a chamada para ANYKEY_TEXT: carregá-lo lda ldx #<MENSAGEM_TEXT #>MENSAGEM_TEXT .byte 23,0 textz ":" sta PRINT_DATA .byte -1 ● Ver CB2K_FILE_SET se não é o que stx PRINT_DATA+1 .include "system.inc" você quer ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 66/89
  • 67. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : ● Aguarda.include "system.def" por outra tecla jsr jsr ANYKEY SYSTEM_HGR SYS CB2K_FILE_LOAD ● Encerra,.org $800 inicializando o Applesoft. jsr ANYKEY NO_FUN: – A CB2k ainda tá na memória, mas não dá jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD suporte ao BASIC ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT – Mas você pode brincar no MiniAssembler! ldx SYS #>NO_FUN CB2K_HANDLER_SET jmp MON_RDKEY HEADER: : ● Se você estiver num Apple //e ou num TK- HEADER_line_0: PRINT HEADERa Tomato Board revisada 2000 com HEADER_line_1 .byte 22,0 dec textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 67/89
  • 68. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : ● Dirty and Tricky! "system.def" .include jsr jsr ANYKEY SYSTEM_HGR SYS CB2K_FILE_LOAD – A anykey, por ser uma subrotina, deveria .org $800 jsr ANYKEY terminar com um RTS NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD – Mas ela por sua vez se vale de outra rotina na sua última#CB2K_HANDLER_ERROR ldy lda instrução, economizei um byte #<NO_FUN ANYKEY: PRINT ANYKEY_TEXT (2 duas posições da pilha) fazendo um JMP ldx SYS #>NO_FUN CB2K_HANDLER_SET jmp MON_RDKEY pra dita cuja. HEADER: : HEADER_line_0: ● O RTS dela é quem faz o retorno a quem PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" chamou a ANYKEY. dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 68/89
  • 69. Aplicações ● Demos! :-) – No arquivo de Distribuição da CB2k você encontrará o fonte para todos os programas de demonstração. ● Console I/O independente de máquina – Conversão automática para maiúsculas em máquinas sem caracteres minúsculos ● Sintetização de SOM! – Eletric Duet / Paul Lutus ● Exemplos mais complexos da API da CB2k – Carregamento e/ou execução de arquivos – Leitura do Diretório – Handlers de sistema ● Tratamento te exceções ● RESET 69/89
  • 70. Aplicações ● Agora: – Beautiful Boot ● Jogos! Yeay! :-) ● Porte feito por Fábio Belavenuto ● Na agulha: – Basic.system para o TK-2000 ● Uma solução definitiva para a fragmentação da memória do BASIC no TK-2000 ● RDOS style – Novas Demos para a CB2k ● Técnicas de animação e sintetização de Som simultâneos ● O TK-2000 pode, o TK-2000 faz! :-) ● Futuro: – Substituto para o RDOS no Apple II ● Tão logo eu crie coragem e escreva as rotinas de gravação de setores... – Suporte transparente para outras mídias ● Enquanto a API for estável, tanto faz de onde vêm os bytes! – Arquivos de “Overlay” 70/89
  • 71. $A000 Known Issues HGR 2 $C000 Mem Map I/O $C100 $D000 Extra RAM ROM Bloco I ● Código não relocável dinamicamente $FFFF – O S.O. está amarrado ao topo da memória principal (pouco antes da área de I/O) – Ruim para o TK-2000, pois sua segunda página de vídeo está lá. ● Jogos que usam paginação vão matar o S.O. – Desperdiça a Bloco I / Language Card ● Menos memória “segura” para os programas – Que pra começo de conversa não foram feitos para conviver com um sistema operacional de disco! :-) 71/89
  • 72. Known Issues ● Read Only – A CB2k não grava. – “By Design” =P ● Um processo complicado e ainda mais time critical. ● Até o momento, baixa demanda. ● Implementar gravação vai aumentar o footprint na memória ● No LIBS – A “biblioteca” não passa de um include sofisticado ● Raios, o S.O. todo tá pendurado assim! – Uma LIB estática é uma demanda forte ● LIB dinâmica é sonho de consumo! ● Incompatibilidade com a CFFA 3000 – Ainda investigando... 72/89
  • 73. Considerações Finais ● Lições (Re)Aprendidas – Projetos pessoais ainda são Projetos! – Realidade Comanda – Wear Sun Screen! :-) ● Onde aprender mais? ● Onde obter ajuda? 73/89
  • 74. Projetos Pessoais ainda são Projetos ● Boas práticas também não têm este nome à toa! – Xtreme Programming! – Rubber Ducking! ;-) ● Eu me estrepei muito por não ter seguido algumas destas práticas desde o começo ● E tive meu traseiro poupado de trágico destino por ter seguido outras 74/89
  • 75. Projetos Pessoais ainda são Projetos ● Version Control System – RCS, CVS, SVN, GIT, Mercurial, Bazaar ● Qualquer um, qualquer um mesmo! – Até copy&paste em diretórios no seu HD! ● Gerência de Configuração – Procure saber em quais ambientes (e configurações) o seu software vai rodar ● Mesmo que não possa garantir o funcionamento em todos! ● Principalmente para poder garantir o funcionamento em alguns! 75/89
  • 76. Projetos Pessoais ainda são Projetos ● Use Cases e Back Logs – Formalismos não são necessários ● mas se você não especifica o quê você quer resolver, você não resolve é nada... – Gold-plating não é legal. – Um arquivo texto com um parágrafo por Requisito / UC / Whatever já é suficiente, o importante é que todos os envolvidos saibam do que se trata ● Principalmente quando “todos os envolvidos” é só você! :-) – O tempo passa e não tem mais ninguém pra lhe lembrar do que você tem que fazer! ● Versione! Versione!! – Foco, ou você não termina esta joça! 76/89
  • 77. Projetos Pessoais ainda são Projetos ● Fail early, Fail often! – Unit Tests ● Imprescindíveis ! :-) ● Mas eles custam caro, não subestimem o impacto no “orçamento” . – Alguns bugs são mais baratos de serem consertados (se ocorrerem) que prevenidos – Você não tem tempo (nem dinheiro) pra fazer tudo o que quer. – Test Cases / Test Suites ● Porque testes de unidade não são capazes de pegar erros de integração que teimam em ocorrer – E sempre nos piores momentos possíveis! :-) ● As aplicações de exemplo são meus Test Suites públicos! 77/89
  • 78. Realidade Comanda ● Eat your own dogfood! – É só aplicando na vida real que você tem certeza se uma idéia realmente funciona. ● Ou não! ¬¬ – Você é seu primeiro e primário beta-tester. ● Use seu produto, encontre você mesmo seus erros – Ou outros o farão por você 78/89
  • 79. Realidade Comanda ● Beta testers – Eu não teria conseguido sem ajuda! ● Sem eles, e você desenvolve no escuro – Exceto se dispor de recursos financeiros para comprar tudo em que bate os olhos! ;-) – Mas eles não serão muito úteis se você não fizer seu dever de casa: ● Use Cases ● Test Cases ● Gerência de Configuração ● Versionamento de Código – Foi aqui que eu percebi que estava atirando no meu próprio pé ao “agilizar” o desenvolvimento ao custo de algumas boas práticas... 79/89
  • 80. Realidade Comanda ● Não subestimar a importância de um bom Error Report – Porque você *NUNCA* pegará todos os erros. ● Principalmente os bobos – Erro grave explode logo, são os bobos que dão trabalho! 80/89
  • 81. Realidade Comanda KDIFF3 é pra vida! :-) 81/89
  • 82. Links Relacionados ● CB2k – Suite de Testes – Debut da CB2k (Apple //e) – Debut² =P no TK-2000 ● Slides da palestra ● http://pt.wikipedia.org/wiki/Apple_II ● http://pt.wikipedia.org/wiki/TK2000 ● http://retro.lisias.net/ 82/89
  • 83. Links Úteis ● http://www.6502.org ● http://www.cc65.org/ ● http://applewin.berlios.de/ ● http://www.fabio.belavenuto.nom.br/tk2000/ ● http://www.datacassete.com.br/ ● ftp://ftp.apple.asimov.net/pub/apple_II/ ● http://www.applefritter.com/ ● http://www.extremeprogramming.org/ ● http://www.codinghorror.com/blog/2012/03/rubber-duck-problem-solving.html ● Ajuda Especializada 0:-) 83/89
  • 84. Links Interessantes ● Paul Langhton – Consultor responsável pelo Apple DOS ● Steve Wozniak – Responsável por todo o resto! :-) ● Apple II History – História do Apple II, versão do usuário. ● ASCII Express' Game Server – “Servidor” de jogos, com download em formato de áudio otimizado – Para máquinas “diskless” 84/89
  • 85. Links “Interessantes” =P ● Câmara de Torturas (ou: se Donatien Alphonse François fosse Analista de Sistemas) – Restauro e 'Mods' do TK-2000 ● E outras vítimas – Outros clássicos ● Alguns poucos conhecidos por aqui – Outros loucos ● Porque gostamos de companhia. O:-) 85/89
  • 86. (alguma) Literatura Recomendada ● How to program the Apple II using ● Software Control of the Disk II or IWM 6502 Assembly Language Controller – DATAMOST, 1982 – Norman Leung – Randy Hyde – Apple Computer, 1984 – Featuring LISA Assembler ● Andrew S. Tanenbaum ● Beneath Apple DOS / – Eternamente :-) Beneath Apple ProDOS ● Microcomputadores e Microprocessadores – Don Worth & Pieter Lechner – Albert Paul Malvino – Quality Software, 1982 – McGraw-Hill, 1985 ● Understanding the Apple II ● The Pragmatic Programmer: From – James Fielding Sather Journeyman to Master – Quality Software, 1983 – Andrew Hunt & David Thomas – Com Introdução do Woz! :-) – Addison-Wesley Professional, 1999 86/89
  • 87. Onde Obter Ajuda ● Lista appleII_br ● Newsgroup comp.sys.apple – E os diversos subgrupos desta hierarquia ● me@lisias.net ;-) ● Ajuda Especializada 0:-) 87/89
  • 88. Free Chat ● Dúvidas? ● Comentários? ● Sugestões? ● Apoio moral? – (Piada interna da appleII_br) – *<8o) 88/89
  • 89. Obrigado! @lisias me@lisias.net http://tk2k.lisias.net/CB2k 89/89 Boldly crashing what no man has crashed before!
  • 90. Um Carregador Rápido para TK-2000 e Apple II que virou Sistema Operacional http://tk2k.lisias.net/CB2k
  • 91. Premissa i.Restaurar um obscuro computador doméstico de quase 30 anos de idade ii.Escrever um sistema operacional pro dito cujo iii.????? iv.PROFIT! :-) Piadinha básica #Slashdot
  • 92. @Lisias | http://lisias.net 3/89 Perfil profissional Enfase na esperiência (porque se depender da competência... X-P) Para o bem e para o mal, botei minhas patas sujas em várias áreas diferentes (e mesmo conflitantes) da Computação Metade elas terem sido compradas pelos concorrentes não foi minha culpa! X-)
  • 93. @Lisias http://retro.lisias.net 4/89 Perfil pessoal Maníaco da Chave de Fenda Não tem nada aqui em casa que eu já não tenha desmontado. Ou destruído. =P Breve histórico da minha iniciação na computação Apple II TK-2000 dos amigos MSX e Amiga de outros
  • 94. As Vítimas ● Scene Retrô brasileira de Apple II e Compatíveis (ou quase) – Intensa movimentação nos últimos 18 meses ● Inúmeras novidades – engenharia reversa do Cartucho Controlador de Discos do TK-2000 – Tomato Board 5/89 ●Scene Retrô brasileira de Apple II e Compatíveis (ou quase) ● Intensa movimentação nos últimos 18 meses ● Não apenas ela, diga-se de passagem ●Inúmeras novidades ● engenharia reversa do Cartucho Controlador de Discos do TK-2000 ● Atualmente raro e dispendioso ● Tomato Board, uma plaquinha adaptadora que permite usar interfaces Disk II do Apple no slot do TK-2000 ● Ironia das ironias, o Cartucho de Disco do TK- 2000 (ou do original, o MPF-II) foi desenvolvido através de engenharia reversa na Disk II :-)
  • 95. O Motivo ● Acesso à Hardware equivalente, mais barato e abundante, da linha Apple ● Mas os jogos (e parte significativa dos demais softwares) ainda estavam em formato Cassete ● Soluções (software) prontas, importadas do Apple II, eram – Muito complexas para portar ● ProntoDOS, DiversiDOS, ProDOS – todos ótimos, mas sistemas operacionais completos! – Overkill – Over memory :-) 6/89 ●As Interfaces de Disco e Drives de Apple II são relativamente baratos ● E, de um mês para outro, diversos TK-2000 ganharam acesso à disquetes! ●Mas os jogos (e parte significativa dos demais softwares) ainda estavam em formato Cassete ● (ou equivalentes modernos como MP3 e CT2) ● sendo carregados pela porta de Audio! ● Convertê-los para formato de arquivo é relativamente fácil ● ainda em andamento, na medida em que os títulos são resgatados ● Fazê-los funcionar debaixo do TK-DOS nem tanto ● E não enlouquecer esperando o boot acontecer ainda menos. ●Soluções importadas do Apple II não atendiam ● As diferenças estruturais entre as máquinas não permitem um reuso direto ● As soluções simples invariavelmente eram limitadas ou incômodas ● Não extensíveis, não adaptáveis ● Hacks interessantes e úteis, mas feitos por hackers para hackers e resolvem um problema específico com o menor custo ● As soluções completas eram muito complexas para portar ● ProntoDOS, DiversiDOS, ProDOS ● todos ótimos, mas sistemas operacionais completos! ● Overkill ● Over memory :-)
  • 96. Enquanto isto... ● “lá fora” (news:comp.sys.apple) – CompatiBoot original (Raven/C700 Club) ● Rápida ● Prática ● Mas não adequada – Capenga no TK-2000 – One shot only – Altas gambiarras pra convencer a dita cuja a fazer o que precisávamos – Efeitos colaterais diversos e inesperados 7/89 ● Enquanto isto, “lá fora” (news:comp.sys.apple) ● Com problemas parecidos, soluções “quick & dirty” foram desenvolvidas e publicadas, dentre elas a CompatiBoot original (Raven/C700 Club) ● teve boa recepção na lista appleII_br ● Hiper rápida ● “Herdeira” das rotinas de disco usadas na eZine francesa Dox-a-gaz (circa 1988), de autoria de Max-a-gaz. ● “Herdeira” do utilitário de cópias “Locksmith”, da Omega Microware (circa 1985) ● Super prática ● Basta copiar o binário para a primeira entrada do catálogo e dar boot. ● Mas capenga no TK-2000 ● One shot only ● Altas gambiarras pra convencer a dita cuja a fazer o que queríamos ● Efeitos colaterais diversos e inesperados
  • 97. Indo direto ao ponto ● Benchmark : TK-DOS 3.3 – Tempo entre ligar a máquina (com um disquete com boot no drive) e o Prompt do Applesoft: ● 31 segs. – Tempo para carregar uma tela gráfica HGR: ● 10 segs – Espaço livre na RAM depois de carregado: ● ~ 24 Kbytes. – Não, não é Mega. É Kilo mesmo! :-) ● Demais S.O.s – Overkill ● Outras Soluções – Não são práticos nem flexíveis – São perdulários – Não funcionam, ou o fazem porcamente, no TK-2000 8/89 ●O Apple/TK DOS 3.3 ● É muito “grande” ● É muito lerdo ●Demais S.O.s ● Overkill ●Fast Loaders legados ● Não são práticos nem flexíveis ● um saco criar o disco de boot! ● Armazenam dados controlando diretamente os setores do disco ● Sem diretórios ● Atualização/manutenção impraticável ● São perdulários ● Um disco por jogo, mesmo que 10 deles caibam no disquete ● Não funcionam, ou o fazem porcamente, no TK-2000
  • 98. O Crime “Hummmm...” Groo faz o que... “Eu acho que faço melhor!” 9/89 As 5 palavrinhas que antecedem uma grande descoberta. Ou um tremendo desastre...
  • 99. Advertência O uso indiscriminado e Podem causar danos concomitante de irreversíveis à/ao – Linguagem Assembler – Sanidade mental – Rotinas de Tempo Real – Computadores Vintage – Relacionamentos amorosos – Conceitos (nem tão assim) – Vida social avançados de Arquitetura de Computadores e Sistemas – Convivência familiar Operacionais – Organização domiciliar – Café, cerveja, pizzas, lanches e – Paz condominial snacks – EL&P, Rick Wakeman, Jean Michel – Perímetro da sua cintura :-) Jarre, Vangelis, Daft Punk e Kraftwerk Depois não digam que a culpa é minha!! :-) 10/89 Porque não há prazer sem dor!
  • 100. Planejando a ação ● A CB2k deve: – Carregar arquivos com a maior eficiência possível – Permitir carregar programas que querem ocupar o espaço onde normalmente ficaria o DOS – Ser prática para criar/atualizar disquetes – Oferecer uma API consistente para programação – Fornecer exemplos de como desenvolver aplicações 11/89 ●A CB2k deve: ● Carregar arquivos com a maior eficiência possível ● Ninguém quer esperar pra brincar! ● Permitir carregar programas que querem ocupar o espaço onde normalmente ficaria o DOS ● menor footprint possível na memória principal ● (a mais concorrida) ● deve permitir ser movida para diferentes posições de memória ● Para se acomodar mesmo com aqueles jogos “mais chatos” ● Ser prática para criar/atualizar disquetes ● Usar o formato do Apple DOS 3.3 ● Todo mundo conhece ● Ferramentas conhecidas para suporte ●A CB2k também deve: ● Oferecer uma API consistente para programação ● API deve proteger as aplicações de: ● Mudanças nos endereços das rotinas do kernel ● (assim eu posso movê-lo pra cima e pra baixo, de acordo com a conveniência) ● Mudanças de formato de mídia (e até mesmo de mídia!) ● Disquetes estão ficando raros ● Facilitar Novas Aplicações! ● Jogos multi-partes (Karateka) ● Jogos BASIC com mais memória disponível ● Algo importante principalmente para o TK-2000 ● Menus para os jogos ● Demos ● Fornecer exemplos de como desenvolver aplicações ● Sistemas Operacionais não são nada sem aplicações!
  • 101. Planejando a ação ● A CB2k não pode deixar de: – Ser extensível e portável – Ficar pronta em umas 4 ou 5 semanas. ● Férias acabam! – Ser útil e agregar valor ● Demais funcionalidades (rede, ambiente gráfico, co-processamento, etc.) – são totalmente fora de escopo ● Hoje! ;-) 12/89 ●A CB2k não pode deixar de: ● Ser extensível e portável ● Outras arquiteturas baseadas em 6502 (porque não?) ● Outras mídias (porque não?) ● Ficar pronta em umas 4 ou 5 semanas. ● Férias acabam! ● Ser útil e agregar valor ● Na boa: ninguém precisa de ainda outra solução meia-boca pra ficar quebrando galho... ●Demais funcionalidades (rede, ambiente gráfico, co- processamento, etc.) são totalmente fora de escopo. ● Linus é um cara legal, não quero concorrer com ele! ;-) ● Ele ganha...
  • 102. It's coding time! ● BELEZA!! Já sei o que quero fazer, agora é só ligar a máquina e... Oh, wait... – Como se programa nesta joça? 13/89
  • 103. First Things First code “One does not simply walk into Mordor!” Boromir, The Fellowship of the Ring 14/89 Rapadura é doce, mas não é mole não! Quando se programa um Sistema Operacional, por mais simples que seja, você passa a ser provedor de serviços, e não mais consumidor! Você vira o juiz de futebol: tudo agora é sua culpa. Uma bela mudança de paradigma... (Comentei que sou paranóico?) X-D
  • 104. Programação de Baixo Nível Não tem este nome à toa... ● O legendário 6502 ● Arquitetura dos Computadores – Apple II+ – MPF-II/TK-2000 – Semelhanças e diferenças entre as máquinas target ● Disquetes: um problema em tempo real – A Shugart – A Disk II do Woz – Persistência de dados em mídias magnéticas 15/89 Comumente chamada de “Programação de Baixo Calão” - vocês não imaginam o que se houve de um programador ASM estressado...
  • 105. O 6502 ● Registradores ● Instruções ● Clock Cycle Time – Cycle para os íntimos ● T States – A únidade básica de tempo do processador – A únidade básica de ansiedade do programador ● Os diferentes Endereçamentos à memória – O segredo do sucesso! – A Salvação da Pátria! ● O primeiro RISC? ● Sucessores – 65C02 – 65816 16/89
  • 106. $0000 Zero Page $0100 Stack O 6502 A 7 6 5 4 3 2 1 0 X Y 7 6 5 4 3 2 1 0 7 6 5 4 3 2 1 0 S P 7 6 5 4 3 2 1 0 N V 1 B D I Z C PC 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ● Load / Store ● Trasnfer ● ROR, ROL, SHL, SHR – Pero no mucho! – AX, XA – A Free Addresses – AY, YA #imm ● LD / ST ● – XS, SX ● Abs – [A,X,Y] #imm ● Branchs ● Abs,X – A abs,X – EQ / NE (Zero Flag) ● Abs,Y – A abs,Y MI / PO (Minus Flag) – ● (Indi,X) – A (indi,X) – CS, CR (Carry) ● (Ind),Y – A (indi),Y – VS, VC (Overflow) ● ADC, SBC ● JMP ● P (Status) – A – JMP abs – SEC, CLC ● #imm – Etc Abs – JMP (indi) ● ● INC / DEC ● Abs,X ● JSR / RTS – A, X, Y ● Abs,Y ● Stack – Abs ● (Indi,X) – PHA / PLA – Abs,X (Ind),Y $FF00 ● ROM – PHP / PLP – Abs,Y Muito Mais! 17/89 $FFFF ● Ênfase no mapa de memória – todo computador baseado no 6502 tem este “jeitão” Ênfase na importância dos modos de endereçamento, em particular, página 0
  • 107. O Apple II+ ● Hardware – Memory Mapped I/O – Modos de vídeo – Mapa da RAM ● ROM – Principais entry-points – Uso da Página Zero ● Console I/O – Teclado – Caracteres 18/89
  • 108. $0000 Zero Page O Apple II+ $0100 Stack $0200 I/O Buffer Free RAM $0300 System Pointers $0400 TEXT/GR Page 1 ● Buffer de I/O $0800 – Usado pelo sistema (e pelo DOS) para TEXT/GR Page 2 entrada e saída de dados $1000 ● Teclado Free RAM ● Disco $2000 ● Etc. HGR 1 ● 2 Páginas de texto – 1 delas pode ser usada para programação $4000 HGR 2 ● 2 Páginas de gráficos – Ambas podem ser usadas para programação $6000 ● A ROM pode ser “sombreada” por um L.C. P0 mecanismo chamado “Language Card” L.C. P1 Free RAM Saturn Bank 7 – A LC é dividida em 3 bancos Main ● 1 Principal ● 2 Secundários, que dividem o mesmo $C000 Mem Map I/O L.C. P0 L.C. P1 endereço $C100 – A LC pode ser expandida através de bancos Expansion Slot ROM Saturn Bank 1 de memória Main $D000 ● Saturn 128Kb. L.C. P0 L.C. P1 ROM Language Card Main 19/89 $FFFF Notar o topo da memória livre, onde fica o DOS. (Importante para entender alguns dilemas com relação ao TK-2000)
  • 109. O Apple II+ ● Teclado “ASCII” – Um uC faz o serviço sujo para você – Curto e Grosso ● E simples de ler! – Mas um saco para os jogos ● Control e Shift não são dectáveis sem mods ● Combinações de teclas (que não envolvem as modificadoras acima) são impossíveis de serem detectadas – A segunda sobrescreve a primeira, e ponto final ● Caracteres – ASCII ● Alfanuméricos ● Suporte à Minúsculas opcional (!!!) – Inverso e Flash 20/89
  • 110. O MicroProfessor II e seu primo brasileiro TK-2000 ● Hardware – Memory Mapped I/O – Modos de vídeo – Mapa da RAM ● ROM – Principais entry-points – Uso da Página Zero ● Console I/O – Teclado – Caracteres 21/89 Curiosidade. O MPF-II foi concebido por uma empresa chamada Multitech – que mais tarde passou a se chamar Acer. Por um acaso, a Acer fabricou o laptop que estou usando na palestra – coincidência interessante!
  • 111. $0000 $0100 Zero Page Stack O MicroProfessor II e seu primo brasileiro $0200 I/O Buffer TK-2000 Free RAM $0300 System Pointers $0400 Free RAM & Some System Variables ● 2 páginas de gráficos $0800 – Como não há modo texto, uma delas Free RAM obrigatoriamente precisa estar em uso pelo sistema $2000 – O TK-DOS ocupa quase toda a página 2 :-( HGR 1 ● ROM pode ser programaticamente $4000 HGR 1 substituída pelas Extra RAM ● Bloco I : 15.75 Kbytes Free RAM ● Bloco II : 4 bancos de 16Kbytes – 1 banco de 8 kbytes $A000 – 2 sub-bancos de 4 kbytes Bloco II/D P0 Bloco II/D P1 HGR 2 – Saturn 64Kb! :-) Extra RAM ● O meu tem 128Kb! :-) $C000 Mem Map I/O Bloco II/D $C100 ● Apenas um Bloco pode estar ativo num momento $D000 Bloco II/A P0 Bloco II/A P1 ROM Extra RAM – Os bancos do Bloco II precisam escolher qual Bloco I Extra RAM página de 4 kbytes deve estar ativa Bloco II/A $FFFF 22/89 Notar o topo da memória livre. Agora ali tem uma página HGR, o que foi boa ideia porque expande o bloco de memória usável caso o programa decida por usar a página 2 como display. Mas no Apple, esta memória era livre e foi ali que o DOS foi parar. Moral: no TK-2000, não se pode ridar jogos com animação complexa (com paginação de vídeo).
  • 112. O MicroProfessor II e seu primo brasileiro TK-2000 ● Teclado com a Matriz exposta – Sem um MicroControlador pra fazer o serviço pesado – Vantagens ● Acesso individual (e múltiplo!) ao estado de cada tecla – permite algumas combinações interessantes para jogos – Desvantagens ● Gasto de processamento para ler o teclado ● Principal e maior motivo da “má fama” do TK-2000 – A rotina do fabricante, oferecida no Manual Técnico como alternativa à leitura do teclado do Apple II era porca – simples assim – Um dos principais artefatos secundários do projeto: ● Uma rotina rápida de leitura de teclado! :-) – Caracteres ● ASCII – Alfanuméricos – Sem suporte às minúsculas (!!!) ● Semigráficos Fonte: pág.21 TK2000/II Manual Técnico Microdigital Eletrônica LTDA 23/89
  • 113. $0000 $0100 Zero Page Stack O Apple //e & //c Zero Page Stack $0200 $0300 I/O Buffer Free RAM System Pointers (porque todo castigo...) I/O Buffer Free RAM System Pointers $0400 TEXT/GR 80TEXT/DGR Page 1 Page 1 $0800 ● Revisões TEXT/GR 80TEXT/ DGR Page 2 – Apple // Extended Page 2 $1000 Free RAM ● 6502 Free RAM $2000 – Apple //c, //e Enhanced e Platinum HGR 1 DHGR 1 ● 65C02 $4000 ● “Mouse Chars” HGR 2 ● DTEXT (80 COLs), DGR & DHGR DHGR 2 $6000 ● 128Kb – Mas num esquema totalmente diferente Free RAM Free RAM – Descreve isto, Lisias! ● Nah... Deixa quieto! =D $C000 Mem Map I/O $C100 Expansion Slot Extension ROM ROM $D000 L.C. P0 L.C. P1 L.C. P1 L.C. P0 Language Card ROM Language Card Main Main $FFFF 24/89 Main AUX Sem chance de dar suporte nativo ao Apple //e. Uma versão específica para ele teria que ser feita, mas esta máquina simplesmente não precisa de mais um carregador rápido – muito menos, de um sistema operacional. Manter a coisa rodando nele é interessante, mas fazer algo pra ele é chover no molhado – não sou necessário aqui.
  • 114. Resumo da Ópera ● As diferenças da ROM enchem o saco – Oferecer uma camada de “abstração” da ROM seria bacana, mas exigiria mais memória ● Mas não sai de graça ● As diferenças na memória principal são facilmente gerenciáveis – Mas o mesmo não acontece com os bancos de memória estendida ● E lá se vão funcionalidades pela janela ● O 65C02 têm instruções extras que seriam (muito) úteis – Maior densidade de código e mais “semântica” por ciclo de clock ● TXY (1 byte, 2 Ciclos) – PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!) – STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma posição da ZP) – STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos) – Mas alienaria o TK-2000 e o Apple II+ 25/89 ●As diferenças da ROM enchem o saco ● Oferecer uma camada de “abstração” da ROM seria bacana, mas exigiria mais memória ● Mas Consumir memória sem apelar para a memória estendida compromete a compatibilidade com software legado (os jogos!) ● Dar suporte à memória estendida exigiria código específico para esta tarefa ● E cada máquina usa uma arquitetura diferente... ● Então cada máquina tem seu próprio código de gerenciamento de memória ● Então eu tenho que praticamente escrever 3 S.O.s diferentes! ●As diferenças na memória principal são facilmente gerenciáveis ● Mas o mesmo não acontece com os bancos de memória estendida ● O que limita a quantidade de código que eu posso socar no Kernel ● O que limita as funcionalidades do Kernel! ●O 65C02 têm instruções extras que seriam (muito) úteis ● Maior densidade de código e mais “semântica” por ciclo de clock ● TXY (1 byte, 2 Ciclos) ● PHA ; TXA ; TAY ; PLA (4 bytes, 10 ciclos!) ● STX <ZP_ADDR>; LDY¨<ZP_ADDR> (4 bytes, 6 ciclos – mas gasta uma posição da ZP) ● STX <ABS_ADDR>; LDY <ABS_ADDR> (6 bytes, 8 ciclos) ● Mas alienaria o TK-2000 e o Apple II+
  • 115. Mas não é só isso! 26/89 Nunca é! :-)
  • 116. Mídias Magnéticas ● Revoluções Por Minuto Mas sem as louras geladas... =/ – Densidade Magnética ● Coerção ● Histeresys – Velocidade Angular “constante” versus Velocidade Linear “constante” ● (Constante, o escambau! O motor não é estável...) – Largura de Banda – Desgaste físico! 27/89 O mundo analogico não é “limpo”. Da mesma forma que pra toda ação corresponde uma reação, para cada atitude temos um efeito colateral que precisa ser considerado. Quanto mais densa a mídia magnética, mais coerção eletromagnética você sofre, demandando mais energia no cabeçote ou menor velodicade de rotação (ou ambos). A histerese é outro problema, pois ela dá um “delay” no tempo necessário para se transmitir a energia no meio ferro-magnético – e ainda deixa resíduo para quem vem atrás. Ajustar a velocidade do motor é equilibrar este castelo de cartas, está mais para magia negra que engenharia. :-)
  • 117. Discos Magnéticos ● As trilhas não têm todas o mesmo tamanho físico. – Perímetro é função do raio! ● Mas tem o mesmo tamanho lógico... – Velocidade angular constante ● Densidade dos dados varia em função da trilha ● Pragmatismo – A Shugart ajustou o mecanismo para ser confiável na trilha mais interna, e desperdiçou densidade nas mais externas – Drives mais sofisticados (e caros) variam a velocidade do motor em função da trilha ● aproveitar melhor a densidade da mídia 28/89
  • 118. Discos Magnéticos ● Os dados são gravados (re)alinhando polaridade na superfície da camada de óxido de ferro – Descobriu-se não ser eficiente usar uma polaridade para o bit 1, e outra para o bit 0 ● Mudança de polaridade na linha do tempo indica bit 1 ● Não mudança de polaridade na linha do tempo indica bit 0 ● Mas o motor não consegue fornecer uma velocidade constante ao nível do microsegundo – Pequenas variações no motor “distorcem” o comprimento de um bit – Dada uma distância longa o suficiente sem inversão de polaridade, o hardware não sabe mais quantos bits '0' foram lidos... 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ? ● As inversões de fase, então, são usadas como “clock” para a leitura dos dados 29/89 ●Logo, não posso gravar qualquer byte no disco, pois algumas combinações de bits não são legíveis ● Boa parte dos bits são “desperdiçados”, pois têm que ficar obrigatoriamente em '1' ● Para gerar a inversão de fase, que serve de clock para a identificação dos bits... ●Codificações usadas pela indústria: ● GCR – Group Code Recording ● Adotada pelo Apple ● Originalmente, a interface Disk II não conseguia ler dois bits '0' seguidos ● Codificação 5x3 – 5 bits de dados intercalados com 3 bits '1' de clock ● Numa revisão posterior do hardware, o hardware passou a ser capaz de detectar 2 bits 0 seguidos (mas apenas uma vez por byte) ● Codificação 6x2 – 6 bits de dados intercalados com 2 bits '1' de clock, ● MFM – Modified Frequency Modulation ● RLL - Run Lenght Limited ● EFM – Eight to Fourteen Modulation ● Outras
  • 119. Discos Magnéticos ● Mas isto tudo foi problema da Shugart! – E do Woz... ● E do Langhton! – Quem? :-) ● Qual foi o meu problema? – 32 * 1 / 1.023 MHz ● 0,0000031280547409579667644183773216031 Segundos ● É o tempo que se tem para ler um raw byte do disquete, salvar na memória e estar pronto para ler o próximo! ● 3196 a 12787 bytes lidos a cada piscar de olhos – E eu só preciso perder UM para causar o infame I/O Error! 30/89
  • 120. Discos Magnéticos 1 1 1 1 1 1 1 1 1 0 0 1 0 0 ? ? 32 T states 31/89
  • 121. Algoritmos de Tempo Real ● Quediaboéisso? – São algoritmos em que o tempo de resposta faz parte do resultado do processamento ● Não é o mesmo que “fazer rapidinho” – “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo. – “Entregar” antes do prazo é desperdício de processamento ● E o Kiko? Kiko'eu tenho a ver com isto? – Acessar disco é uma tarefa de tempo real ● Missão Crítica! – Computadores modernos possui um micro controlador especializado para lidar com disco ● O Apple II não. – Welcome to hell... 32/89 ●Quediaboéisso? ● São algoritmos em que o tempo de resposta faz parte do resultado do processamento ● Não é o mesmo que “fazer rapidinho” ● Um determiado processamento pode precisar ficar pronto só em 24 horas ● Ou 24 milisegundos... ● “Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo. ● “Entregar” antes do prazo é desperdício de processamento ● Que pode ser necessário para entregar outra tarefa que está vencendo antes ●E o Kiko? Kiko'eu tenho a ver com isto? ● Acessar disco é uma tarefa de tempo real ● Missão Crítica! ● Se você não ler a porta de I/O no milisegundo correto, você não leu nada. ● Se você não gravar na porta de I/O no millisegundo adequado, você destruiu os dados que estavam no disquete! ● Computadores modernos possui um micro controlador especializado para lidar com disco ● O Apple II não. ● Welcome to hell...
  • 123. Reavaliação ● Riscos – Gravar setores dá mais trabalho que ler ● E eu nem tinha certeza de que iria conseguir ler... – Não vou conseguir fazer tudo! ● Muitas diferenças entre cada target, praticamente um software diferente pra cada um ● Prioridades – BOOT eficiente – Carga rápida de Binários – Serviços (mínimos) de diretório – (nice) API ● Sólida – Abrir mão da memória extra, e focar na principal ● E economizar onde der 34/89
  • 124. Reação ● Começar prototipando as rotinas básicas de disco – Se eu não estabilizar a rotina de leitura de setores, o resto não serve de nada – Um terço do esforço total do projeto foi gasto só nelas ● Redução de escopo – Serviços de “Console I/O” pelo Kernel :-| – Cache de disco (em especial, do CATALOG) :-| – Gravação de Dados ¬¬ – Gerenciamento da memória ¬¬ – Relocação em memória X-( – Suporte à programas BASIC X-( 35/89
  • 125. Resolução ● “Internalizar” algumas funções da ROM para o S.O. – Não sem conseqüências... ¬¬ ● Delegar à aplicação gerenciar o resto do hardware – O S.O. identifica para você a máquina em que está rodando – “Bibliotecas” padrão no “User Space” – E cada um que se vire! ● BASIC.SYSTEM – Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no User Space. ● “Forkar” o Kernel para casos especiais – Versões especializadas para cada arquitetura e/ou funcionalidade específica – Gerência de Configuração to the rescue! :-) 36/89 ●“Internalizar” algumas funções da ROM para o S.O. ● Me livrou de dependências externas ● Comeu uns bytes preciosos ● Mas viabilizou um binário único para todas as plataformas ● Facilitará aproveitar as extensões de memória no futuro ●Delegar à aplicação gerenciar o resto do hardware ● O S.O. identifica para você a máquina em que está rodando ● “Bibliotecas” padrão no “User Space” ● E cada um que se vire! ●BASIC.SYSTEM ● Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no User Space. ●“Forkar” o Kernel para casos especiais ● Versões especializadas para cada arquitetura e/ou funcionalidade específica ● Versionar a API ● Congelar um subset mínimo da API com garantias de funcionamento em todas as versões futuras ● Oferecer à aplicação um mecanismo para que ela saiba o que o Kernel corrente é capaz de oferecer ● Gerência de Configuração to the rescue! :-)
  • 126. E o inesperado (porque todo castigo...) ● O uso da Página Zero me mordeu o traseiro. – Feio. :-( – Quase assassinou o projeto no berço ● Quando a R*TS não matava o resto da máquina, o resto da máquina matava a R*TS ● Cerca de 20% do esforço de desenvolvimento foi gasto mapeando e documentando, corretamente, o uso da Z.P. – No TK-2000 e no Apple II – Um esforço com o qual eu não contava – Não havia mais o que fazer exceto desistir ou pagar o pato e seguir adiante ● 5 dias de trabalho indo pelo ralo. – E as férias, digo, o prazo acabando! =] ● A única documentação formal do projeto. 37/89 Único momento em que tive vontade de desistir Impotência, meus esforços submetidos à forças que das quais não tenho controle. Mas depois que passou a depressão (e a ressaca), umas 80 horas =P foram suficientes para mapear quais endereços podiam ser usados pela CB2k. Ver o programa zp_profile , nos discos de testes da CB2k (em attic, no reposítório)
  • 127. ; Depends on rwts.def. ; Updates zp_profile.s ; Apple II Zero Page Usage ; ; Lo Nibble of Address ; Hi ; Nib 0 1 2 3 4 5 6 7 8 9 A B C D E F ; ----- ----- ------ ------ ----- ------ ----- ---- ---- ---- ---- ---- ----- ----- ----- ----- ; 0 | A~ A~ A A A A - - - - A A A AI A A ; 1 | A A A A A A A A A A A A A A - M* ; 2 | M M M M M3 M MA3 MA3 M3 M3 M3 M3 MA3 MA3 M3 MA3 ; 3 | MA M MA MA3 M M3 M3B M3B M3B M3B M~ M~ MA3~^ MA3~^ MA3~^ MA3~^ ; 4 | M3~+^ M3~+^ M3~@^ M3~@^ M3~@^ M3~@ M3~ M3~ M3~ M3~ I3~ I3~ I3~ I3~ M~@# M@# ; 5 | MA MA MA MA MA* MAI* AI AI AI AI AI AI AI AI AI AI ; 6 | AI+ AI+ AI@ AI@ AI@ AI@ AI@# AI3 AI3 AI3 AI3 AI AI AI AI AI3 ; 7 | AI3 AI AI AI3 AI3 AI AI3 AI AI AI AI AI AI AI AI AI ; 8 | AI AI AI AI AI AI AI AI@ AI@ AI AI AI AI AI AI AI ; 9 | AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI ; A | AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI3 ; B | AI3 AI AI AI AI AI AI AI AI AI AI AI AI AI AI AI ; C | AI AI AI AI AI AI AI AI AI AI AI3 AI3 AI3 AI3 I# I# ; D | AI AI AI AI AI AI AI3 I! AI3 AI3 AI AI AI AI AI3 AI ; E | A A A A A A A A A A A ? - - - - ; F | A A A A A A A A A A - - - - Ik AI ; ; ; M = Used by Monitor; * used in early Apple IIe ROMs-- now free ; A = Used by Applesoft BASIC ; I = Used by Integer BASIC ; 3 = Used by DOS 3.3 ; ~ = Used by ProDOS ($40-$4E is saved before and restored after use) ; B = Used by ProDOS BASIC.SYSTEM (also uses all Applesoft locations) ; - = Free; not used ; ; k = Used by TK-2000 / MPF-II ; ; + = RWTS, Comunicação com "Cliente" ; @ = RWTS, Conteúdo descartável. ; ! = RWTS, Posição Chave: não pode ser mudada nem destruída! ; ; ^ = CompatiBoot 2k, Comunicação com "Cliente" ; # = CompatiBoot 2K, Conteúdo descartável. ; ? = CompatiBoot 2K, Posição Chave: não pode ser mudada nem destruída! ; ; --Bryan Dunphy, Michael J. Mahon, Rubywand, CompatiBoot 2k 38/89 Vale comentar que sem os esforços de dois outros caras da Scene mundial, as 80 hora de pesquisa facilmente se transformariam nas 300 do projeto inteiro!
  • 128. E quando tudo o mais falhar... “How many times do I have to tell you, the right tool for the right job!” Montgomery Scott (Scotty) Chief Engineer, NCC-1701-A USS Enterprise 39/89 Aquela ferramenta mágica que resolve todos os problemas! ;-) Pausa rápida para comentários. Aqui encerram-se as lamúrias :-), e começa a se descrever os problemas que foram resolvidos. Para então descrever as soluções.
  • 129. Anatomia de um Disquete 40/89 Trilhas concentricas, blablabla :-)
  • 130. Anatomia de um Disquete 35 Trilhas 0 1 2 … 35 Address Field gapzão gapzão gapzão gapzão 14 Addr_0 Addr_0 Addr_0 3 2 Addr_0 2 2 2 3 gap gap gap Prologo Volume gap Track Sector Chk Sum Epilogo Data Data Data 'D5 AA 96 '4 & 4 encoding '4 & 4 encoding '4 & 4 encoding Data '4 & 4 encoding 'DE AA EB =4096 bytes (lógicos) gap gap gap gap Addr_1 Addr_1 Addr_1 Addr_1 ~48000 bits (raw) gap gap gap gap Data Field Data Data Data Data 349 gap gap gap 3 gap 342 1 3 Addr_2 Addr_2 Addr_2 Prologo Addr_2 Data ChkSum Epilogo gap gap gap 'D5 AA AD 6 & gap 2 encoding 'XX 'DE AA EB Data Data Data Data gap gap gap gap Addr_3 Addr_3 Addr_3 … “gapzãp” Addr_3“Self Sync bytes” gap gap gap gap 48 a 100 gap 5 a 60 Data Data Data 'FF FF FF … Data 1 1 1 1 1 1 1 0 0 '1 'FF FF FF gap gap gap gap Addr_4 Addr_4 Addr_4 Addr_4 gap gap gap gap Data Data Data Data gap gap gap gap … … … … Addr_15 Addr_15 Addr_15 Addr_15 gap gap gap gap Data Data Data Data 41/89 Raw bytes , logical bytes (payload). What you see is not what you get! ;-)
  • 131. Anatomia de um Disco DOS 3.3 Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 42/89 Breve exemplo de 4 arquivos num disquete. Notar que a ordem dos setores foi “simplificada” para melhorar a didática, a ordem correta está na trilha zero Notar que são necessárias 2 rotações para ler uma trilha inteira, pela ordenação do DOS As trilhas 1 e 2 estão livres na CB2k, mas não com o DOS Setor de Boot (T0,S0) Tabela de alocação (T17, S0) Catalogo (T17, o resto) 4 Arquivos (notar que não é 1 arquivo por setor!) Track/Sector List
  • 132. Boot ● Power On RESET – RESET Vector ● Autostart ROM (BOOT 0) – Busca por uma placa DISK II na ROM de expansão ● BOOT 1 (second stage) – Trilha 0, Setor 0 – L-Boot1 ● BOOT 2 (third stage) – Sistema Operacional Ou outro payload qualquer... 43/89
  • 133. A L-Boot1 ● Fornece a melhor performance possível para carga sequêncial – Multi trilha ● Serviços independentes de “plataforma” – Impressão em tela – Carga de setores – Descompressão de dados ● Também foi usada com sucesso: – Boot do TK-DOS 3.3 – Boot do Apple DOS 3.3 – Jogos stand-alone 44/89
  • 134. Finalmente: CB2k ● R*TS ● Kernel – Serviços de Diretório – Serviços “Raw Files” – Serviços Binary Files – Serviços de House Keeping 45/89 Kernel: Quem coordena toda esta bagunça É quem dá cara à CB2k Diretório: Mínimos Não liga pra nome de arquivo, o que interessa é o índice relativo dele. 0, 1, 2, etc. RAW Files: Notar que é a única parte da CB2k que: É responsável pela alta performance ao acesso ao disco Aliás, é a única parte que faz acesso ao disco Granularidade: um setor 256 bytes, para DOS 3.3 Impossível acessar qualquer informação sem ser por múltiplos de um setor Acesso sequencial ou randômico Endereçamento por setor relativo Teoricamente pode ser substituída por qualquer outra coisa, como: Acessar HD Acessar servidor de arquivos em REDE Raios, telepatia que seja! :-) BIN Files: Especialização do Raw Files Permite carregar arquivos cujo tamanho não seja múltiplo de um setor Resguarda memória adjascente Não tem acesso parcial, é tudo ou nada. House Keeping: Identificação da Máquina Relocação dos buffers Configuração dos handlers Exceção Reset
  • 135. O Inferno das Entry-Points 00B3D5 2 KERNEL__ADDR_START: 00B3D5 2 ; Prevents accidental running 00B3D5 2 00 BRK 00B3D6 2 1E .byte __WARM_BOOT - __KERNEL_SERVICES_TABLE 00B3D7 2 00B3D7 2 __KERNEL_SERVICES_TABLE: 00B3D7 2 F8 B3 .word __PANIC 00B3D9 2 59 B5 .word KERNEL_SYSTEM_IDENTIFICATION 00B3DB 2 F4 B8 .word KERNEL_FILE_LOAD 00B3DD 2 21 B9 .word KERNEL_FILE_RUN 00B3DF 2 61 B5 .word KERNEL_SESSION_FINISH 00B3E1 2 10 B6 .word KERNEL_CATALOG_ENTRY_SET 00B3E3 2 33 B6 .word KERNEL_CATALOG_ENTRY_QUERY 00B3E5 2 92 B6 .word KERNEL_CATALOG_ENTRY_GET 00B3E7 2 F7 B6 .word KERNEL_RAWFILE_SEEK 00B3E9 2 82 B7 .word KERNEL_RAWFILE_READ 00B3EB 2 23 B5 .word KERNEL_HANDLER_SET 00B3ED 2 9E B5 .word KERNEL_CONFIGURATION_SET 00B3EF 2 DB B5 .word KERNEL_CONFIGURATION_GET 00B3F1 2 F9 B4 .word KERNEL_SECTOR_READ 00B3F3 2 F5 B3 .word __WARM_BOOT 00B3F5 2 __KERNEL_SERVICES_TABLE_end: 00B3F5 2 00B3F5 2 __WARM_BOOT: 00B3F5 2 4C 5A BA jmp KERNEL__WARMBOOT 00B3F8 2 00B3F8 2 __PANIC: 00B3F8 2 ; System is unstable. The next reset will reboot from the same slot the CB2K was rebooted last time. 00B3F8 2 20 9D BA jsr KERNEL__HW_RESET_HANDLER_REBOOT_SET 00B3FB 2 A9 80 lda #KERNEL_ERR_PANIC 00B3FD 2 A6 EB ldx KERNEL_SUPERVISOR__STACKPOINT 46/89 Ao passo que o kernel cresce, os pontos de entrada das rotinas mudam de endereço. Não é problema para o kernel, o Linker automaticamente faz as correções Mas como os clientes vão se virar? Não é razoável recompilar todos os aplicativos a cada vez que muda a versão do kernel! O DOS 3.3 cagou pro problema. ProntoDOS e DiversiDOS precisaram fazer malabarismos pra reusar os entry-points conhecidos. Que nem eram oficiais ProDOS criou uma chamada fixa em $BF00. Dali em diante tudo podia mudar, mas a entry-point oferecia uma interface padrão. Foi minha abordagem inicial, mas oferecia um problema: eu queria ser capaz de mover o Kernel inteiro pra cima ou pra baixo de acordo com a conveniência do momento, não podia amarrar um endereço de entry-point A entry point então iria estar registrada num endereço da página 0 (como se as coisas lá já não estivessem complicadas!).
  • 136. O Supervisor ● A instrução mágica – BRK KERNEL_SUPERVISOR: cli ; Desativamos interrupções. ; O Kernel não sabe ser interrompido, e a R*TS *NÃO PODE* ser interrompida! ; A RTI abaixo restaurará o Status, e se a IRQ estava ativada, ela voltará a estar. .ifndef LANGUAGE_CARD jsr MON_RESTORE ; Pois é... A ROM do Apple IIe faz o favor de, ; trabalho fodástico de resetar o estado da ; anterior para permitir restauro!), tirar da ; (o que eu não queria), e *não manter* o ; virtualmente fodendo com o conceito de ; ; TODO: Mover a CB2K para Language Card, escrever .endif jsr __SAVE_THE_WORLD ldx KERNEL_SUPERVISOR__STACKPOINT ; O Supervisor *NÃO É* reentrante. bne @PANIC lda __REG_P and #%00010000 ; Checa se o BRK STATUS está ativo beq @PANIC ; Se não está, a máquina tá despirocada e o PC caiu ; aqui por acidente! 47/89 CP/M e MS-DOS foram por este caminho. Usar as interrupções de software para fazer o serviço. O Kernel pode ir pra onde quiser, contanto que ele ajuste o vetor de interrupção para seu handler interno ao mudar de endereço. Clean. Lean. Lindo! :-) Absolutamente nenhum problema de linkagem estática Mas é um mecanismo um pouquinho caro para se usar em bibliotecas
  • 137. A (nice) API .define VERSION_MAJOR 1 .define VERSION_MINOR 1 .define VERSION_RELEASE "2012.0901" .macro SYS syscall BRK .byte syscall .endmacro ; This two entries are garanteed to never change or be renamed! CB2K_SYSTEM_PANIC := 0 CB2K_SYSTEM_IDENTIFICATION := 2 + CB2K_SYSTEM_PANIC ; The following entries can, but is unlikely to, change on MAJOR versions. CB2K_FILE_LOAD := 2 + CB2K_SYSTEM_IDENTIFICATION CB2K_FILE_RUN := 2 + CB2K_FILE_LOAD CB2K_FINISH := 2 + CB2K_FILE_RUN CB2K_FILE_SET := 2 + CB2K_FINISH CB2K_FILE_QUERY := 2 + CB2K_FILE_SET CB2K_FILE_GET := 2 + CB2K_FILE_QUERY CB2K_RAWFILE_SEEK := 2 + CB2K_FILE_GET CB2K_RAWFILE_READ := 2 + CB2K_RAWFILE_SEEK CB2K_HANDLER_SET := 2 + CB2K_RAWFILE_READ CB2K_CONFIGURATION_SET := 2 + CB2K_HANDLER_SET CB2K_CONFIGURATION_GET := 2 + CB2K_CONFIGURATION_SET CB2K_SECTOR_READ := 2 + CB2K_CONFIGURATION_GET ; The following entries (if any) can be added on MINOR versions ; CB2K_FUTURE_EXPANSION := 2 + CB2K_SECTOR_READ 48/89 E finalmente, a cara da CB2k para seus clientes.
  • 138. Resultados ● Footprint 3.75Kbytes – Kernel, R*TS, Supervisor, buffers, tudo! – E os buffers ainda são configuráveis (on the fly) ● Melhor performance – 6 a 7 Kbytes/s – próximo do limite operacional do dispositivo ● Usa discos formatados pelo Apple DOS 3.3 – Até o FID pode ser usado para povoar seus discos ● Mas eu recomendo o CiderPress. :-) ● Aplicações – Game Loaders – Demos – Outros 49/89 ●Footprint 3.75Kbytes ● Kernel, R*TS, Supervisor, buffers, tudo! ● E os buffers ainda são configuráveis ● Você pode movê-los on the fly durante a execução do seu programa, caso precise justamente daqueles endereços num determinado momento ●Melhor performance ● 6 a 7 Kbytes/s – próximo do limite operacional do dispositivo ●CATALOG ● Usa discos formatado pelo Apple DOS 3.3 ● Até o FID pode ser usado para povoar seus discos ● Mas eu recomendo o CiderPress. :-) ●Aplicações ● Beautiful Boot ● Game Loaders ● Karateka do TK-2000 ● Loader para jogos grandes no TK-2000
  • 139. Resultados ● Benchmark TK-2000 – Tempo entre ligar a máquina (com o disquete já no drive) e o Prompt do Applesoft : ● DOS: ~31 Segundos (!!!!) ● CB2k: 6 segundos ● DOS + LBoot1: 7 segundos (!!!!) – Tempo para carregar uma tela HGR: ● DOS: 10 segundos ● CB2k: 4 segundos – Espaço livre na RAM (MEMTOP - $800): ● DOS: $9600 - $800 = $8E00 = 35.5Kb ● CB2k: $B000 - $800 = $A800 = 42Kb ● Mas convêm lembrar: – A CB2k faz pouca coisa mais que carregar binários 50/89 E é possível aumentar em ¾ de kbyte a memória livre movendo os buffers para posições de memória alternativas Mas isto é altamente dependente de máquina] No TK-2000 eu tenho algumas boas oportunidades (I know how to cook or what?)
  • 140. Por que o DOS é tão lento? ● Os “raw sectors” (342 bytes físicos) são lidos para um buffer intermediário ● Este buffer é então decodificado para os 256 bytes de dados, em um buffer auxiliar ● Estes dados são, finalmente, copiados para o buffer de I/O para leitura pelo programa BASIC ou para a memória destino, se binário ● E o disco continua virando 51/89 ●Os “raw sectors” (342 bytes físicos) são lidos para um buffer intermediário ●Este buffer é então decodificado para os 256 bytes de dados, em um buffer auxiliar ●Estes dados são, finalmente, copiados para o buffer de I/O para leitura pelo programa BASIC ou para a memória destino, se binário ●Como o disco continua virando, até o DOS poder ler novamente um setor, já pode ter passado vários (no mínimo 1) debaixo do cabeçote (incluindo, talvez, o que deveria ser o próximo setor lógico) ● De forma que poderia ser necessário esperar a trilha “dar a volta” para ler o próximo setor desejado ● Por esta razão existe o tal do Skewing ● os setores físicos eram remapeados para setores lógicos, e estes últimos eram endereçados pelo DOS na Track/Sector List
  • 141. DOS: Modus Operandi Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 52/89 Mover o cabeçote é um evento traumático para o drive, ele leva centenas de millisegudos para se recuperar, estabilizar a leitura do cabeçote e voltar a ler dados. Se eu estou lendo sequencialmente, ao mover o cabeçote o drive fica “cego” por algus setores – de forma que é inevitável que eu perca a seqüência e precise esperar a trilha dar uma volta inteira para recomeçar a ler (ver a área 'cega', esbranquiçada, no desenho acima. Esta insistência em ler os setores em seqüência também causa delays desnecessários quando os arquivos estão espalhados
  • 142. E por que a R*TS ficou tão “rápida”? ● Os raw sectors são decodificados on the fly, indo diretamente para a memória a que se destinam – Sem buffers intermediários, sem memory moves – Exceto o primeiro e o último setor de arquivos binários, que são carregados num buffer de I/O e então copiados para o target para não sobrescrever memória limítrofe ● Era o mais perverso efeito colateral da CompatiBoot original, diga-se de passagem ● Ela não espera pelo próximo setor, mas monta uma lista dos setores desejados e vai carregando na medida em que eles passam debaixo do cabeçote – Não há espera pelo “próximo setor” – Os gap bytes me dão tempo suficiente para recomeçar a leitura entre o fim de um setor e o começo do outro – Mesmo o pior caso leva apenas uma revolução do disquete para ser lido. 53/89 ●O DOS foi o PRIMEIRO sistema operacional de disco para Micro Computadores ● Nunca ninguém havia feito isto antes! ● O único “concorrente” funcionava em mainframes, e tinha megabytes de tamanho ● O Apple DOS tinha menos de 10 Kbytes... ●Todos os erros ainda estavam por ser cometidos ● Os melhores videntes não sabem programar ● Os programadores insistem em usar teclados, e não bolas de cristal... ●Dificuldades técnicas inerentes ao período ● Os binários eram alimentados na máquina de desenvolvimento usado fita perfurada ● Usando um hardware feito à mão pelo Woz ● Ao menos eu tinha um PC com emulador para testar a bagaça ● Mas usei a porta cassete na hora de testar no bares metal! =P
  • 143. CB2k: Modus Operandi Disk Trilha 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 0 0 1A 15 31 47 62 78 0 15 23 102 109 116 120 1 8 0 16 32 48 63 79 1 16 24 103 110 117 121 2 1 1 1 17 33 49 64 80 2 17 25 104 111 118 122 3 9 2 18 34 50 65 81 3 18 26 105 112 119 1B 4 2 8 3 19 35 51 66 82 4 19 27 36 45 54 123 5 10 3 4 20 36 52 67 83 5 3 28 37 46 55 124 6 3 10 5 5 21 37 53 68 84 6 0 29 38 47 56 124 Setor 7 11 2 6 22 38 54 69 85 7 1 30 39 48 57 125 8 4 4 9 7 23 39 55 70 86 8 2 31 40 49 58 125 9 12 4 8 24 40 56 71 87 9 20 32 41 50 59 126 10 5 9 25 41 57 72 88 10 95 99 106 113 60 126 11 13 6 10 26 42 58 73 89 11 96 100 107 114 61 127 12 6 4 11 27 43 59 74 90 12 97 101 108 115 62 127 13 14 7 3 12 28 44 60 75 91 13 21 33 42 51 63 14 7 2 13 29 45 2 76 92 14 22 34 43 52 64 15 15 1 14 30 46 61 77 93 94 98 35 44 53 65 54/89 A CB2k não espera por um setor, mas faz uma lista dos setores desejados para cada trilha. Quando a mudança de trilha estabiliza, para cada setor que passa no cabeçote eu checo se ele tá na wish-list. Se estivar, ele é lido e ponto final. Quando a wish-list tá vazia, é hora de trocar de trilha e o processo recomeça. Não há esperas por um setor específico – todos os setores desejados vão, eventualmente, aparecer debaixo do cabeçote. As rotinas de leitura de setores serem otimizadas também ajudam, pois eu sou capaz de ser setores contínuamente (sem precisar de pausas para decodificar nada). Então, além da otimização acima, eu sou capaz de ler uma trilha em apenas uma revolução – poi eu sou capaz de ler 16 setores continuos.
  • 144. Mas então... ● Por que não consertaram antes? – Consertaram! ● Apple – ProDOS ● Terceiros – ProntoDOS – DiversiDOS – CP/M – Mas nenhum deles foi portado para o TK-2000! ● CB2k! :-) – Nem implementaram leitura múltipla! ● CB2k! ;-) 55/89 Em condições normais de uso (que efetivamente acontecia na época), os arquvos tendem a se fragmentar com o tempo, se aproximando gradativamente ao pior caso do exemplo dado. A CB2k se aproveita de uma particularidade dos tempos modernos: os disquetes não são mais usados para trabalhos ordinários – mas sim para uma função específica e normalmente read/only – no nosso caso, armazerar e carregar jogos. As extreme optimizations da CB2k não renderiam os mesmos benefícios num ambiente “normal”, e aumentaria em muito a complexidade (e o risco de erros) nas demais rotinas de um Sistema Operacional comum O que o Dick Vigarista tá fazendo aí? ;-) Breve histórico da Apple patinando com o Apple III enquanto deixava o Apple II à míngua.
  • 145. Hands on 56/89 Finalmente! :-)
  • 146. Check List ● Café ● Instruções de onde baixar e como instalar: ● Salgadinhos – MINGW – CC65 ● Daft Punk na – CiderPress vitrolinha :-) – AppleWin ● Estes Slides – Emulador TK2000 ● Os fontes do Hello Word ● Imagem de disco – Leia o READ.ME ! ;-) da CB2k (1.1r4a:Set/2012) ● Instruções: – Para montagem do programa, – Importação do binário para uma imagem de disquete – e execução em emulador. 57/89 Programar em ASM é fácil. Mas da mesma forma que é difícil montar algo interessante com um LEGO de apenas 3 bloquinhos, o mesmo acontece quando você tem só 3 registradores: você precisa rebolar pra realizar as tarefas de pouquinho em pouquinho. A CB2k por sua vez também ajuda – as tarefas básicas ganharam rotinas prontas (o fato de tais rotinas saberem sozinhas quando estão num TK- 2000 ou num Apple também ajuda um bocado!). Este Hello World pode ser compreendido por um leigo no assunto em meia hora, sério. Você vai gastar mais tempo baixando e instalando o ambiente de produção que aprendendo como funciona o Hello World.
  • 147. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : jsr ANYKEY .include "system.def" jsr SYSTEM_HGR SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 58/89
  • 148. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 .include "../CB2k.def" ● Configura dialeto do : bne :- processador SYSTEM_HGR jsr ANYKEY .include "system.def" jsr SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY jsr SYSTEM_INIT ● Configura prefixo para rótulos NO_FUN: jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR locaisANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx SYS #>NO_FUN CB2K_HANDLER_SET ● Inclui HEADER: cabeçalhos que jmp MON_RDKEY : PRINT HEADER definem símbolos da HEADER_line_0: .byte 22,0 plataforma 23,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte Lda #90 textz " " : jsr beq MON_WAIT :- ● ; Branch always! Inclui o cabeçalho do Sistema .byte 1,0,0 .byte -1 lda #<MENSAGEM_TEXT Operacional 23,0 ANYKEY_TEXT: .byte ldx #>MENSAGEM_TEXT textz ":" sta stx PRINT_DATA PRINT_DATA+1 ● Inclui o cabeçalho da .byte -1 .include "system.inc" ldy #0 biblioteca de sistema MENSAGEM_TEXT: .include "mensagem.txt" 59/89
  • 149. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" .include "../bios.def" ● Onde começar o programa? bne inc :- PRINT_DATA+1 bne :- .include "../CB2k.def" : .include "system.def" – Qual o tamanho do binário? jsr jsr ANYKEY SYSTEM_HGR SYS CB2K_FILE_LOAD .org $800 ● Difícil preverjsr antes de começar, não? ANYKEY NO_FUN: jsr SYSTEM_INIT – Usa gráficos? jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda ldx #<NO_FUN #>NO_FUN ● Num Apple? PRINT jmp ANYKEY_TEXT MON_RDKEY SYS CB2K_HANDLER_SET ● Num TK-2000? HEADER: : HEADER_line_0: PRINT HEADER dec HEADER_line_1 – Mas o TK sempre usa gráficos! World .byte 22,0 textz "============ Hello !! ============" dec bmi lda HEADER_line_0 :+ #90 – Modo texto? .byte 23,0 HEADER_line_1: textz " " jsr MON_WAIT .byte 1,0,0 beq :- ● ; Branch always!Num Apple?.byte -1 : lda #<MENSAGEM_TEXT ● Num TK-2000? 23,0 ANYKEY_TEXT: .byte ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA – Mas o TK não tem modo texto! .byte -1 stx PRINT_DATA+1 ldy #0 ● Onde é que tá a CB2k mesmo? .include MENSAGEM_TEXT: "system.inc" .include "mensagem.txt" 60/89
  • 150. Hello World Bloco II/A $FFFF $0000 Zero Page Zero Page Extra RAM $0100 Stack Stack Bloco I ROM $0200 Bloco II/A P1 Bloco II/A P0 Extra RAM I/O Buffer I/O Buffer $D000 $0300 Free RAM Free RAM System Pointers System Pointers $0400 $C100 TEXT/GR 80TEXT/DGR Mem Map I/O $C000 Page 1 Page 1 Bloco II/D Sentiram Extra RAM $0800 TEXT/GR 80TEXT/ DGR HGR 2 Page 2 Page 2 Bloco II/D P1 Bloco II/D P0 $A000 $1000 $0000 Zero Page Free RAM Free RAM $0100 Stack $2000 $0200 Key Buffer o drama? Free RAM Free RAM HGR 1 DHGR 1 $4000 $0300 System Pointers $0400 $4000 HGR 1 TEXT/GR Page 1 $4000 HGR 2 DHGR 2 $2000 $0800 HGR 1 TEXT/GR Page 2 $6000 $2000 $1000 Free RAM Free RAM Free RAM Free RAM $2000 $0800 HGR 1 Some System Variables & Free RAM $0400 $C000 Mem Map I/O $4000 System Pointers $0300 Free RAM $C100 Expansion Slot HGR 2 I/O Buffer $0200 ROM Stack $0100 $D000 L.C. P0 L.C. P1 L.C. P1 L.C. P0 Zero Page $0000 $6000 Language Card L.C. P0 L.C. P1 ROM Language Card Main Main $FFFF RAM Free Saturn Bank 7 Main Main AUX $C000 Mem Map I/O L.C. P0 L.C. P1 $C100 Expansion Slot ROM Saturn Bank 1 Main $D000 L.C. P0 L.C. P1 ROM Language Card Main $FFFF 61/89
  • 151. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny ● .include "../sys.def" .include "../bios.def" Algumas opções default bne inc :- PRINT_DATA+1 bne :- .include "../CB2k.def" – Para programas pequenos (pequenos mesmo) : jsr ANYKEY .include "system.def" jsr SYSTEM_HGR .org $800 ● $800 - $1FFF (6 Kbytes) SYS jsr CB2K_FILE_LOAD ANYKEY jsr SYSTEM_INIT – Para programas maiorzinhosSYSTEM_APPLESOFT_START_COLD NO_FUN: jmp ldy lda #CB2K_HANDLER_ERROR ● #<NO_FUN $4000 - $9FFF (~24 Kbytes) ANYKEY: PRINT ANYKEY_TEXT jmp MON_RDKEY Fora disto, e terá HEADER: montar versões que ldx #>NO_FUN SYS ● CB2K_HANDLER_SET : PRINT HEADER específicas para cada máquina Hello World !! ============" HEADER_line_0: .byte 22,0 textz "============ dec HEADER_line_1 dec HEADER_line_0 HEADER_line_1: bmi lda :+ #90 – Use CB2K_CONFIGURATION_GET saber o limite " .byte 23,0 textz " jsr beq MON_WAIT :- superior da memória .byte 1,0,0 ; Branch always! usável .byte -1 : lda #<MENSAGEM_TEXT – Nem sonhe em usar.byte 23,0 no TK-2000! HGR2 ANYKEY_TEXT: ldx #>MENSAGEM_TEXT textz ":" sta stx PRINT_DATA PRINT_DATA+1 ● Até a próxima versão da-1CB2k, lógico! :-) .byte .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 62/89
  • 152. Hello World .setcpu "6502" : lda (PRINT_DATA),y ● Inicialização .localchar '@' beq jsr :+ PRINT_ASCII .include "../hw.def" iny – Biblioteca SYSTEM .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 ● Configura manipulador de Erro bne :- .include "../CB2k.def" : – Se algo der errado, inicializa o Applesoft e dá o prompt jsr ANYKEY jsr SYSTEM_HGR pro usuário "system.def" .include SYS CB2K_FILE_LOAD .org $800 jsr ANYKEY NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 63/89
  • 153. Hello World ● LOOP (até "6502" a linha da primeira zString seja menor que 0) .setcpu que : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII – PRINT (macro em SYSTEM.DEF) .include "../hw.def" iny .include "../sys.def" bne :- Imprime <n> zStrings .include ● "../bios.def" (terminada em 0, C-style) em inc posições específicas da tela PRINT_DATA+1 bne :- ● (Rotina de SYSTEM.INC) .include "../CB2k.def" : jsr ANYKEY – Pausa de ~25 mSecs .include "system.def" jsr SYS SYSTEM_HGR CB2K_FILE_LOAD .org $800 jsr ANYKEY ● (Rotina na ROM) NO_FUN: – jsr NotarSYSTEM_INIT que MON_WAIT sempre volta com ZeroFlag em 0. jmp SYSTEM_APPLESOFT_START_COLD ldy #CB2K_HANDLER_ERROR ANYKEY: Notar os branchs relativos anônimos! ● lda ldx #<NO_FUN #>NO_FUN PRINT jmp ANYKEY_TEXT MON_RDKEY SYS CB2K_HANDLER_SET HEADER: : HEADER_line_0: PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 64/89
  • 154. Hello World ● Dois loops: .setcpu "6502" : lda beq (PRINT_DATA),y :+ .localchar '@' – O interno, “driven” pelo Y jsr PRINT_ASCII .include "../hw.def" iny ● O INY “overflows” para 0 depois do 255. .include "../sys.def" bne :- ● BNE :.include último resultado da ULA não deu em zero pula se o "../bios.def" inc PRINT_DATA+1 bne :- – O externo, “driven” pelo último valor lido em Acc .include "../CB2k.def" : jsr ANYKEY ● BEQ: .include "system.def" em Acc for zero, sai do Se o último byte carregado jsr SYSTEM_HGR loop. SYS CB2K_FILE_LOAD – .org $800 BEQ/BNE e outros atuam em cima do Registrador jsr ANYKEY de Status (P) NO_FUN: ●jsr reflete o SYSTEM_INIT operação da ULA, ou da Que status da última jmp SYSTEM_APPLESOFT_START_COLD última carga em registrador ldy #CB2K_HANDLER_ERROR ANYKEY: – PRINT_ASCII#<NO_FUN lda PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY ● Imprime o caractere ASCII no Acc SYS CB2K_HANDLER_SET ● PRINT_DATA HEADER: ● : Dirty and Tricky! HEADER_line_0: – Duas posições na página zero (escolhidas à .byte 22,0 – PRINT HEADER Eu sei que a única forma do INC dar em zero é dec HEADER_line_1 PRINT_DATA HEADER_line_0 acabar apontando para a página zero dedo!) para servir deHello World !! ============" textz "============ ponteiro para o buffer do dec HEADER_line_1: –bmi nunca :+ armazena strings! ;-) onde se texto a 23,0 impresso .byte ser lda #90 textz " " – Na prática, pula sempre! – Estas instruções ocupam 2 bytes, e não 3! .byte 1,0,0 jsr MON_WAIT beq :- ; Branch always! .byte -1 : ● Usaremos o Y como indexador no loop que lda #<MENSAGEM_TEXT vem a seguir ANYKEY_TEXT: .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA – Inicializa em .byte -1 0! stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 65/89
  • 155. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny ● Aguarda por"../sys.def" .include uma tecla (não .include "../bios.def" bne inc :- PRINT_DATA+1 importa qual"../CB2k.def" .include : bne jsr :- ANYKEY .include "system.def" jsr SYSTEM_HGR ● Entra em modo gráfico .org $800 SYS jsr CB2K_FILE_LOAD ANYKEY ● Carrega o SYSTEM_INIT arquivo jsr próximo NO_FUN: jmp SYSTEM_APPLESOFT_START_COLD binário do #<NO_FUN ldy lda catálogo #CB2K_HANDLER_ERROR ANYKEY: PRINT ANYKEY_TEXT ldx #>NO_FUN jmp MON_RDKEY – ÉSYS uma tela HGR CB2K_HANDLER_SET HEADER: : HEADER_line_0: EuHEADER fui eu que coloquei lá! PRINT ● sei, .byte 22,0 textz "============ Hello World !! ============" dec HEADER_line_1 – Adec CB2k já o deixou 'na agulha' bmi HEADER_line_0 :+ HEADER_line_1: .byte 23,0 lda #90 textz " " quando carregou o programa jsr MON_WAIT .byte 1,0,0 .byte -1 beq :- ; Branch always! : corrente, basta a chamada para ANYKEY_TEXT: carregá-lo lda ldx #<MENSAGEM_TEXT #>MENSAGEM_TEXT .byte 23,0 textz ":" sta PRINT_DATA .byte -1 ● Ver CB2K_FILE_SET se não é o que stx PRINT_DATA+1 .include "system.inc" você quer ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 66/89
  • 156. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : ● Aguarda.include "system.def" por outra tecla jsr jsr ANYKEY SYSTEM_HGR SYS CB2K_FILE_LOAD ● Encerra,.org $800 inicializando o Applesoft. jsr ANYKEY NO_FUN: – A CB2k ainda tá na memória, mas não dá jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD suporte ao BASIC ldy #CB2K_HANDLER_ERROR ANYKEY: lda #<NO_FUN PRINT ANYKEY_TEXT – Mas você pode brincar no MiniAssembler! ldx SYS #>NO_FUN CB2K_HANDLER_SET jmp MON_RDKEY HEADER: : ● Se você estiver num Apple //e ou num TK- HEADER_line_0: PRINT HEADERa Tomato Board revisada 2000 com HEADER_line_1 .byte 22,0 dec textz "============ Hello World !! ============" dec HEADER_line_0 HEADER_line_1: bmi :+ .byte 23,0 lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 67/89
  • 157. Hello World .setcpu "6502" : lda (PRINT_DATA),y .localchar '@' beq :+ jsr PRINT_ASCII .include "../hw.def" iny .include "../sys.def" bne :- .include "../bios.def" inc PRINT_DATA+1 bne :- .include "../CB2k.def" : ● Dirty and Tricky! "system.def" .include jsr jsr ANYKEY SYSTEM_HGR SYS CB2K_FILE_LOAD – A anykey, por ser uma subrotina, deveria .org $800 jsr ANYKEY terminar com um RTS NO_FUN: jsr SYSTEM_INIT jmp SYSTEM_APPLESOFT_START_COLD – Mas ela por sua vez se vale de outra rotina na sua última#CB2K_HANDLER_ERROR ldy lda instrução, economizei um byte #<NO_FUN ANYKEY: PRINT ANYKEY_TEXT (2 duas posições da pilha) fazendo um JMP ldx SYS #>NO_FUN CB2K_HANDLER_SET jmp MON_RDKEY pra dita cuja. HEADER: : HEADER_line_0: ● O RTS dela é quem faz o retorno a quem PRINT HEADER .byte 22,0 dec HEADER_line_1 textz "============ Hello World !! ============" chamou a ANYKEY. dec HEADER_line_0 HEADER_line_1: .byte 23,0 bmi :+ lda #90 textz " " jsr MON_WAIT .byte 1,0,0 beq :- ; Branch always! .byte -1 : ANYKEY_TEXT: lda #<MENSAGEM_TEXT .byte 23,0 ldx #>MENSAGEM_TEXT textz ":" sta PRINT_DATA .byte -1 stx PRINT_DATA+1 .include "system.inc" ldy #0 MENSAGEM_TEXT: .include "mensagem.txt" 68/89
  • 158. Aplicações ● Demos! :-) – No arquivo de Distribuição da CB2k você encontrará o fonte para todos os programas de demonstração. ● Console I/O independente de máquina – Conversão automática para maiúsculas em máquinas sem caracteres minúsculos ● Sintetização de SOM! – Eletric Duet / Paul Lutus ● Exemplos mais complexos da API da CB2k – Carregamento e/ou execução de arquivos – Leitura do Diretório – Handlers de sistema ● Tratamento te exceções ● RESET 69/89
  • 159. Aplicações ● Agora: – Beautiful Boot ● Jogos! Yeay! :-) ● Porte feito por Fábio Belavenuto ● Na agulha: – Basic.system para o TK-2000 ● Uma solução definitiva para a fragmentação da memória do BASIC no TK-2000 ● RDOS style – Novas Demos para a CB2k ● Técnicas de animação e sintetização de Som simultâneos ● O TK-2000 pode, o TK-2000 faz! :-) ● Futuro: – Substituto para o RDOS no Apple II ● Tão logo eu crie coragem e escreva as rotinas de gravação de setores... – Suporte transparente para outras mídias ● Enquanto a API for estável, tanto faz de onde vêm os bytes! – Arquivos de “Overlay” 70/89
  • 160. HGR 1 $4000 HGR 1 Free RAM $A000 Bloco II/D P0 Known Issues HGR 2 Extra RAM $C000 Mem Map I/O Bloco II/D $C100 $D000 Extra RAM Bloco II/A P0 Bloco ROM Bloco I ● Código não relocável dinamicamente Extra RAM Bloco II/A $FFFF – O S.O. está amarrado ao topo da memória principal (pouco antes da área de I/O) – Ruim para o TK-2000, pois sua segunda página de vídeo está lá. ● Jogos que usam paginação vão matar o S.O. – Desperdiça a Bloco I / Language Card ● Menos memória “segura” para os programas – Que pra começo de conversa não foram feitos para conviver com um sistema operacional de disco! :-) 71/89
  • 161. Known Issues ● Read Only – A CB2k não grava. – “By Design” =P ● Um processo complicado e ainda mais time critical. ● Até o momento, baixa demanda. ● Implementar gravação vai aumentar o footprint na memória ● No LIBS – A “biblioteca” não passa de um include sofisticado ● Raios, o S.O. todo tá pendurado assim! – Uma LIB estática é uma demanda forte ● LIB dinâmica é sonho de consumo! ● Incompatibilidade com a CFFA 3000 – Ainda investigando... 72/89
  • 162. Considerações Finais ● Lições (Re)Aprendidas – Projetos pessoais ainda são Projetos! – Realidade Comanda – Wear Sun Screen! :-) ● Onde aprender mais? ● Onde obter ajuda? 73/89
  • 163. Projetos Pessoais ainda são Projetos ● Boas práticas também não têm este nome à toa! – Xtreme Programming! – Rubber Ducking! ;-) ● Eu me estrepei muito por não ter seguido algumas destas práticas desde o começo ● E tive meu traseiro poupado de trágico destino por ter seguido outras 74/89
  • 164. Projetos Pessoais ainda são Projetos ● Version Control System – RCS, CVS, SVN, GIT, Mercurial, Bazaar ● Qualquer um, qualquer um mesmo! – Até copy&paste em diretórios no seu HD! ● Gerência de Configuração – Procure saber em quais ambientes (e configurações) o seu software vai rodar ● Mesmo que não possa garantir o funcionamento em todos! ● Principalmente para poder garantir o funcionamento em alguns! 75/89
  • 165. Projetos Pessoais ainda são Projetos ● Use Cases e Back Logs – Formalismos não são necessários ● mas se você não especifica o quê você quer resolver, você não resolve é nada... – Gold-plating não é legal. – Um arquivo texto com um parágrafo por Requisito / UC / Whatever já é suficiente, o importante é que todos os envolvidos saibam do que se trata ● Principalmente quando “todos os envolvidos” é só você! :-) – O tempo passa e não tem mais ninguém pra lhe lembrar do que você tem que fazer! ● Versione! Versione!! – Foco, ou você não termina esta joça! 76/89
  • 166. Projetos Pessoais ainda são Projetos ● Fail early, Fail often! – Unit Tests ● Imprescindíveis ! :-) ● Mas eles custam caro, não subestimem o impacto no “orçamento” . – Alguns bugs são mais baratos de serem consertados (se ocorrerem) que prevenidos – Você não tem tempo (nem dinheiro) pra fazer tudo o que quer. – Test Cases / Test Suites ● Porque testes de unidade não são capazes de pegar erros de integração que teimam em ocorrer – E sempre nos piores momentos possíveis! :-) ● As aplicações de exemplo são meus Test Suites públicos! 77/89
  • 167. Realidade Comanda ● Eat your own dogfood! – É só aplicando na vida real que você tem certeza se uma idéia realmente funciona. ● Ou não! ¬¬ – Você é seu primeiro e primário beta-tester. ● Use seu produto, encontre você mesmo seus erros – Ou outros o farão por você 78/89
  • 168. Realidade Comanda ● Beta testers – Eu não teria conseguido sem ajuda! ● Sem eles, e você desenvolve no escuro – Exceto se dispor de recursos financeiros para comprar tudo em que bate os olhos! ;-) – Mas eles não serão muito úteis se você não fizer seu dever de casa: ● Use Cases ● Test Cases ● Gerência de Configuração ● Versionamento de Código – Foi aqui que eu percebi que estava atirando no meu próprio pé ao “agilizar” o desenvolvimento ao custo de algumas boas práticas... 79/89
  • 169. Realidade Comanda ● Não subestimar a importância de um bom Error Report – Porque você *NUNCA* pegará todos os erros. ● Principalmente os bobos – Erro grave explode logo, são os bobos que dão trabalho! 80/89
  • 170. Realidade Comanda KDIFF3 é pra vida! :-) 81/89
  • 171. Links Relacionados ● CB2k – Suite de Testes – Debut da CB2k (Apple //e) – Debut² =P no TK-2000 ● Slides da palestra ● http://pt.wikipedia.org/wiki/Apple_II ● http://pt.wikipedia.org/wiki/TK2000 ● http://retro.lisias.net/ 82/89
  • 172. Links Úteis ● http://www.6502.org ● http://www.cc65.org/ ● http://applewin.berlios.de/ ● http://www.fabio.belavenuto.nom.br/tk2000/ ● http://www.datacassete.com.br/ ● ftp://ftp.apple.asimov.net/pub/apple_II/ ● http://www.applefritter.com/ ● http://www.extremeprogramming.org/ ● http://www.codinghorror.com/blog/2012/03/rubber-duck-problem-solving.html ● Ajuda Especializada 0:-) 83/89
  • 173. Links Interessantes ● Paul Langhton – Consultor responsável pelo Apple DOS ● Steve Wozniak – Responsável por todo o resto! :-) ● Apple II History – História do Apple II, versão do usuário. ● ASCII Express' Game Server – “Servidor” de jogos, com download em formato de áudio otimizado – Para máquinas “diskless” 84/89
  • 174. Links “Interessantes” =P ● Câmara de Torturas (ou: se Donatien Alphonse François fosse Analista de Sistemas) – Restauro e 'Mods' do TK-2000 ● E outras vítimas – Outros clássicos ● Alguns poucos conhecidos por aqui – Outros loucos ● Porque gostamos de companhia. O:-) 85/89
  • 175. (alguma) Literatura Recomendada ● How to program the Apple II using ● Software Control of the Disk II or IWM 6502 Assembly Language Controller – DATAMOST, 1982 – Norman Leung – Randy Hyde – Apple Computer, 1984 – Featuring LISA Assembler ● Andrew S. Tanenbaum ● Beneath Apple DOS / – Eternamente :-) Beneath Apple ProDOS ● Microcomputadores e Microprocessadores – Don Worth & Pieter Lechner – Albert Paul Malvino – Quality Software, 1982 – McGraw-Hill, 1985 ● Understanding the Apple II ● The Pragmatic Programmer: From – James Fielding Sather Journeyman to Master – Quality Software, 1983 – Andrew Hunt & David Thomas – Com Introdução do Woz! :-) – Addison-Wesley Professional, 1999 86/89 Na falta de qualquer outro critério, foram estes que eu usei desde a primeira vez que me propuz a aprender Assembler, em 1980 e vovó de bicicleta!
  • 176. Onde Obter Ajuda ● Lista appleII_br ● Newsgroup comp.sys.apple – E os diversos subgrupos desta hierarquia ● me@lisias.net ;-) ● Ajuda Especializada 0:-) 87/89
  • 177. Free Chat ● Dúvidas? ● Comentários? ● Sugestões? ● Apoio moral? – (Piada interna da appleII_br) – *<8o) 88/89 Aproveitar para agradecer blah, blah, blah e ETC. E demonstrar a Karateka CB2k do Fábio Belavenuto, que foi meu primeiro cliente! :-)
  • 178. Obrigado! @lisias me@lisias.net http://tk2k.lisias.net/CB2k 89/89 Boldly crashing what no man has crashed before! Nos momentos difícieis em que nem o pato de borracha pôde me ajudar, fazia parte do processo de superação =P fantasiar em jogar meu TK-2000 pela janela e transformá-lo no mais novo satélite artificial brasileiro. A piada faz algum sucesso na lista apple_II. :-) Nota: o micrinho é uma GIF animada (sou retrô ou what?), mas o slideshare não dá suporte a esta feature.

Notas do Editor

  • #7: As Interfaces de Disco e Drives de Apple II são relativamente baratos E, de um mês para outro, diversos TK-2000 ganharam acesso à disquetes! Mas os jogos (e parte significativa dos demais softwares) ainda estavam em formato Cassete (ou equivalentes modernos como MP3 e CT2) sendo carregados pela porta de Audio! Convertê-los para formato de arquivo é relativamente fácil ainda em andamento, na medida em que os títulos são resgatados Fazê-los funcionar debaixo do TK-DOS nem tanto E não enlouquecer esperando o boot acontecer ainda menos. Soluções importadas do Apple II não atendiam As diferenças estruturais entre as máquinas não permitem um reuso direto As soluções simples invariavelmente eram limitadas ou incômodas Não extensíveis, não adaptáveis Hacks interessantes e úteis, mas feitos por hackers para hackers e resolvem um problema específico com o menor custo As soluções completas eram muito complexas para portar ProntoDOS, DiversiDOS, ProDOS todos ótimos, mas sistemas operacionais completos! Overkill Over memory :-)
  • #8: Enquanto isto, “lá fora” (news: comp.sys.apple ) Com problemas parecidos, soluções “ quick &amp; dirty ” foram desenvolvidas e publicadas, dentre elas a CompatiBoot original (Raven/C700 Club) teve boa recepção na lista appleII_br Hiper rápida “ Herdeira” das rotinas de disco usadas na eZine francesa Dox-a-gaz (circa 1988), de autoria de Max-a-gaz. “ Herdeira” do utilitário de cópias “Locksmith”, da Omega Microware (circa 1985) Super prática Basta copiar o binário para a primeira entrada do catálogo e dar boot. Mas capenga no TK-2000 One shot only Altas gambiarras pra convencer a dita cuja a fazer o que queríamos Efeitos colaterais diversos e inesperados
  • #9: O Apple/TK DOS 3.3 É muito “grande” É muito lerdo Demais S.O.s Overkill Fast Loaders legados Não são práticos nem flexíveis um saco criar o disco de boot! Armazenam dados controlando diretamente os setores do disco Sem diretórios Atualização/manutenção impraticável São perdulários Um disco por jogo, mesmo que 10 deles caibam no disquete Não funcionam, ou o fazem porcamente, no TK-2000
  • #12: A CB2k deve: Carregar arquivos com a maior eficiência possível Ninguém quer esperar pra brincar! Permitir carregar programas que querem ocupar o espaço onde normalmente ficaria o DOS menor footprint possível na memória principal (a mais concorrida) deve permitir ser movida para diferentes posições de memória Para se acomodar mesmo com aqueles jogos “mais chatos” Ser prática para criar/atualizar disquetes Usar o formato do Apple DOS 3.3 Todo mundo conhece Ferramentas conhecidas para suporte A CB2k também deve: Oferecer uma API consistente para programação API deve proteger as aplicações de: Mudanças nos endereços das rotinas do kernel (assim eu posso movê-lo pra cima e pra baixo, de acordo com a conveniência) Mudanças de formato de mídia (e até mesmo de mídia!) Disquetes estão ficando raros Facilitar Novas Aplicações! Jogos multi-partes (Karateka) Jogos BASIC com mais memória disponível Algo importante principalmente para o TK-2000 Menus para os jogos Demos Fornecer exemplos de como desenvolver aplicações Sistemas Operacionais não são nada sem aplicações!
  • #13: A CB2k não pode deixar de: Ser extensível e portável Outras arquiteturas baseadas em 6502 (porque não?) Outras mídias (porque não?) Ficar pronta em umas 4 ou 5 semanas. Férias acabam! Ser útil e agregar valor Na boa: ninguém precisa de ainda outra solução meia-boca pra ficar quebrando galho... Demais funcionalidades (rede, ambiente gráfico, co-processamento, etc.) são totalmente fora de escopo. Linus é um cara legal, não quero concorrer com ele! ;-) Ele ganha...
  • #33: Logo, não posso gravar qualquer byte no disco, pois algumas combinações de bits não são legíveis Boa parte dos bits são “desperdiçados”, pois têm que ficar obrigatoriamente em &apos;1&apos; Para gerar a inversão de fase, que serve de clock para a identificação dos bits... Codificações usadas pela indústria: GCR – Group Code Recording Adotada pelo Apple Originalmente, a interface Disk II não conseguia ler dois bits &apos;0&apos; seguidos Codificação 5x3 – 5 bits de dados intercalados com 3 bits &apos;1&apos; de clock Numa revisão posterior do hardware, o hardware passou a ser capaz de detectar 2 bits 0 seguidos (mas apenas uma vez por byte) Codificação 6x2 – 6 bits de dados intercalados com 2 bits &apos;1&apos; de clock, MFM – Modified Frequency Modulation RLL - Run Lenght Limited EFM – Eight to Fourteen Modulation Outras
  • #35: Quediaboéisso? São algoritmos em que o tempo de resposta faz parte do resultado do processamento Não é o mesmo que “fazer rapidinho” Um determiado processamento pode precisar ficar pronto só em 24 horas Ou 24 milisegundos... “ Entregar” depois do prazo é o mesmo que não entregar. Ou entregar lixo. “ Entregar” antes do prazo é desperdício de processamento Que pode ser necessário para entregar outra tarefa que está vencendo antes E o Kiko? Kiko&apos;eu tenho a ver com isto? Acessar disco é uma tarefa de tempo real Missão Crítica! Se você não ler a porta de I/O no milisegundo correto, você não leu nada. Se você não gravar na porta de I/O no millisegundo adequado, você destruiu os dados que estavam no disquete! Computadores modernos possui um micro controlador especializado para lidar com disco O Apple II não. Welcome to hell...
  • #40: “ Internalizar” algumas funções da ROM para o S.O. Me livrou de dependências externas Comeu uns bytes preciosos Mas viabilizou um binário único para todas as plataformas Facilitará aproveitar as extensões de memória no futuro Delegar à aplicação gerenciar o resto do hardware O S.O. identifica para você a máquina em que está rodando “ Bibliotecas” padrão no “User Space” E cada um que se vire! BASIC.SYSTEM Todo o suporte ao BASIC ficará ao cargo de uma (futura) “Aplicação” no User Space. “ Forkar” o Kernel para casos especiais Versões especializadas para cada arquitetura e/ou funcionalidade específica Versionar a API Congelar um subset mínimo da API com garantias de funcionamento em todas as versões futuras Oferecer à aplicação um mecanismo para que ela saiba o que o Kernel corrente é capaz de oferecer Gerência de Configuração to the rescue! :-)