You are on page 1of 52

UNIVASF

Microprocessadores e
Microcontroladores
Conjunto de Instruções do
PIC16F877A
Prof. Rodrigo Ramos
godoga@gmail.com

Tipos de Instruções

A família PIC16F87XA possui 35 instruções

São divididas basicamente em quatro tipos:

Instruções de transferência de dados

Instruções de processamento de dados

Instruções de mudança de direção de execução

Instruções de controle

Tipos de Instruções
 Instruções de transferência de dados: limitam-se a mover dados da memória

de programa para o espaço de registradores e entre registradores, sempre
passando pela ULA.

Literal ou endereçamento imediato: dados são parte da instrução.

Acesso

direto: usa endereço da instrução mais endereçamento do
banco de memória.

Endereçameto indexado: através dos registradores FSR e INDF.

Tipos de Instruções (cont.)
Instruções de processamento de dados: dado sai do
registrador, passa pela ULA junto com o conteúdo do
WREG e volta ao registrador ou WREG. Operações
disponíveis:

Adição e subtração

Incremento e decremento

Limpar registrador (clearing)

Bit setting e bit clearing (resetting)

AND, OR, XOR e complemento bit-a-bit

Tipos de Instruções (cont.)
Instruções de mudança de direção de execução:
causam desvio na execução normal do programa

call e goto

Saltos condicionais

São três: − NOP: Sem operação.  SLEEP: aciona o modo de baixa potência da CPU. O processador gasta um ciclo sem executar nenhuma operação.   CLRWDT: Zera o contador watchdog. .Tipos de Instruções (cont.) Instruções de controle: usadas para funções internas e controle da CPU.

Conjunto de Instruções .

e modifique-o para cada nova instrução apresentada.  Verifique o estado dos bits do registrador STATUS para cada instrução.  . usando o Watch do MPLAB.Conjunto de Instruções Nas descrições a seguir.  Use o mesmo arquivo. criar um projeto no MPLAB para verificar o funcionamento de cada instrução.

“d” = “w” or “f” .pela ULA e seta o flag Zero . d .Move o conteúdo de “Variable” .Instruções de transferência de dados   movlw k − Método básico para carregar w com valor constante: − Ex. −Ex.copia 0x12 para posicao 0x20 movf Variable.Grava “Variable” de acordo com .: movlw 0x12 movwf f − Copia conteúdo de w para f.: movlw 0x12 movwf 0x20  .carrega w com 0x12 .dependendo do seu valor. .

Isto condiz com o esperado?  movlw 0x47 movwf 0x20 movlw 0x00 movwf 0x21 movf 0x20. f goto $ O que acontece se a penúltima linha for modificada para movf 0x21. 0x22 ?  .) Copie o seguinte trecho do programa e verifique os pontos em que o flag Z é setado. w movf 0x21.Instruções de transferência de dados (cont.

− Útil para carregar WREG sem alterar nenhum flag de STATUS.d − − Troca o nibble mais significativo pelo menos significativo do registrador f e guarda de volta em f ou em WREG. Não modifica nenhum flag. − .Instruções de transferência de dados (cont.)  clrw  Limpa o conteúdo de WREG clrf f  Limpa o conteúdo do registrador reg swapf f.

Instruções de transferência de dados (cont. em especial WREG e os flags do STATUS. w goto $  O que fazem as duas linhas com o comando swapf? . f swapf 0x20. Carrega registrador 0x20 com valor .  movlw 0xF5 movwf 0x20 . Seta bits aritméticos de STATUS swapf 0x20. 0xF5 movlw 0x1F movwf STATUS .) Copie o seguinte trecho do programa e verifique seu funcionamento.

execute o código a seguir: − movlw b'01111111' movwf 0x20 bsf 0x20.b  Limpa o bit b do registrador f bsf − Seta o bit b do registrador f  Para verificação. 0 goto $ .)  bcf f. 7 bcf 0x20.Instruções de transferência de dados (cont.

0X20 com valor 0x5A .Instruções de transferência de dados (cont.RP0> para endereçamento de banco  movlw movwf 0x5A 0x20 bsf STATUS. RP0 movwf 0x20 goto $ . carrega reg.  . seleciona banco 1 Usar a janela File Registers para verificar o funcionamento do programa.) Uso dos bits STATUS<RP1.

 . do . no banco 1 (reg 0xAA)‫‏‬ . carrega valor 0x23 no reg.Instruções de transferência de dados (cont. banco 1 Observe que é possível acessar o banco 1 sem modificar o bit RP0. carrega FSR com endereço de reg.) Uso dos bits STATUS<IRP> para endereçamento indexado (indireto)   Registrador FSR é o ponteiro e INDF é usado para acesso movlw movwf 0xAA FSR movlw 0x23 movwf INDF goto $ . .

Conjunto de instruções  Identifique o erro no programa a seguir e corrija-o. clrf movlw movwf goto  TRISC b'00001111' PORTC $ Verificação do espelhamento: ex. PCLATH movlw movwf bsf movf goto 0x05 PCLATH STATUS. RP0 PCLATH $ .

O programa deve escrever um número qualquer no display.  Utilize o Proteus para verificar o funcionamento do display.  Dica: utilize a diretiva BANKSEL Reg.Exercício Escreva um programa para acionar um display de 7 segmentos através da porta B. assim como verificar o programa.  . que é usada pelo montador para selecionar automaticamente o banco referente ao registrador Reg.

: addwf 0x20.f .: addlw 55 addwf f.d Adiciona conteúdo do registrador f a WREG e guarda ou em WREG ou no próprio f. − − Operação: d ← w + f − Ex. − Operação: w ← w + k − Ex.Instruções de processamento de dados   addlw k − Adiciona constante k a WREG e guarda em WREG.

adiciona 0x0A a 0x0A . e guarda em WREG/ Flag C = 1 .  movlw movwf addwf 10 0x20 0x20. e guarda em WREG/ Flag DC = 1 .Instruções de processamento de dados (cont. w movlw 160 movwf 0x20 addwf 0x20. w goto $ . adiciona 0xA0 a 0xA0 .) Copie o seguinte trecho do programa e verifique os flags C e DC sendo modificados.

− − Operação: d ← f + (-w) − Na verdade: d ← f + [ (w ^ 0xFF) + 1 ] XOR Ex.Instruções de processamento de dados (cont.)  subwf f. d Subtrai do conteúdo do registrador f o conteúdo de WREG e guarda ou em WREG ou no próprio f.: Se quiséssemos realizar a operação 1 – 2 no PIC. w Carry: “empréstimo negativo” Resultado negativo: C = 0 Resultado positivo: C = 1 . faríamos: − movlw movwf movlw subwf 1 0x20 2 0x20.

Ex.: Se quiséssemos realizar as operações 1 – 2 e 2 – 1 no PIC.)  sublw k − Operação: w ← k + (-w) − Trabalha de modo similar a subwf. faríamos: − movlw 2 sublw 1 movlw 1 sublw 2 − O que faz a operação abaixo? sublw − 0 O que fazer para subtrair um valor de WREG? addlw -45 .Instruções de processamento de dados (cont.

d . − Para complemento de 2.)  decf f.Instruções de processamento de dados (cont. deve-se fazer: comf f. − − Complemento de 1. d  − Operações de incremento e decremento de f. − Resultado é salvo em d (WREG ou f). com resultado salvo em d. d  incf f. d incf f. comf f. d Complementa (inverte logicamente) o conteúdo do um registrador f.

Instruções de processamento de dados (cont. f decf decf decf 0x20.) Verifique o programa abaixo e tente prever o resultado final dos registradores 0x20 e WREG. w 0x20. w comf incf 0x20. f 0x20. w 0x20. f 0x20.  movlw 47 movwf 0x20 incf incf incf 0x20. f goto $ . f 0x20.

xorwf f. iorwf f.Instruções de processamento de dados (cont.)  andlw k  AND entre k e o conteúdo de WREG. d − − − − − − XOR entre o conteúdo de f e o conteúdo de WREG. . d  AND entre o conteúdo de f e o conteúdo de WREG. andwf f. d  (Inclusive) OR entre o conteúdo de f e o conteúdo de WREG. xorlw k  XOR (ou exclusivo) entre k e o conteúdo de WREG. iorlw k  (Inclusive) OR entre k e o conteúdo de WREG.

salvando resultado em d (rotate right .rr). d Deslocamento à esquerda do conteúdo de f.Instruções de processamento de dados (cont. − −  Deslocamento com carry STATUS<C> rrf f. d Deslocamento à esquerda do conteúdo de f. − − Deslocamento com carry STATUS<C> .rl).)  rlf f. salvando resultado em d (rotate left .

) Para que não se perca nenhum bit no processo de rotação.fragmento) rrf Reg.Instruções de processamento de dados (cont. Na segunda instrução. o carry é carregado com o LSB de Reg (Reg<0>) e o resultado é salvo em WREG. o carry é colocado no MSB de Reg (Reg<7>). w rrf Reg. f  Na primeira instrução. pode-se usar o seguinte trecho de código (chamado snippet . .

) O código a seguir mostra o uso do snippet anterior para deslocar um bit do registrador 0x20 de 4 posições.  movlw b'00100000' movwf 0x20 rrf 0x20. w rrf 0x20.Instruções de processamento de dados (cont. f rrf 0x20. w rrf 0x20. f rrf 0x20. f goto $ . w rrf 0x20.

 . testando-o nos kits didáticos.  O incremento deve ocorrer quando for ativado um botão (push button) conectado ao pino RA0.  Implemente o dispositivo no protoboard e programe o PIC16F877A com seu firmware.Exercício 1 Escreva um programa que incremente o número binário mostrado em um conjunto de 8 leds conectados ao PORTB.

apenas as operações de transferência e de processamento de dados.  Lembrar que uma rotação à esquerda com um zero em LSB equivale a uma multiplicação por 2. uma segunda rotação equivale a multiplicar por 4 e assim por diante.  Não usar desvio condicional.  .Exercício 2 Escreva um programa que realize a multiplicação 9 x 5 (note que N x 5 = N x 4 + N x 1).

 DICA: Utilize labels para especificar os registradores que guardarão os valores a serem usados.Exercício 3 Escreva um programa para somar dois números de 16 bits. . Dica: use a diretiva CBLOCK para definir blocos de constantes..  CBLOCK 0x20 Var1.. VarN ENDC Não usar desvio condicional.  . Var2. apenas as operações de transferência e de processamento de dados. Var3..

Para valores de labels acima disso.Instruções de desvio  goto k − Desvia programa para o ponto k (geralmente um label) − Desvio incondicional sem retorno. Lembrar que a instrução só consegue endereçar 211 bytes = 2048 bytes (0x800). − Dois ciclos de máquina. − . devese usar os bits PCLATH<4:3>.

Organização da Memória (cont.)  Memória de programa − 13 bits para endereçamento − 8k palavras x 14 bits 0x0800 = 0000 1000 0000 0000 0x1000 = 0001 0000 0000 0000 0x1800 = 0001 1000 0000 0000 HIGH LOW .

Instrução não executada FirstLabel: movlw HIGH SecondLabel . considere o código abaixo.  goto movf FirstLabel STATUS.) Como exemplo do uso do goto. HIGH retorna o byte mais signif. Execução do goto $ abaixo .Instruções de desvio (cont. Endereco na pagina 3 . w . movwf PCLATH goto SecondLabel org 0x376 movlw 40 org 0x1B76 SecondLabel: goto $ . Habilite a opção View → Program Memory do MPLAB.

Ao fim da sub-rotina. com exceção de que PC é salvo na pilha. uma instrução return (ou equivalente) faz com que o fluxo retorne ao ponto seguinte à chamada. − Pilha (13-bits x 8)‫‏‬ Topo da pilha ULA . − − Dois ciclos de instrução. Operação idêntica à goto.Instruções de desvio (cont.)  call k − Chamada de subrotina especificada por k.

retlw k Retorno de sub-rotina.)  return −  Retorno de sub-rotina. com valor k copiado em WREG. útil para criação de tabelas. INTCON<GIE> = 1 (habilita interrupções) Pilha (13-bits x 8)‫‏‬ Topo da pilha ULA . − −  Equivalente a movlw k return retfie − Retorno de interrupção.Instruções de desvio (cont.

Exercício Re-escreva o programa para somar dois números de 16 bits.  . utilizando agora uma sub-rotina. de forma a que seja possível realizar a soma diversas vezes a partir da chamadas à sub-rotina.

skip if clear) −  btfss f. skip if set) −   Testa o bit b do registrador f e salta próxima instrução se b = 0.   btfsc f. desvia para Label . Z goto Label .: Saltar para um endereço se flag Z for 1.Instruções de desvio (cont. Tempo de execução: − 1 ciclo se condição for falsa (sem desvio) − 2 ciclos se verdadeira (com desvio) Ex.salta a próxima instrução dependendo da condição do bit testado. b (bit test file-reg. Testa se Z = 0 e salta se V . b (bit test file-reg. Testa o bit b do registrador f e salta próxima instrução se b = 1. Instruções “skip on bit condition” .)  Desvios condicionais – só desviam fluxo se condição for verdadeira. btfsc STATUS. Se Z = 1.

 . escreva no registrador 0x25 o valor 0x0E. Caso eles sejam iguais. escreva 0x0D.Exercício Escreva um programa em assembly que compare dois valores vA e vB. Caso sejam diferentes.

movf e subwf devem ser substituídas por movlw e sublw. w btfs# STATUS. SecondValue e # são definidos na tabela a seguir.   Pseudo-código: if (A condição B) then goto Label  Assembly: movf FirstValue.) Desvios condicionais – de forma geral.Instruções de desvio (cont. Caso sejam usadas constantes. desvios baseados na comparação de dois valores têm uma forma definida.  . flag goto Label  Onde FirstValue. w subwf SecondValue.

Instruções de desvio (cont.) .

)  Desvios condicionais  incfsz f. d Incrementa o registrador f. −  decfsz f. −   Tempo de execução: − 1 ciclo se resultado não for zero (não salta próxima instrução) − 2 ciclos se for zero (salta) São geralmente utilizados para controle de loops. d Decrementa o registrador f. salva resultado em d e salta próxima instrução se o resultado do decremento for zero.Instruções de desvio (cont. . salva resultado em d e salta próxima instrução se o resultado do incremento for zero.

Instruções a serem executadas repetidamente decfsz 0x20. f . caso contrário.  movlw movwf 10 0x20 .) O código a seguir pode ser usado para repetição de um trecho de programa 10 vezes. decrementa contador goto Loop . continua . carrega contador Loop: .Instruções de desvio (cont. repete . se não é zero.

São usadas para retornar valores de acordo com o parâmetro passado à tabela.  No novo endereço.   Ex. f.  A forma mais tradicional no PIC é com o uso de uma subrotina que adiciona uma constante ao PC.: Tabela de quadrados de números.  IMPORTANTE: PC é incrementado antes da execução da instrução!!  . com o uso da instrução addwf PCL. uma instrução retlw é usada para salvar em WREG o valor a ser retornado.Tabelas Estruturas de dados para armazenamento de constantes e apontadas por um índice (banco de dados de uma coluna).

) Exemplo: Programa para determinar quadrado de um número entre 0 e 6. Assim.  Quadrado: addwf retlw retlw retlw retlw retlw retlw retlw main movlw call goto END PCL. PCL = 5 + 2 = 7 .f 0 d'1' d'4' d'9' d'16' d'25' d'36' 0x05 Quadrado $ .Tabelas (cont. . PCL é incrementado antes da execução.

w LOW Quadrado2 STATUS. PCLATH deve ser modificado. Temp HIGH Quadrado2 PCLATH Temp.  Quadrado: movwf movlw movwf movf addlw btfsc incf movwf Quadrado2: retlw retlw . C PCLATH... Se houver. f PCL 0 1 .) Deve-se ter o cuidado de não haver cruzamento de página na tabela.Tabelas (cont.

 . Os bits de acionamento dos números de 0 a 9 devem estar disponíveis em uma tabela.Exercício Escreva um programa em assembly para acionamento de um display de 7 segmentos usando uma tabela.

 . são necessários 25.: Para um atraso de 5 ms em um PIC rodando a 20MHz.2 us. Atrasos de tempo podem ser convertidos em ciclos de instrução pela expressão:   Ciclos de instrução = Atraso de tempo * (Freq. Clock / 4) Ex.Atrasos (Delays)  Unidade básica de tempo é o ciclo de instrução:  Ciclo de instrução = 4 / freqüência de clock  Ex. temos:   Ciclos de instrução = 5 x 10-3 (20 x 106 / 4) = 25.000 ciclos de instruções para obter um atraso de 5 ms.000 Assim.: Para um clock de 20 MHz: Ciclo de instrução = 4 / 20 MHz = 0.

pode-se usar loops que decrementem um contador. k = k-1.f . pula se zero goto kloop decfsz j. w = 200 decimal movwf j .) A maneira mais simples de criar atrasos é 'gastando tempo' com instruções.Atrasos (cont. j = w jloop: movwf k .  Com um contador duplo.008 s (clock de 20MHz)  delay: movlw . pula se zero goto jloop return . k = w kloop: decfsz k. conta-se aproximadamente o quadrado disto.  Para isso. Contador de ~(200)2 = 400. podendo-se contar 256 vezes (ciclos de instrução).000 ciclos = 0.200 . Ex.f . j = j-1.

Z decfsz DelayH. f goto loop return Valor = ((atraso * freqüência/4)/5) + 256 Ex. f btfsc STATUS.256 = 0x10A0 .)  Forma alternativa: delay: movlw LOW Valor movwf DelayL movlw HIGH Valor movwf DelayH loop: decf DelayL.: 20 ms com clock 4 MHz Valor = ( (20 x 10-3 x 1 x 106) / 5) + 256 = 4.Atrasos (cont.

) Para atrasos maiores. o que dá 250. Porém. usa-se loop externo.05 s com 20MHz).  Valor pode ir até 65.  delay: movlw movwf loopExt: movlw movwf movlw movwf loop: decf btfsc decfsz goto decfsz goto return 4 ValorRep LOW Valor DelayL HIGH Valor DelayH DelayL.Atrasos (cont. Z DelayH. faz-se Valor máximo = 50. f STATUS.535 (0xFFFF).256 (0xC450). por facilidade.  Exercício: Testar código ao lado para que acenda e apague um led conectado ao pino RB0. f loop ValorRep loopExt .  Para ~1 s.000 ciclos (0. repete-se 20 vezes o loop.

enquanto um valor digital 1 esteja presente em um pino de entrada. Se o pino estiver em nível 0. .Exercício Escreva um programa em assembly que acenda 4 leds na barra gráfica. cada um sendo acionado durante ~100ms com os demais apagados. desativar todos os leds. Utilize uma rotina de atraso para gerar os 100ms.

3rd. Microchip Technology Inc. “Microcontroladores PIC: Técnicas Avançadas – 16F627 e 16F628”.. Predko. Érica.Bibliografia  MPASM User's Guide. 2008. Microchip Technology Inc. “Programming and Customizing the PIC Microcontroller”. 2003. 2005. Ed. McGraw-Hill. Pereira..  PIC16F87xA Data Sheet.. 5a.  F.. M.  . Ed. 2008.