servus, hab da ein problem mit interrupts der msp430 soll auf einen bewegungssensor reagieren der sehr empfindlich ist. dieser toggelt dann eine led in der ISR hab bei der ISR ein DELAY eingefügt damit der sensor ausschwingen kann und den PORT interrupt ausgescahltet stoß ich jetzt meinen sensot ein wenig an, dann schaltet sich die led ein, aber nachdem der timer abgelaufen ist wieder aus! es soll aber so sein, dass beim nächsten stoß sich erst die led abschaltet. bitte um hilfe was mach ich da falsch?!? danke und allen einen guten rutsch ins neue jahr!!!!!
Hallo, So habe ich das verstanden: Sensor anstoßen LED ein Sensor anstoßen LED aus Du brauchst in diesem Fall nur ein Flag zu setzen und diese abfragen. Sensor anstoßen() { if flag then { LED=1; flag=0; } else { LED=0; flag=1; } } Müsste so passen. Wenn nicht, das Prinzip sollte klar sein.
Nochwas:
for(;;){
WDTCTL = WDTPW + WDTHOLD; // Stop WDT
P2IE |= 0x08; // P2.3 int enabled
P2IES |= 0x00; // P2.3 low/high edge
P2IFG &= ~0x08; // P2.3 IFG clear
_EINT(); //General Interrupt Enable
_BIS_SR(LPM3_bits); //Enter LPM3
}
Das solltest du nicht machen. Das ist die Initialisierung, die sollte
nur 1x aufgerufen werden. Du hast sie in die Endlosschleife gesetzt und
rufst sie immer wieder auf.
Bei deinem Beispiel wäre die Endlosschleife leer, da eh alles
interrupgesteuert ist.
Mal abgesehen davon, dass die Struktur Deines Programms ein bissl von
hinten durchs Knie ist, liegt das Grundübel wohl in Deiner
Interrupt-Routine:
pragma vector=PORT2_VECTOR
__interrupt void Port_2(void)
{
_BIS_SR(LPM3_EXIT);
P4DIR |= 0x01; //Set P4.0 to Out
P4OUT ^= 0x01; //Toggle P4.0 => RED_LED
P2IFG &= ~0x08; // P2.3 IFG clear
_DINT();
P2IE &= ~0x08;
c delay_10us(7000);
P2IE |= 0x08;
}
Du loescht vor dem Delay das Interruptflag (noch dazu gleich zweimal).
Somit bist Du unmittelbar vor dem Delay wieder "aufnahmefähig" für das
nächste Setzen des Interrupt-Request-Flag P2IFG durch Deinen Sensor. Mit
dem Delay verzögerst Du nur die Ausführung der ISR(mal abgesehen davon,
dass der MSP ohne Tricks keine nested interrupts unterstützt). Du
unterdrückst nicht, wie Du das denke ich willst, das Setzen des
Interrupt-Request-Flags für die 70ms. Wenn Du die Struktur so lassen
willst, musst Du die Zeile
P2IFG &= ~0x08;
nach dem Delay einfügen. Dann sollte zumindest die Funktion erfüllt
sein.
erst mal danke für die hilfe!!! das problem ist, dass der sensor sehr lange nachschwingt! wie kann man das den msp430 sagen, dass er nach dem interrupt warten soll, also das port sperren, damit kein weiterer interrupt ausgelöst wird??? ich weiß, dass mein code ein wenig dureinander ist da ich viel herumprobiert hab, ohne nachzudenken was ich da mache. hätte auch eine generelle frage, da ich noch mich noch nicht so gut damit auskenne. was passiert genau wenn ein interrupt ausgelöst wird? was macht das IFG dabei?? danke!!
Hiho,
also, man muss zwei Dinge unterscheiden, das Interrupt-Request-Flag (in
PxIFG) und das Interrupt-Enable-Flag (in PxIE).
PxIFG wird gesetzt, wenn eine Flanke am Pin erkannt wird (Art der Flanke
wird in PxIES einegstellt). Das Rücksetzen muss über die SW vorgenommen
werden. Falls keine Interrupts (ISR) verwendet werden sollen, kannst Du
PxIFG pollen. Das Flag wird unabhängig von der Interrupt-Freigabe (PxIE
bzw. GIE) gesetzt.
Über das Interrupt-Enable-Flag (PxIE) kannst Du steuern, ob bei
Auftreten einer Flanke am Eingang die Interrupt-Service-Routine
angesprungen wird.
Kurz zusammengefasst (Beipiel P2.0):
Fall 1: P2IE = 0x00 oder GIE = 0:
1. Flanke
2. P2IFG = 0x01 (durch HW)
3. Pollen (z.B.in main)
4. Reaktion (z.B. toggeln LED)
5. P2IFG = 0x00 (durch SW)
Fall 2: P2IE = 0x01 und GIE = 1:
1. Flanke
2. P2IFG = 0x01 (durch HW)
3. Anspringen ISR (in ISR z.B. toggeln LED)
4. P2IFG = 0x00 (durch SW in ISR)
Ich persönlich verwende, falls möglich, die Polling-Methode, falls es
nicht auf Stromverbrauch und zeitkritische Anwendung ankommt. Aber das
ist natuerlich jedem selbst ueberlassen.
So, ich hoffe, ich habe prinzipiell nix vergessen und es ist halbwegs
verständlich. In den User Manuals (z.B. slau049d.pdf)ist das Ganze auch
ganz gut beschrieben.
DANKE für die hilfe!!! ja, ist stromkritisch, also LPM3 ist nötig! werd morgen, des gleich ausprobieren!! wenn ich dann noch ein problem hab, werd ich mich wieder melden! mfg
sodala, es ist soweit
das nächste problem steht an!
der IAR sagt beim debuggen, dass der STACK voll ist
in der zeile
while(time_us != irq_count); // Fertig?
bleibt das prog stecken.
ir_qcount ist dann 32941
und flag ist 244
irgendwo ist da ein überlauf, oder??
Hiho, ich denke mal, da laufen mehrere Port2 Interrupts verschachtelt, sodass der Stack überläuft. Ich habe Dein Programm mal etwas ueberarbeitet (habe leider gerade keinen Compiler dabei, sind also sicherlich noch Fehler drin). Aber prinzipiell sollte es gehen. Probiere es mal aus. Gruss Steffen
servus danke, hab deine version getestet, bleibt aber in der ISR des ports stecken. hab selbst meine version umgeschrieben, und es funzt jetzt so, wie ich mir das vorgestellt habe. das problem war, wie du sagtest, das ein port interrupt durch das nachschwingen des sensors, in die routine des timers gefunkt hat, und deshalb denk ich mal hats net gefunzt. hab jetzt einfach das port interrupt in der ISR ausgeschaltet und erst nachdem die LED funktion abgearbeitet ist, wieder eingeschaltet, und jetzt gehts schaus dir an, vl findest noch ein paar verbesserungs vorschläge ;-) mfg
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.