
          ͻ
                    Tutorial de Assembler de Adam Hyde 1.0        Ŀ
                                                                   
                                  PARTE II                         
                      Traduzido por Renato Nunes Bastos            
          ͼ 
            


Verso   :  1.2
Data     :  17-02-1996
Contato  :  blackcat@vale.faroc.com.au
            http://www.faroc.com.au/~blackcat
;Renato  :  bastos@lci.ufrj.br
            krull@geocities.com
            http://www.geocities.com/SiliconValley/Park/3174


 

Ol de novo, futuros proramadores de Assembler. Para aqueles que perderam
a primeira parte, pegue-a agora na minha homepage.

De qualquer modo, no ltimo nmero eu disse que estaria discutindo sobre
hexadecimal, segmentos + offsets, mais algumas intrues e algumas procedures
contendo assembler que voc poderia realmente usar.

Ento, l vamos ns, com segmentos e offsets!


 

 LIO 3 - Segmentos e Offsets
---------------------------------

Antes de explorarmos o grande e mau mundo dos segmentos e offsets, h umas
terminologias que voc precisar conhecer.

    O BIT - a menor parte de dados que podemos usar. Um bit - um oitavo de
     um byte pode ser ou um 1 ou um 0.  Usando esses dois dgitos podemos
     fazer nmeros em BINRIO ou BASE 2.

     EX.:    0000 = 0   0100 = 4   1000 = 8    1100 = 12   10000 = 16
             0001 = 1   0101 = 5   1001 = 9    1101 = 13   ...Acho que voc
             0010 = 2   0110 = 6   1010 = 10   1110 = 14   j sacou..
             0011 = 3   0111 = 7   1011 = 11   1111 = 15

    O NIBBLE, ou quatro bits. Um nibble pode ter um valor mximo de 1111 que
      15 em decimal.  aqui que o hexadecimal entra. Hex  baseado naqueles
     16 nmeros, (0-15), e quando escrevemos em hex, usamos os 'dgitos'
     abaixo:

     0 1 2 3 4 5 6 7 8 9 A B C D E F

     Hexadecimal  na verdade muito fcil de se usar, e, apenas como
     curiosidade, eu acho que os Babilnios - uma civilizao antiga qualquer
     - usava um sistema de numerao em BASE 16. Tem algum historiador a
     fora que queira confirmar isso?

     IMPORTANTE >>> Um nibble pode aguentar um valor at Fh <<< IMPORTANTE

    O BYTE - o que mais usaremos. O byte tem 8 bits de tamanho - isso  2
     nibbles, e  o nico valor que voc vai conseguir colocar num registrador
     de 8 bits. EX.: AH, AL, BH, BL, ...

     Um byte tem um valor mximo de 255 em decimal, 11111111 em binrio,
     ou FFh em hexadecimal.

    A WORD - outra unidade comumente usada. Uma word  um nmero de 16 bits,
     e  capaz de armazenar um nmero at 65535. Isso  1111111111111111 em
     binrio, e FFFFh em hex.

     Obs.:  Por causa de uma word ser quatro nibbles,  tambm representada
            por quatro dgitos hexadecimais.

     Obs.:  Isto  um nmero de 16 bits, e corresponde aos registradores de
            16 bits. Ou seja, AX, BX, CX, DX, DI, SI, BP, SP, DS, ES, SS
            e IP.

    A DWORD, ou double word consiste de 2 words ou 4 bytes ou 8 nibbles ou
     32 bits. Voc no vai usar muito as double words nestes tutoriais, mas
     vamos mencion-las mais tarde quando falarmos de PROGRAMAO EM 32 BITS.

     Uma DWORD pode armazenar de 0 a 4,294,967,295, que  FFFFFFFFh, ou
     11111111111111111111111111111111.  Espero que haja 32 um's l atrs.

     A DWORD tambm  o tamanho dos registradores extendiddos de 32 BITS,
     ou seja, EAX, EBX, ECX, EDX, EDI, ESI, EBP, ESP e EIP.

    O KILOBYTE,  1024 bytes, NO 1000 bytes.  O kilobyte  igual a
     256 double-words, 512 words, 1024 bytes, 2048 nibbles ou 8192 BITS.
     Eu no vou escrever todos os um's.

    O MEGABYTE, ou 1024 kilobytes. Isso  1,048,576 bytes ou 8,388,608
     bits.

Agora que j cobrimos a terminologia, vamos dar uma  olhada mais de perto como
aqueles registradores so estruturados. Ns dissemos que AL e AH eram
registradores de 8 bits, logo, eles no deveriam se parecer com algo assim?

                    AH                                 AL
           Ŀ              Ŀ
             00000000                  00000000  


Neste caso, ambos AH e AL = 0, OU 00h e 00h.  Como resultado, para calcular 
AX usamos:  AX = 00h + 00h. Quando digo + eu quero dizer, 'ponha junto' no
AX = AH MAIS AL.

Assim, se AH era igual a 00000011 e AL era igual a 0000100, para calcular 
AX ns devemos fazer o seguinte.

1) Pegue os valores hexadecimais de AH e AL.

   00000011 = 03h   00010000 = 10h

2) Combine-os.

   AX = AH  + AL
   AX = 03h + 10h
   AX = 0310h

E a voc consegue o resultado. No  to macetoso assim.

Okay, agora vamos ver os registradores de 16 bits:


                                 AX
                     Ŀ
                                            

                    AH                       AL
           Ŀ    Ŀ
             00000000        00000000  

De onde podemos ver que AX = 00000000 e 00000000, ou 0000000000000000.


Agora por ltimo, vejamos como um registrador de 32 bits se parece:

              Ŀ
                                    EAX                       
              Ŀ                        
                         AX                                  
              Ĵ                        
               00000000    00000000  00000000     00000000  
                  AH          AL                            
              

No  muito difcil, espero. E se entendeu isso, voc est pronto para
SEGMENTOS e OFFSETS.


 Uma Arquitetura Segmentada
-----------------------------

H muito, muito tempo atrs, quando a IBM construiu o primeiro PC, no era
costume programas terem mais de 1 megabyte - eca, os primeiros XT's tinham
apenas 64K de RAM! De qualquer modo, vendo que os projetistas do XT no
consideravam aplicaes enormes, decidiram dividir a memria em SEGMENTOS,
pequenas reas de memria RAM que voc pode colocar APENAS uma tela virtual
para grficos em modo 320x200x256.

 claro, voc pode acessar mais de um megabyte de RAM, mas voc tem que
dividi-la em segmentos para us-la, e esse  o problema.  obvio, com
programao em 32 bits d pra acessas at 4GB de RAM sem usar segmentos, mas
isso  uma outra histria.

Segmentos e offsets so apenas um mtodo de especificar uma posio na memria.


EG:   3CE5:502A

      ^^^^ ^^^^
      SEG  OFS

Okay, aqui est a especificao:


Um OFFSET  = SEGMENT X 16
Um SEGMENT = OFFSET  / 16

Algums registradores de segmento so:

CS, DS, ES, SS e FS, GF  - Obs.: Os ltimos 2 so registradores que s existem
                                 em 386 ou superiores.

Alguns registradores de offset so:

BX, DI, SI, BP, SP, IP     - Obs.: Quando em modo protegido, voc pode usar
                                   qualquer registrador de uso geral como
                                   um registrador de offset - EXCETO IP.


Alguns segmentos e offsets comuns so:

    CS:IP - Endereo do cdigo executando no momento.
    SS:SP - Endereo da posio atual da pilha.

    OBS.: NO SE INTROMETA COM ELES !

Assim quando nos referirmos a segmentos e offsets, faremos dessa forma:

SEGMENTO:OFFSET

Um bom exemplo seria:

A000:0000 - que na verdade corresponde ao topo esquerdo da tela VGA em
            modo colorido 320x200x256.

            ** FATO ENGRAADO ** A RAM da VGA comea em A000h  :)


 

Ufa! Isso foi muito para o segundo tutorial. Contudo, ainda no terminamos.
Esse negcio de AX, AH, AL  um conceito que voc pode no ter sacado ainda,
ento l vamos ns:

    MOV   AX, 0     ; AX = 0
    MOV   AL, 0     ; AL = 0
    MOV   AH, 0     ; AH = 0

    MOV   AL, FFh   ; AL = FFh
                    ; AX = 00FFh
                    ; AH = 00h

    INC   AX        ; AX = AX + 1

                    ; AX = 0100h
                    ; AH = 01h
                    ; AL = 00h

    MOV   AH, ABh   ; AX = AB00h
                    ; AH = ABh
                    ; AL = 00h


Pegou?


COISAS A FAZER:

1) Aprender aquele negcio de BIT/NIBBLE/BYTE... de cor.
2) Voltar nos exemplos de segmento e offset.
3) Tenha certeza que voc entendeu a relao entre AX, AH e AL.
4) Que tal um problemas de adio hexadecimal?


 

 A Pilha
-----------

A pilha  uma caracterstica muito til de que podemos tirar vantagem. Pense
nela como uma pilha de papis numa bandeja de ENTRADA. Se voc pe algo no
topo, ela ser a primeira a ser tirada.

 medida que voc adiciona algo  pilha, o apontador de pilha  DECREMENTADO,
e quando tira,  INCREMENTADO. Para explicar isso melhor, veja o diagrama
abaixo:

    Ŀ
         A  PILHA     
    Ĵ
                            <<< Quando colocamos um byte na pilha, ele vai
                               aqui - ltimo a entrar, primeiro a sair.
                     
                     
                     
                     


      SP                    <<< O ponteiro de pilha se move para baixo.
    


E na prtica:


   MOV   AX, 03h   ; AX = 03h
   PUSH  AX        ; PUSH AX na pilha (coloca no topo)

   MOV   AX, 04Eh  ; AX = 04Eh

                   ; Faa alguma coisa... uma soma?

   POP   AX        ; AX = 03h

Ou:

   MOV   AX, 03h   ; AX = 03h
   PUSH  AX        ; Adiciona AX  pilha

   MOV   AX, 04Eh  ; AX = 04Eh

                   ; Faa alguma coisa... uma soma?

   POP   BX        ; BX = 03h


Voc acabou de aprender duas instrues:

    PUSH <registrador>   - PUSH (coloca algo na pilha), e

    POP <registrador>    - POP (retira ele de volta).


 tudo o que voc precisa de aprender sobre pilha - por enquanto.


 

Por ltimo, algumas procedures que demonstram algo disso tudo. Note que
os comentrios foram DELIBERADAMENTE REMOVIDOS.  seu dever tentar 
coment-los. Note tambm, que algumas novas instrues so introduzidas.


Procedure ClearScreen(A : Byte; Ch : Char);   Assembler;

Asm     { ClearScreen }
  mov   ax, 0B800h
  mov   es, ax
  xor   di, di
  mov   cx, 2000
  mov   ah, A
  mov   al, &Ch
  rep   stosw
End;    { ClearScreen }


Procedure CursorXY(X, Y : Word);   Assembler;

Asm    { CursorXY }
   mov   ax, Y
   mov   dh, al
   dec   dh
   mov   ax, X
   mov   dl, al
   dec   dl
   mov   ah, 2
   xor   bh, bh
   int   10h
End;    { CursorXY }


Procedure PutPixel(X, Y : Integer; C : Byte; Adr : Word);   Assembler;

Asm     { PutPixel }
   mov   ax, [Adr]
   mov   es, ax
   mov   bx, [X]
   mov   dx, [Y]
   xchg  dh, dl
   mov   al, [C]
   mov   di, dx
   shr   di, 2
   add   di, dx
   add   di, bx
   stosb
End;    { PutPixel }


Procedure Delay(ms : Word);   Assembler;

Asm     { Delay }
   mov   ax, 1000
   mul   ms
   mov   cx, dx
   mov   dx, ax
   mov   ah, 86h
   int   15h
End;    { Delay }


COISAS A FAZER:

1) V ao exemplo de pilha. Faa seu prprio cdigo exemplo.
2) Comente as procedures acima do melhor modo que puder. Tente adivinhar o que
   as novas intrues fazem. No  to difcil.


 


                              NA PRXIMA SEMANA:
                            ----------------------

            Muito mais instrues, todos os JUMPS.

            O que so flags?

            As proceures acima com comentrios.

            Um programa s em assembler. Voc vai precisar pelo menos do
             DEBUG, embora TASM e TLINK sejam uma boa idia.



Se voc deseja ver um tpico discutido num tutorial no futuro, escreva-me, e
eu vou ver o que eu posso fazer.


 

No perca!!! Baixe o tutorial da prxima semana na minha homepage:

   http://www.faroc.com.au/~blackcat
   http://www.geocities.com/SiliconValley/Park/3174

- Adam Hyde.
- Renato Nunes Bastos.
