Forum: Mikrocontroller und Digitale Elektronik MSP430 LaunchPad Taster Interrupt


von Christian Q. (osx)


Lesenswert?

1
#include <msp430g2231.h> 
2
3
/* MSP430 PushButton that toggles LEDs On and Off                                       */
4
/*                                                                                      */
5
/* Description: PushButton in P1.3 through interrupt turns on and off the LED at P1.0   */
6
/* and P1.6.  By changing the P1.3 interrupt edge, the interrupt is called every time   */
7
/* the button is pushed and pulled; toggling the LED everytime.                         */
8
9
10
/* (#1 Pull Up)LaunchPad revisions 1.3 and 1.4 come with R34 populated. The 47-kO resistor is used as a pullup for the button S2. */
11
/* If the port P1.3 is driven to ground, as suggested to keep the power consumption down, the pullup resistor generates an additional current of approximately 77 µA. */
12
/* To reduce the power consumption, the port should stay in input mode or the resistor should be removed if button S2 is not used. The internal pullup of the MSP430G2xx can be used instead. */
13
 
14
#define LED1    BIT0
15
#define LED2    BIT6
16
#define BUTTON  BIT3
17
 
18
int main(void)
19
{
20
    WDTCTL = WDTPW + WDTHOLD;           /* Stop watchdog timer */
21
    P1DIR |= (LED1 + LED2);             /* Set LEDs to output direction */
22
                                        /* P1.3 must stay at input (this is the default) */
23
   
24
    P1OUT &= ~(LED1 + LED2);            /* turn LEDs off */
25
    P1IE |= BUTTON;                     /* P1.3 interrupt enabled */
26
    P1IFG &= ~BUTTON;                   /* P1.3 IFG cleared */
27
    /* P1REN |=  BUTTON;  (see #1) Enable the Pull Up? */
28
    __enable_interrupt();               /* enable all interrupts */
29
    
30
    while(1) {
31
      __delay_cycles(100000);
32
      P1OUT ^= LED1 ;
33
    }
34
    /* endless loop */ 
35
}
36
 
37
// Port 1 interrupt service routine
38
#pragma vector=PORT1_VECTOR
39
__interrupt void Port_1(void)
40
{
41
    P1OUT ^= (LED1 + LED2);              /* LED toggle */
42
    P1IFG &= ~BUTTON;                   /* P1.3 IFG cleared */
43
}

Hallo, ich habe das Problem, dass ich auf meinem LaunchPad nicht auf 
Durck des Tasters reagieren kann.
Das Programm lässt die rote LED toggeln. Wenn der Interrupt auslöst 
werden zudem die rote und die grüne LED getoggelt.
Am Ende der ISR hab ich außerdem einen Breakpoint gesetzt.

Komisches verhalten: Wenn ich die aus dem uC Pin ausgeführte 
Steckerleiste P1.3 anpacke funktioniert es so wie gedacht. Wenn ich den 
Taster drücke passiert nichts.

Ich besitze die Rev.1.5. In dieser Version wurde der externe Pull-Up 
Widerstand vom Board entfernt. Deswegen habe ich den internen durch die 
Zeile
1
P1REN |=  BUTTON;
aktiviert. Jedoch wirkt sich das noch negativer aus. Sodass die Sache 
mit der Steckerleiste nicht einmal mehr funktioniert.

Hat jemand eine Idee?

von Vn N. (wefwef_s)


Lesenswert?


von Christian Q. (osx)


Lesenswert?

Spielt doch keine Rolle, ich habe nicht den Effekt des Prellens (Mehrere 
Signale hintereinander die die ISR auslösen würden) sondern empfange gar 
kein Signal.

von Martin (Gast)


Lesenswert?

P1OUT |= BUTTON;
P1DIR &= ~BUTTON;

von Christian Q. (osx)


Lesenswert?

Martin schrieb:
> P1OUT |= BUTTON;
> P1DIR &= ~BUTTON;


P1OUT |= BUTTON;
Damit gebe ich aber doch Saft auf den Button. Nicht das was ich möchte.

P1DIR &= ~BUTTON;
P1.3 must stay as input (this is the default)! - Also es ist von anfang 
an ein Eingang. P1DIR sieht zu Laufzeit so aus:
P0       P7
 100000010
Scheint mir korrekt.

Okay, mit Martins Änderung sieht mein Programm so aus:
1
#include <msp430g2231.h> 
2
3
/* MSP430 PushButton that toggles LEDs On and Off                                       */
4
/*                                                                                      */
5
/* Description: PushButton in P1.3 through interrupt turns on and off the LED at P1.0   */
6
/* and P1.6.  By changing the P1.3 interrupt edge, the interrupt is called every time   */
7
/* the button is pushed and pulled; toggling the LED everytime.                         */
8
9
10
/* (#1 Pull Up)LaunchPad revisions 1.3 and 1.4 come with R34 populated. The 47-kO resistor is used as a pullup for the button S2. */
11
/* If the port P1.3 is driven to ground, as suggested to keep the power consumption down, the pullup resistor generates an additional current of approximately 77 µA. */
12
/* To reduce the power consumption, the port should stay in input mode or the resistor should be removed if button S2 is not used. The internal pullup of the MSP430G2xx can be used instead. */
13
 
14
#define LED1    BIT0
15
#define LED2    BIT6
16
#define BUTTON  BIT3
17
 
18
int main(void)
19
{
20
    WDTCTL = WDTPW + WDTHOLD;           /* Stop watchdog timer */
21
    P1DIR |= (LED1 + LED2);             /* Set LEDs to output direction */
22
                                        /* P1.3 must stay at input (this is the default) */
23
   
24
    P1OUT &= ~(LED1 + LED2);            /* turn LEDs off */
25
    P1OUT |= BUTTON;
26
    P1DIR &= ~BUTTON;
27
    P1IE |= BUTTON;                     /* P1.3 interrupt enabled */
28
    P1IFG &= ~BUTTON;                   /* P1.3 IFG cleared */
29
     P1REN |=  BUTTON;  /*(see #1) Enable the Pull Up? */
30
    __enable_interrupt();               /* enable all interrupts */
31
    
32
    while(1) {
33
      __delay_cycles(100000);
34
      P1OUT ^= LED1 ;
35
    }
36
    /* endless loop */ 
37
}
38
 
39
40
// Port 1 interrupt service routine
41
#pragma vector=PORT1_VECTOR
42
__interrupt void Port_1(void)
43
{
44
    P1OUT ^= (LED1 + LED2);              /* LED toggle */
45
    P1IFG &= ~BUTTON;                   /* P1.3 IFG cleared */
46
}
Und es läuft. Wenn ich Einen Pin als Eingang setze und dann aber Saft 
draufgebe. Was tut dies dann? - Scheinbar aktiviere ich damit den 
internen Pull-Up. Aber was für einen Sinn hat dann P1REN? Wähle ich 
damit ob ich Pull-Up oder Pull-Down möchte?

//edit: Hab die Erklärung gefunden
PxREN
The resistor enable register is a very useful feature for the ports. 
Sometimes it is helpful to pull the voltage up to Vcc or down to Vss, 
such as when you attach a push button to a pin.  The resistor enable 
register lets you turn on that ability.  When a PxREN bit is enabled, 
you can select it as a pull-up or pull-down resistor by setting the 
corresponding bit in PxOUT, 1 for up, 0 for down.

von Martin (Gast)


Lesenswert?

Im User Guide für die MSP430F5xx sind die Port-Funktionen besser 
erklärt.
PxOUT, PxDIR und PxREN beeinflussen sich gegenseitig

PxDIR PxREN PxOUT    I/O Configuration
 0      0     x       Input
 0      1     0       Input with pulldown resistor
 0      1     1       Input with pullup resistor
 1      x     x       Output

von Christian Q. (osx)


Lesenswert?

Danke! Werd ich mir sofort suchen.
Aber warum kann man nicht auch AVR-like die Register manipulieren? ala
P1DIR  |= (1 << LED1) | (1 << LED2);
Ich fand das zu meinen atmega-Zeiten ganz übersichtlich.

von Vn N. (wefwef_s)


Lesenswert?

Christian Q. schrieb:
> Aber warum kann man nicht auch AVR-like die Register manipulieren? ala
> P1DIR  |= (1 << LED1) | (1 << LED2);
> Ich fand das zu meinen atmega-Zeiten ganz übersichtlich.

Reine Frage der C-Library. Aber welchen großen Vorteil nun
1
P1DIR  |= (1 << LED1) | (1 << LED2);
gegenüber
1
P1DIR |= LED1 | LED2;
hat, ist mir auch nicht ganz  klar.

von Christian Q. (osx)


Lesenswert?

Da konnte man schön die Datenrichtung eines Port definieren. Ob Eingang 
oder Ausgang.
Wie sage ich in dieser Schreibweise, dass es ein Eingang ist?
Würd das so machen:
1
P1DIR |= LED1 | LED2;
2
P1DIR &= ~BUTTON;
wäre bei der AVR lib schön:
1
P1DIR  |= (1 << LED1) | (1 << LED2) | (0 << BUTTON);

von Stefan (Gast)


Lesenswert?

Christian Q. schrieb:
> Wie sage ich in dieser Schreibweise, dass es ein Eingang ist?
> Würd das so machen:
1
P1DIR |= LED1 | LED2;
2
> P1DIR &= ~BUTTON;

Meist besser einfach mit
1
P1DIR = LED1 | LED2;
Nur da wo ein Ausgang sein soll wird das Bit gesetzt, alles andere 
bleibt Eingang.
Nur wenn später im Programm ein Portpin von Ausgang zurück auf Eingang 
umgeschaltet werden soll ist etwas wie
1
P1DIR &= ~BUTTON;
sinnvoll.

von Lesbarer Code (Gast)


Lesenswert?

Christian Q. schrieb:
> wäre bei der AVR lib schön:P1DIR  |= (1 << LED1) | (1 << LED2) | (0 << BUTTON);

Das funktioniert bestimmt nicht. Eine '1' im P1DIR an Bitpos BUTTON kann 
man nicht per ODER löschen.

Diesen Shift-Sch... findet man nur beim AVR. Richtige Compiler-Libs 
erlauben vernünftiges Programmieren.

von Info (Gast)


Lesenswert?

Christian Q. schrieb:
> Ich besitze die Rev.1.5. In dieser Version wurde der externe Pull-Up
> Widerstand vom Board entfernt.

Na super. Der R34 ist im aktuellen Schaltplan für Rev.1.5 mit Wert
47k enthalten (slau318g ), aber tatsächlich nicht bestückt (Nähe Pin 1 
der Stiftleiste) . Danke, dass ich euren Fehler suchen durfte, TI.

http://www.ti.com/tool/msp-exp430g2

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
Noch kein Account? Hier anmelden.