Ir ao conteúdo
  • Cadastre-se
Entre para seguir isso  
Paivas

[Resolvido] Duvidas sobre interrupções em microcontrolador AVR

Recommended Posts

Ola pessoal

Sou iniciante em programar microcontroladores. estou programando a butterfly, e desenvolvi o seguinte código.

#include <avr/io.h>
#include <avr/interrupt.h>

int var_3=0x00;

void iniciarInt(void)
{
TIMSK0|=(1<<TOIE0);
TCCR0A|=(0<<CS02)|(0<<CS01)|(1<<CS00);
SREG|=(1<<7);
}

int main(void)
{
int var_1;
iniciarInt();

while(1)
{
var_1=PINB;
if(var_1>var_3)
{
var_3=var_1;
}
}
}

ISR(TIMER0_OVF_vect)
{
SREG|=(0<<7);
DDRD=0xFF;
PORTD=var_3;
var_3=0x00;
SREG|=(1<<7);
}

Pretendo que o valor de PORTD apresente o valor da variavel var_3, que corresponde à tensão máxima existente no porto de entrada B num determinado periodo de tempo.

Sempre que ocorre uma interrupção por overflow do timer, a variavel var_3, e portanto o portoD, apresentam um valor 0x00, e não o valor máximo.

Que posso fazer para que quando ocorra uma interrupção, o portoD apresente o valor máximo ocorrido?

obrigado pela atenção:)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Olha, eu nunca programei AVR em C, só em ASSEMBLY, então peco desculpas antecipadamente se eu estiver falando besteira:

1: Nao entendi exatamente o que voce quis dizer com "corresponde à tensão máxima existente no porto de entrada B"... o que voce quer é fazer uma leitura em um pino com ADC e depois enviar o valor lido para um port inteiro de saida, seria isto ?

2: voce só coloca um valor diferente de 0 em var 3 em um ponto do programa, mas isto ocorre somente se var_1>var_3, mas o valor de var_1 esta indefinido, e pode ser que seja inicializado em zero, nao permitindo que o valor de var_3 seja alterado... ou seja, var_3 nunca sai de zero, e consequentemente PORTD tambem nao (ah, você nao precisa configurar DDRD toda hora que for escrever algo, basta fazer isto uma unica vez no inicio do programa);

3: Em assembly quando ocorrem interrupcoes nao é necessario mexer no bit I do SREG, o hardware já faz isto automaticamente. Acho muito estranho isto ser necessario em C como voce fez nas seguintes linhas:

SREG|=(0<<7); /* Pelo que entendi esta linha faz um OU com SREG e 0000000, ou seja, nao faz nada */

SREG|=(1<<7); /* Esta linha seta o bit I. Em assembly tem uma intrucao especifica pra setar este bit e retornar: "RETI". */

De uma pesquisada pra confirmar se é mesmo necessario o uso destas duas linhas acima mencionadas.

Compartilhar este post


Link para o post
Compartilhar em outros sites

Obrigado pela sua resposta

Concordo consigo em tudo o que disse. Realizei este programa no simulador AVR studio 4, e como não posso simular com uma entrada analógica, considerei o PORTB como o valor digital obtido do conversor A/D.

Após simulando o programa, variando a entrada digital no PORTB conclui que: A rotina de interrupção não consegue ler(obter) o valor actualizado de uma variavel, neste caso var_3.

Alguem sabe como obtenho o valor na rotina de interrupção de uma variavel que é actualizada?

Obrigado pela vossa atenção e respostas :)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Já descobri a solução para o problema :D

Tinha de definir a variavel var_3 da seguinte forma:

- volatile int var_3=0x00;

Obrigado a todos:)

Compartilhar este post


Link para o post
Compartilhar em outros sites

Caso o autor do tópico necessite, o mesmo será reaberto, para isso deverá entrar em contato com a moderação solicitando o desbloqueio.

Compartilhar este post


Link para o post
Compartilhar em outros sites
Visitante
Este tópico está impedido de receber novos posts.
Entre para seguir isso  





Sobre o Clube do Hardware

No ar desde 1996, o Clube do Hardware é uma das maiores, mais antigas e mais respeitadas publicações sobre tecnologia do Brasil. Leia mais

Direitos autorais

Não permitimos a cópia ou reprodução do conteúdo do nosso site, fórum, newsletters e redes sociais, mesmo citando-se a fonte. Leia mais

×