Escreva um programa em assembly para monitorar o bit PC3. Quando o bit estiver com valor alto, escrever 0x55 em PORTD.

Passo 1

Beleza, manda ver: a questão pede um programa em Assembly (vamos assumir AVR, tipo ATmega328P) que fique monitorando o bit PC3. Sempre que esse bit estiver em nível lógico alto (1), a gente deve colocar o valor 0x55 em PORTD.
Matéria envolvida: configuração de registradores de direção (DDR), leitura de pinos (IN), teste de bit (SBRC) e escrita em porta (OUT). Vamos precisar entender como configurar DDRx, ler PINx, usar instruções de teste/branch e carregar constantes em registradores.

Passo 2

Configurar os registradores de direção:
  • DDRC define se cada pino de PORTC é entrada (0) ou saída (1). Como queremos ler PC3, deixamos esse bit como 0.
  • DDRD define porta D como saída se 1. Vamos mandar 0x55 para PORTD, então configuramos todos ou só os pinos que interessam como saída (por simplicidade, vamos setar todo o DDRD para 1).
Em Assembly AVR, fazemos assim:
    ldi r16, 0x00   ; r16 = 0x00
    out DDRC, r16   ; todos PCx como entrada
    ldi r16, 0xFF   ; r16 = 0xFF
    out DDRD, r16   ; todos PDx como saída

Passo 3

Agora precisamos de um loop infinito que:
  1. Leia o registrador PINC (estado atual dos pinos C).
  2. Teste o bit 3 (PC3).
  3. Se estiver alto, escreva 0x55 em PORTD.
  4. Volte pro início e repita.
Para ler PINC:
loop:
    in r17, PINC    ; traz em r17 o estado de todos os pinos C

Passo 4

Teste de bit PC3 em r17. Usamos SBRC (Skip if Bit in Register is Cleared), que pula a próxima instrução se o bit especificado estiver em 0. Ou seja:
    sbrc r17, 3     ; se bit 3 de r17 (=PC3) for 0, pula o próximo rjmp
    rjmp write55    ; se não pulou, significa que PC3=1, então vai pro label write55
    rjmp loop       ; PC3=0, volta ao início do loop sem escrever nada

Passo 5

No label write55, carregamos 0x55 em um registrador e escrevemos em PORTD, depois voltamos ao loop:
write55:
    ldi r18, 0x55   ; r18 = 0x55
    out PORTD, r18  ; escreve 0x55 em PORTD
    rjmp loop       ; volta pra ler PINC de novo

Resposta

Segue o programa completo em AVR Assembly:
    ;--------------------------------------------------
    ; Programa: Monitora PC3 e escreve 0x55 em PORTD
    ;--------------------------------------------------
    .include "m328pdef.inc"  ; nome do header para ATmega328P (ajuste conforme o MCU)
    .cseg
    rjmp start

start:
    ; 1) Configurações iniciais
    ldi r16, 0x00
    out DDRC, r16       ; DDRC = 0x00 -> PC3 como entrada
    ldi r16, 0xFF
    out DDRD, r16       ; DDRD = 0xFF -> todos PDx como saída

loop:
    ; 2) Leitura de PINC
    in  r17, PINC       ; r17 = estado dos pinos C

    ; 3) Teste do bit PC3 (bit 3)
    sbrc r17, 3         ; se PC3 == 0, pula próximo rjmp
    rjmp write55        ; se PC3 == 1, vai escrever 0x55
    rjmp loop           ; se PC3 == 0, volta pro início

write55:
    ; 4) Escreve 0x55 em PORTD
    ldi r18, 0x55
    out PORTD, r18
    rjmp loop           ; repete indefinidamente

Exercícios relacionados