Hallo, nach jahrelanger Erfahrung mit Atmels habe ich mich aus Stromspargründen an den MSP430 gewagt. Soweit läuft meine Anwendung, nur, wie kommt man durch ein externes Signal wieder vom LPM3- oder LPM4 - Mode wieder in den AM - Mode. Ich verwende den MSP430F1101A. Danke, Bernhard
Hi Das Signal, welches du überwachen willst, muss einen Interrupt auslösen. In der ISR weckst du dann den MSP430 mit dem ersten Befehl wieder auf. Sehr gut sind die Codebeispiele von TI, dort findest du zu allen Peripheriegeräten kleine Beispiele. Die in C sind hier: http://www-s.ti.com/sc/psheets/slac013d/slac013d.zip. Ich poste dir jetzt mal fet120_lpm3.c, ein Demo der Basic Clock, aus dieser Sammlung: //********************************************************************** ******** // MSP-FET430P120 Demo - Basic Clock, LPM3 Using WDT ISR, 32kHz ACLK // // Description: This program operates MSP430 normally in LPM3, pulsing P1.0 // at 4 second intervals. WDT ISR used to wake-up system. All I/O configured // as low outputs to eliminate floating inputs. Current consumption does // increase when LED is powered on P1.0. Demo for measuring LPM3 current. // ACLK = LFXT1/4 = 32768/4, MCLK = SMCLK = default DCO // //* External watch crystal on XIN XOUT is required for ACLK *// // // MSP430F123(2) // --------------- // /|\| XIN|- // | | | 32kHz // --|RST XOUT|- // | | // | P1.0|-->LED // // M. Buccini // Texas Instruments Inc. // Feb 2005 // Built with IAR Embedded Workbench Version: 3.21A //********************************************************************** ******** #include <msp430x12x2.h> void main(void) { BCSCTL1 |= DIVA_2; // ACLK/4 WDTCTL = WDT_ADLY_1000; // WDT 1s/4 interval timer IE1 |= WDTIE; // Enable WDT interrupt P1DIR = 0xFF; // All P1.x outputs P1OUT = 0; // All P1.x reset P2DIR = 0xFF; // All P2.x outputs P2OUT = 0; // All P2.x reset P3DIR = 0xFF; // All P3.x outputs P3OUT = 0; // All P3.x reset while(1) { int i; _BIS_SR(LPM3_bits + GIE); // Enter LPM3, enable interrupts P1OUT |= 0x01; // Set P1.0 LED on for (i = 5000; i>0; i--); // Delay P1OUT &= ~0x01; // Clear P1.0 LED off } } #pragma vector=WDT_VECTOR __interrupt void watchdog_timer (void) { _BIC_SR_IRQ(LPM3_bits); // Clear LPM3 bits from 0(SR) } Den Code nachzuvollziehen sollte wohl kein Problem mehr darstellen. Gruss & HTH Tom
Hi Tom, vielen Dank. Diese Beispiele hatte ich auch schon durchforstet aber nicht 'meine' Anwendung mit dem Port-Int. gefunden. Aber Mut durch Deine Antwort bekommen, habe ich es probiert und es klappt tatsächlich. Hatte mich nur gefragt, wie mit abgeschalteter CPU und irgendwelchen Clocks überhaupt was gehen kann. Allerdings aus dem LPM4 komme ich nicht mehr 'raus, obwohl doch gerade dies nur extern möglich sein müsste. Aber die Zeit wird auch noch Erfahrung bringen.... Gruß Bernhard
>Hatte mich nur gefragt, wie mit abgeschalteter CPU > und irgendwelchen Clocks überhaupt was gehen kann. Die Clocks der entsprechenden Funktionen müssen weiterhin aktiv bleiben, damit es funktioniert. Wenn du z.B. den Timer mit Quarz-Takt laufen lässt und den Quarz-Oszi abschaltetest bleibt auch der Timer stehen und produziert keinen IRQ mehr. z.T. wird das automatisch geregelt, dass die entsprechenden Clocks anbleiben. In machen Fällen musst du dich aber auch darum kümmern. Aus dem LPM4 kommt du IIRC nur mit einem externen Signal an einen P1 oder P2 pin, der für Interrupts konfiguriert ist. Da sind dann alle Clocks aus. Also läuft auch kein Timer, etc. weiter.
Bei den MSPs brauchst du immer zwei Dokus: Das Datenblatt, wo die elektrische Charakteristik und typenspezifische Informationen enthalten sind und den User's Guide, ein gut 1000 Seiten starkes Dokument, welches ein wenig abstrakter abgefasst ist und es für alle MSP430x1xx gleich ist. Dort sind die Low Power Modi genau beschrieben. Aber das weisst du ja warscheinlich schon. Was hast du denn vor mit dem kleinen Zwerg? Hab erst neulich entdeckt, dass es die Dinger auch in einem 4 x 4 mm-Gehäuse gibt! Kleiner geht's wohl nicht mehr.
Guten Morgen ! Ja, zwischen diesen beiden Dokus schalte ich schon dauernd hin und her, habe aber den Eindruck, dass einiges, zumindest für mich, nicht genau genug beschrieben ist. Übrigens scheint das Aufwecken vom LPM4 zu funktionieren. Klar, mit einem Portinterrupt, weil ja sonst nichts läuft, das wars was ich suchte ! War mir nur nicht sicher, ob die Portperipherie zur Datenübernahme bzw. IRQ-Erzeugung nicht einen Takt braucht. Irgendwo steht sinngemäss: '... das Signal muss min. 1,5 Taktzyklen anstehen, um sicher erkannt zu werden...'. Wie geht das also, wenn nichts taktet ...? Die Anwendung ist für meine ruderbegeisterten Kids: Einen (billigen) Fahrradtacho als Schlagzahluhr zu verwenden. Kurz: Rollsitzkontaktgaben durch 2 teilen, Zeit zwischen Kontaktgaben messen, daraus eine brauchbare Zeit für die Radumdrehungen berechnen um dann 'Schläge pro Minute' in 'km/h' anzuzeigen. Wird nicht gerudert, soll das Ding schlafen, damit die Batterie 100 Jahre hält. Gruß Bernhard
Hi Das Signal muss warscheinlich so lange anliegen, damit eine Kapazität gefüllt werden kann. Sehr kurze Störimpulse werden so rausgefiltert (Mutmassung). Cool, ich hab früher auch gerudert! Wie rechnest du aber die Schläge in die Geschwindigkeit um? Das ist ja je nach Grösse und Kraft des Ruderers unterschiedlich. Bei uns hatte mal jemand so ein Teil, welches mit einem Sensor im Wasser die Geschwindigkeit gemessen hat. Vielleicht könnte man aber auch die Bewegung der Dole (Das Teil am Ausleger, wo das Ruder reinkommt. Keine Ahnung wie ihr das nennt) messen und so relativ genau auf den zurückgelegten Weg schliessen. Okay, du brächtest dazu sicher den Slope-ADC, also den Vergleicher. Ob sich der Aufwand lohnt mag ich jedoch bezweifeln... FG Tom
Hi Tom, nein, Missverständnis, viel einfacher: Angezeigt werden sollen lediglich die Ruder-Schläge pro Minute. Weil der Fahrradtacho halt nur km/h als Einheit anzeigt muss der User dies ignorieren bzw. in Gedanken mit Schl./min ersetzen. Es müssen also nur die Rollsitzkontaktgaben je Zeiteinheit in Werte entsprechend sinnvollen Raddurchmesser umgerechnet und ausgegeben werden. Falls Du eine Idee hast OHNE Flügelrad o.ä. tatsächlich die Bootsgeschwindigkeit relativ zum Wasser zu messen, wäre dies genial. Hatte schon an eine optische Maus gedacht, wie auch immer die funktioniert. Man kann auch ganz unspektakulär einen GPS-Empfänger nehmen.... Gruß Bernhard
Hello All; I am looking for some good material to learn msp430-gcc I tried to run some files on this environment , but it doesnot work I would be very grateful for any piece of advice. thnaks in advance
Hi Bernhard Eine normale Maus könnte vielleicht eine Möglichkeit bieten: Da ist doch normalerweise ein 'Zahnrad' drin, welches eine Lichtschranke durchbricht. Wenn man so ein Rad an der Dole anbringen könnte und die Lichtschranke am Ausleger, dann müsste sich doch der Bewegungswinkel des Ruders messen lassen. Über die Länge des Ruders kommst du in etwa auf die Strecke, die pro Schlag zurückgelegt wird. Natürlich musst du das verdrengte Wasser davon abziehen. Mit ein bisschen Kopfarbeit und Mathe kommst du warscheinlich schon auf einen guten Wert.
Hi Tom, ..und das verdrängte Wasser hängt wieder von der Kraft, der Form und Größe der Blätter, dem eingestellten Hebel,...u.s.w. ab. Nicht einfach alles zu brücksichtigen. Aber nochmal zu meinem Hauptproblem: Ich schicke den MSP430 in dem LPM4 Mode, wenn eine gewisse Zeit nichts mehr passiert - das funktioniert. Am Oszilloskop kann man sehen, wie der Quarzoszillator abgeschaltet wird und das Ganze nur noch nA's an Strom verbraucht. Duch einen ext. Interrupt schaltet er auch wieder ein. Aber das wars. Das Prog. macht nur gelegentlich richtig an der erwarteten Stelle (in der Portinterrupt- Routine) weiter, meistens hängt es sich irgendwo auf. Der Quarz schwingt auch sehr langsam wieder an, könnte dies das Problem sein ? Es gibt doch ein Oszillator-Fail Bit, was man abfragen soll, wenn auf den LowFrequency Takt umgeschaltet wird. Muss man vor dem Schlafenschicken evtl. wieder auf einen schnellen Takt (den internen) umschalten ? Bernhard
Es schadet in keinen Fall, wenn du mit dem DCO startest, weil dann der Quarz genug Zeit hat ums sich zu stabilisieren. Bei den Aufwachzeiten im DB is ja explizit angegeben, dass die nur gelten wenn der DCO benutzt wird. Evtl. ist es ja auch ne Option den Quarz anzulassen und nur LPM3 zu benutzen. Da braucht er ja auch max. 1.9µA bei 25°C und 3V. Ich hab z.B. ne Uhr mit dem MSP realisiert, da muss der 32Khz-Quarz natürlich aktiv bleiben und die gesamte Schaltung verbraucht ca. 4µA im LPM3, wobei die Leckströme der Dioden schon einiges ausmachen. Wenn du noch ein bisschen mehr Strom sparen möchtest wärs vielleicht auch möglich den Quarz nur ganz selten zu benutzen um den DCO damit zu kalibrieren. Eine ensprechende Appnote gibts von TI.
Hello All; I have tried to run some source code for msp430f1611 om msp-gcc compiler with the following command on the command prompt c:\mspgcc>msp430-gcc -0s -mmcu=msp430f1611 -o sourcefile.elf sourcefile.c I got the following message (null):0: confused by earlier errors, bailing out the second question : how to generate the file with extension .elf I would be very grateful for anz piece of advice. thank you in advance.
AHRSCHEINLICH LIGT DAS AN DEINEM pOGRAMM . Solche Bilderscheinung wie du beschreibst . NormalBetrieb-> LPM4-> sleep...-> Interrupt -> kurz aufwachen und einschlafen von ohne In Hauptprogramm zu gehen kann auch aufchengen sein hatte ich auch . 1.schreib das Aufwecken(LPM3_EXIT;) nie in eine Routine die in Interrupt aufgerufen wird . sonst wacht er nur für ausführung des Iterruptroutine auf . 2. Sehr ernst fürLPM4. Du benutzt Portinterrupts auf Jedem Fahl ENPRELLUNG !!!!!!!! per SW stueuern , sonst kans du Mehrfaches Interrupt aufruf haben und als Folge Stecküberlauf. Anderes um Auch wichtig Interrupt Flags von >PORT Pin !!!! in Interruptroutine LÖSCHEN . auch auf HW muss man aufpassen. Keine in Lüft hängende Eingenge von Port der Interrupt gibt. usw... vielspass
Danke für die Tipps, den LPM4 muss ich nehmen, da eine Lithiumzelle einige Jahre halten soll. Habe nun auf den Xtal verzichtet und benutze nur den DC0, da die Anwendung nicht zeitkritisch ist, damit geht zwar alles so wie gewollt, aber etwas unbefriedigend ist es schon... Habe auch versucht vor LPM4 von Xtal auf DC0 zu schalten und nach dem Aufwecken wieder zurück, mit Wartezeit, da der Quarz ja langsam wieder anschwingt. Aber leider 'no go'. Werde das Prog. nochmal nach Sergey's Tipps durchsehen... R2D2 welche Anzeige hast Du für Deine Uhr genommen ? Gruß Bernhard
hello Dary ! start a new tread in english. a mixture of german and english and two different matters (here we are talking about the WDT) produces only garbage. michael
meine frage zum watchdog timer beim MSP: meiner läuft mit ACLK=32 KHz. bräuchte einen reset nach frühestens 2 sekunden, wenn der prozessor hängenbleiben sollte (leere batterie oder andere gründe). jede sekunde könnte ich den wdt zurücksetzen, da ein interrupt mit 1 sek intervall läuft und ich darin den wdt rücksetzen kann. meine frage: im datenblatt steht dass der wdt ein 16 bit zähler ist, also von 0 bis FFFF (65535) läuft. die WDTISx bits bestimmen bei 32 KHz das "timer interval", bzw die clock source vorteilung. bei /32768 hiesse das: der zähler zählt mit 1 hz und nach 65535 sekunden (=18 stunden) wird ein reset ausgelöst. ist das richtig ? oder wird der reset nach 1 sekunde ausgelöst ? d.h. meine frage läuft darauf hinaus ob mit 32 KHz überhaupt > als eine sekunde wartezeit möglich sind. michael
bernhard: ist eine led uhr, die mit trafo läuft aber über nacht wird der strom abgeschalten, also muss in der zeit ne batterie die versorgung übernehmen. michael: wenn du dir das blockdiagramm des watchdogs anschaust siehst du das er keinen eigenen prescaler hat. also is das max. intervall bei 32khz 1sek beträgt. du kannst aber einen vorteiler für aclk benutzen wenn du da nicht die vollen 32khz brauchst.
hallo hermann ! doch er hat einen (mein F135 zumindest). teilerfaktor wird in WDTCTL in den bits WDTISx eingestellt und kann zwischen /64 und /32768 in 4 stufen eingestellt werden. das problem ist dass ich den ACLK unbedingt auf 32 khz laufen lassen muss, da ich den takt auch rausführe und dort eine andere hardware noch dranhängt und die will genau 32 KHz. ich verstehe noch nicht ganz wie die und du auf eine sekunde kommen. bei /32768 gelangt ja ein impuls ACLK pro sekunde an den WDT. aber es soll ja ein 16 bit timer sein. ich kann es nur so verstehen dass im WDT-betrieb der übergang 0>1 einen power-on-reset auslöst, also die übrigen 15 bits wurscht sind. und dass nur im timer-betrieb die 16 bits eine rolle spielen. schade. ich habe nämlich das unangenehme problem dass bei 2 anwendungen von bis jetzt 50, nach einer weile ein hängenbleiben auftrat. ursache unbekannt. offenbar ganz kurze unterbrechnung an der 3 V batterieklemme. da die dinger in schweden und österreich usw laufen ist das in beiden fällen ein drama gewesen. 1000 mal nix passiert, und dann hats zummm gemacht. monatelange tests bestanden und nun sowas. ein wdt könnte wenigstens die dinger wieder anschmeissen. michael (2)
> doch er hat einen (mein F135 zumindest). Sonderanfertigung? > teilerfaktor wird in WDTCTL in den bits WDTISx >eingestellt und kann zwischen /64 und/32768 in >4 stufen eingestellt werden. Damit stellts du ein, welche Teilerstufe dieses 16Bit-Counters du verwenden willst. Der Counter wird immer mit vollem ACLK betrieben. Du kannst nur auswählen, welchen Abgriff du benutzt. Schau dir mal das Block-Diagramm an, dann wird dir einiges klar.
Hello all; I have to program a small project and i have to deal with flash memeory (msp430f1611). I would be very grateful if you could tell how to program the flash memeory to read from and to write it using (IAR compiler). thanks
Hallo, ich habe am msp430 eine Temperatur-Sensor für den I2c-bus laufen, und will über eine Timersignal eine optimal Abfragezeit einstellen. Der Temperatur-Sensor braucht für die Bearbeitung des Ergebnises 750ms. Was mir noch nicht so klar ist, wie der Basic-Clock-System (in dem Fall SMCLK) den Timer speist und die richtige zeit generieren... Gruss Andre
> Was mir noch nicht so klar ist, wie der Basic-Clock-System (in dem Fall > SMCLK) den Timer speist und die richtige zeit generieren... Auf jeden Fall vorher aufwecken. Hrhrhrhr
>Was mir noch nicht so klar ist, wie der Basic-Clock-System (in dem Fall >SMCLK) den Timer speist und die richtige zeit generieren... Wann der Timer den Interrupt generiert musst du selber einstellen. Und welcher Clock den Timer speist bleibt dir auch überlassen. Es muss halt einer sein der bei deinem gewählten Low Power Modus noch aktiv ist.
Ok, ich denke ich hab die Lsg, war wieder zu kompliziert gedacht. Der Timer wird durch die SMCLK gespeisst welcher mit800kHz läuft. Der Temp.-Sensor nötigt 750ms für die Umwandlung und sagen wir mal noch mal ca. 50ms bis der Wert zu Verfügung steht. D.h. 800ms / 800kHZ -> 800ms/0.00125ms = 640000 --> 0x9C400. Da der Timerzähler aber nur bis 0xFFFF geht, wird diser 9 mal durchlaufen bis der nächste Wert angefordert wird. Gruss Andre
Du kannst den Timer CLK auch noch mal teilen, der muss nicht mit der vollen Taktgeschwindigkeit laufen. Ebenso könntest du auch das CCR0 Register benutzen, wenn du absolut exakte Zeiten willst.
Erstmal sorry, dass ich diesen Thread nach so langer Zeit wieder aufwecke...aber wollte das Zitat nicht in nen neuen Thread mitnehmen: Sergey Ionov schrieb: > 1.schreib das Aufwecken(LPM3_EXIT;) nie in eine Routine die in > Interrupt aufgerufen wird . sonst wacht er nur für ausführung des > Iterruptroutine auf . Warum soll denn das Aufwachen nur für die ISR-Ausführung gelten, wenn ich die entsprechenden SR-Bits rücksetze? Ich meine, das ist doch gerade der Sinn von LPMx_EXIT...? Sobald ein Interrupt auftritt, befinde ich mich für die Zeit der ISR im Acitve mode und kehre mit Verlassen der ISR in den LPMx zurück, oder nicht? Will ich aber auch nach der ISR wieder im Active mode sein, dann muss ich doch LPMx_EXIT ausführen. Aber warum soll ich das nicht in der ISR tun bzw. wo kann ich es sonst tun? Oder ist einfach gemeint, dass ich ne extra Funktion z.B.
1 | void wakeup(){ LPMx_EXIT; } |
schreib und die in der ISR aufrufe?
>Sobald ein Interrupt auftritt, befinde ich mich für die Zeit der ISR im >Acitve mode und kehre mit Verlassen der ISR in den LPMx zurück, Richtig >Will ich aber auch nach der ISR wieder im Active mode sein, dann >muss ich doch LPMx_EXIT ausführen. Richtig >Aber warum soll ich das nicht in der ISR tun bzw. wo kann ich es sonst >tun? ISR ist schon richtig.
Jörg S. schrieb: >>Aber warum soll ich das nicht in der ISR tun bzw. wo kann ich es sonst >>tun? > ISR ist schon richtig. Das heißt, Sergey schreibt Schrott? :)
Ob es Probleme gibt wenn das Exit in einer Funktion aufgerufen wird weiss ich nicht. Wenn es direkt in der ISR steht geht es auf alle Fälle.
Eben, aber er hat ja geschrieben, dass gerade der Aufruf in der ISR Probleme geben könnte.
Mark M. schrieb: > Eben, aber er hat ja geschrieben, dass gerade der Aufruf in der ISR > Probleme geben könnte. Das ist ja eben für genau diesen Zweck da. Das Makro modifiziert das Statuswort der CPU auf dem Stack so, dass nach dem RETI die CPU aktiv bleibt und alle Stromspar-Modi aus sind. Das gibt eher Probleme außerhalb einer ISR, weil dann ja irgendwas auf dem Stack manipuliert wird. Innerhalb der ISR ist ja bekannt, an welcher Stack-Position das Wort steht.
Christian R. schrieb: > Das ist ja eben für genau diesen Zweck da. Das Makro modifiziert das > Statuswort der CPU auf dem Stack so, dass nach dem RETI die CPU aktiv > bleibt und alle Stromspar-Modi aus sind. Das gibt eher Probleme > außerhalb einer ISR, weil dann ja irgendwas auf dem Stack manipuliert > wird. Innerhalb der ISR ist ja bekannt, an welcher Stack-Position das > Wort steht. Und genau deswegen frage ich mich, warum Sergey meint, dass man LPMx_EXIT nie innerhalb einer ISR auufrufen sollte!?? Ich glaub, ihr habt meine Frage nicht verstanden.
Richtig lesen! Sergey schrieb, man darf das Exit nicht in eine Routine schreiben, die in einer ISR aufgerufen wurde. Das ist auch richtig, denn dann wurde ja zwischendurch wieder was auf den Stack gepusht. Das Exit muss immer direkt in die ISR, niemals woanders hin.
Ah ok, hab die ganze Zeit gedacht, die "Routine" wäre die ISR. Jetzt ist's klar ;)
Jetzt hab ich noch ne Frage. Angenommen, ich befinde mich in LPM3. Dann kommt ein Interrupt, sodass ich mich kurz im Active Mode befinde. Wenn ich nun nach der ISR in LPM2 wechseln möchte, muss ich dann zuerst LPM3_EXIT und anschließend LPM2 ausführen? In der App-Note 430-02 steht nämlich, dass es in C garnicht so einfach sei, nach der ISR in einen anderen Operating Mode zu wechseln, weil man nicht auf den Stack zugreifen kann. Aber mit diesen Makros ist es doch eigentlich recht einfach? Klar, hinter denen steckt ja dann auch Assemblercode, mit dem es laut App-Note geht. Genau genommen ist es aber ja schon ein anderer Operating Mode, wenn man zuerst in LPM3 ist, und in der ISR LPM3_EXIT ausführt, sodass man hinterher Active Mode hat. Da meint der Verfasser der App-Note wohl eher, dass es mit reinem C, ohne Makros, schwierig sei, oder?
Da müsstest du dir wohl selbst ein Makro schreiben, was das CPU Wort auf dem Stack so verändert, dass nach dem RETI der LPM2 aktiv ist. Sollte theoretisch gehen, ist ja eigentlich auch nix anderes als in den Active Mode wechseln.
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.