atmega8 de int0 kesmesini kullanmaya çalışıyorum.kesme çalışıyor fakat ilk enerjilenme durumunda 1 defaya mahsus kendiliğinden kesmeye gidiyor.bunu nasıl çözebiliriz?
eğer sakıncası yoksa kesmeyi belli bi zaman gecikmesinden sonra aktif edebilirsiniz.
onuda deniyorum 500ms ye ye kadar gecikme koydum ama yinede kendiliğinden kesme oluştu.
kesme register ayarlarınıda gecikme sonunda yapmayı denedinizmi..
kesmeleri aktif ettiğiniz andamı gidiyo kesmeye sei(); den sonra bende avr kullanıyorum ama karşılaşmadım daha önce böyle bi sorunla..
edit:
son bişey daha merak ettim :) işlemciyi değiştirdinizmi..
Alıntı yapılan: SERRO EFE - 15 Haziran 2011, 23:48:43
kesme register ayarlarınıda gecikme sonunda yapmayı denedinizmi..
kesmeleri aktif ettiğiniz andamı gidiyo kesmeye sei(); den sonra bende avr kullanıyorum ama karşılaşmadım daha önce böyle bi sorunla..
kesme ayarlarını gecikme sonuda da yapmayı denedim öncesinde de.sei(); den sonrada denedim.sanırım osilator kurulumu veya uyanma durumu ile ilgili bir sorunvar ama hala çözebilmiş değilim.
çözüm bulamadıysanız bunun için bir değişken kullanın kesmeye geldiğinde bu değişkenin değeri "0" sa bunun ilk kesme olduğunu bilsin normal yapması gereken işlemleri yapmasın değişken değerini "1" yapsın sonraki kesmelerde bu değer "1" ise diğer işlemleri yapsın.
DS18B20 yi ilk okuduğunuzda da 85 derece veriyor aynı şekilde çözüm buldum
aşagıdaki kod attiny2313 de sorunsuz çalışıyor atmega8'in registerları biraz farklı ama benzer
#include <avr/io.h> /* avr için İ/O kütüphanesi*/
#include <util/delay.h> /* gecikme kütüphanesi */
#include <avr/interrupt.h>
ISR(INT0_vect) //int0 harici kesme
{
PORTB|= _BV(0); //1 yap
}
void mcu_init(void){
/* giriş ve çıkış ayarları*/
PORTB =0x00; /*portd içeriğini sıfırla*/
DDRB =0xff; /*portd içeriği */
//DDRD =0x72; //portd içeriği
DDRD = 0b01110010;
//DDRD |= (1 << PD4); // port out
PORTD =0x00; /*portd içeriğini sıfırla*/
}
/* Ana program burdan başlıyor*/
int main(void){
mcu_init(); /* islemciyi hazirla */
PCMSK |= (1<<PIND2) ;
//MCUCR = (1<<ISC01) | (1<<ISC00); //kesme kenarı seçimi yükselen kenar-bırakınca
MCUCR = (0<<ISC01) | (0<<ISC00); //kesme kenarı seçimi düşen kenar-basınca
GIMSK |= (1<<INT0); //int0 aktif et
sei();
while(1){ /* program sonsuz döngüde */
PORTD|= _BV(6); /*portd.0 +5V yapıldı*/
_delay_ms(500); /*0.5 sn gecikme yapıldı*/
_delay_ms(500); /*0.5 sn gecikme yapıldı*/
PORTD&= ~_BV(6); /* portd.0 0V yapıldı*/
_delay_ms(500); /*0.5 sn gecikme yapıldı*/
_delay_ms(500); /*0.5 sn gecikme yapıldı*/
}
}
ayrıca bu kodu atmega8 için isisde denedim çalışıyor ama devrede henüz deneyemedim
#include<avr\io.h>
#include<avr\interrupt.h>
ISR(INT1_vect) //int1 harici kesme
{
PORTC|= _BV(5);
}
ISR(INT0_vect) //int0 harici kesme
{
PORTC&= ~_BV(5);
}
int main(void)
{
DDRC = 0xff; // PortB çıkış
PORTC = 0x00; // portu temizle
DDRD = 0x00; // port D giriş
PORTD = 0x00; // portu temizle
GICR = (1<<INT0)|(1<<INT1); //int0 ve int1 kesmesi aktif
MCUCR = (1<<ISC00)|(1<<ISC01)|(1<<ISC10)|(1<<ISC11); // int 0ve 1 yukselen kenar
sei(); // enable interrupts
for (;;) {
PORTC|= _BV(4);
} // loop forever
}
evet sorunu buldum buradan paylaşayım dedim.saçma ve tuhaf gelecek ama int0 veya int1 den hangisi en üste yazarsanız ilk çalışma anında bu kesme kendiliğinden aktif oluyor.eğer bu 2 kesmeden sadece birini kullanıyorsanız da o kesme kendiliğinden aktif oluyor.
tuhaf ama gerçek.sizin verdiğiniz örnekte int0 ı üste yazarsanız ne dediğimi anlayacaksınız.