-
Content Count
908 -
Joined
-
Last visited
-
Days Won
85
Reputation Activity
-
chicken got a reaction from LiviuM in Implementing a simple Menu
PS: If you want to get fancy/generic, you could implement the state/menu system with a structure. Something along these lines:
struct { int menu_id, // continuous but not functional, helps to keep track of the menu id's int next_menu, // entry when pressing next void (*action) (void), // action when pressing select const char* label // displayed text } menu_t; int current_menu = 0; void do_select0(void) { current_menu = 2; // set to sub menu } void do_ select1(void) { // do main action 1 } void do_subaction1(void) { // do sub action 1 } void do_subaction2(void) { // do sub action 2 } void do_gotop(void) { current_menu = 0; // set to top menu } menu_t menu[] = { // Top level { 0, 1,"Sub Menu", do_select0 }, { 1, 0, "Action", do_select1 }, // Sub menu { 2, 3, "Sub action 1", do_subaction1 }, { 3, 4, "Sub action 2", do_subaction2 }, { 4, 2, "Up", do_gotop } }; and in the main loop / event handler:
switch(event) { case next: current_menu = menu[current_menu].next_menu; write_text(menu[current_menu].label); break; case select: menu[current_menu].action(); write_text(menu[current_menu].label); break; default; // do nothing break; } event = none; // reset event variable -
chicken got a reaction from energia in Library DNP3 to MSP430
Definitely looks like a complex undertaking. But those are the best learning opportunities.
You will have to get an understanding about the overall architecture of OpenDNP. As @@Fmilburn suggested, contacting the owner or main contributors of the Github repository is probably your best bet when stuck on that topic. This includes getting their implementation to build. If the AVR implementation is working, there's a good chance that the FR6989 has sufficient resources.
The "embedded" link includes "adapter" sub-folders, which look like platform specific code for AtmelAVR and AtmelDue (probably referring to the boards, not the whole Arduino programming framework). I think the files in there are a good indication for what needs to be re-implemented for a new platform like MSP430. On a quick glance, the code doesn't look too extensive, which is encouraging.
Also check whether they make use of Atmel libraries in the code that's not platform specific.
-
chicken got a reaction from veryalive in Implementing a simple Menu
PS: If you want to get fancy/generic, you could implement the state/menu system with a structure. Something along these lines:
struct { int menu_id, // continuous but not functional, helps to keep track of the menu id's int next_menu, // entry when pressing next void (*action) (void), // action when pressing select const char* label // displayed text } menu_t; int current_menu = 0; void do_select0(void) { current_menu = 2; // set to sub menu } void do_ select1(void) { // do main action 1 } void do_subaction1(void) { // do sub action 1 } void do_subaction2(void) { // do sub action 2 } void do_gotop(void) { current_menu = 0; // set to top menu } menu_t menu[] = { // Top level { 0, 1,"Sub Menu", do_select0 }, { 1, 0, "Action", do_select1 }, // Sub menu { 2, 3, "Sub action 1", do_subaction1 }, { 3, 4, "Sub action 2", do_subaction2 }, { 4, 2, "Up", do_gotop } }; and in the main loop / event handler:
switch(event) { case next: current_menu = menu[current_menu].next_menu; write_text(menu[current_menu].label); break; case select: menu[current_menu].action(); write_text(menu[current_menu].label); break; default; // do nothing break; } event = none; // reset event variable -
chicken got a reaction from Fmilburn in Implementing a simple Menu
PS: If you want to get fancy/generic, you could implement the state/menu system with a structure. Something along these lines:
struct { int menu_id, // continuous but not functional, helps to keep track of the menu id's int next_menu, // entry when pressing next void (*action) (void), // action when pressing select const char* label // displayed text } menu_t; int current_menu = 0; void do_select0(void) { current_menu = 2; // set to sub menu } void do_ select1(void) { // do main action 1 } void do_subaction1(void) { // do sub action 1 } void do_subaction2(void) { // do sub action 2 } void do_gotop(void) { current_menu = 0; // set to top menu } menu_t menu[] = { // Top level { 0, 1,"Sub Menu", do_select0 }, { 1, 0, "Action", do_select1 }, // Sub menu { 2, 3, "Sub action 1", do_subaction1 }, { 3, 4, "Sub action 2", do_subaction2 }, { 4, 2, "Up", do_gotop } }; and in the main loop / event handler:
switch(event) { case next: current_menu = menu[current_menu].next_menu; write_text(menu[current_menu].label); break; case select: menu[current_menu].action(); write_text(menu[current_menu].label); break; default; // do nothing break; } event = none; // reset event variable -
chicken reacted to enl in Electronic Thermometer with analog meter
The board sockets on to the power header
The 5-pin with the cable going to the right is for a button and double pole, center off momentary switch for adjusting the scale in operation. The software does linear interpolation from 0 to 100 degrees F, and allows for key points every 10 degrees. The three yellow wires go to the remote sensor (DS18B20). The mounting is leftover oak from redoing a floor. Glued up, planed, bored for the meter and the electronics, and finished to hang on the wall. The circuit board is mounted by putting epoxy in the pocket and dropping it in.
Power board on. The tie point for the power line isn't on yet.
The face of the finished display:
The finish is shellac. I slopped on a heavy coat, light sanded, and then wiped another couple on. Then paste wax. Not perfect, but I banged it out quickly.
The meter:
Operating. The temp in my shop has climbed to 66F with a lot of help from the electric radiator.
-
chicken reacted to Fmilburn in MSP430 Wearable with Radio
I didn't get a whole lot done this past week on the project but Santa did bring me a decent mulitimeter to replace my old clunker.
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
Simply wire up J1 to the respective pins on the programmer. See the last column of table 6 in the MSPFET documentation.
http://www.ti.com/lit/ug/slau647f/slau647f.pdf
-
chicken got a reaction from Fmilburn in [POTM] dAISy - A Simple AIS Receiver
What an enjoyable Sunday afternoon.
Seriously, I love debugging!
-
chicken got a reaction from dubnet in [POTM] dAISy - A Simple AIS Receiver
What an enjoyable Sunday afternoon.
Seriously, I love debugging!
-
chicken got a reaction from spirilis in [POTM] dAISy - A Simple AIS Receiver
What an enjoyable Sunday afternoon.
Seriously, I love debugging!
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
The error is not related to the code that you posted.
Make sure to only include msp430.h.
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
You only need to clear P2IFG if you use interrupts triggered by voltage changes on a given pin. You are using a timer interrupt and wiggle the output "manually", which is unrelated.
I'm also getting confused on your requirements. If one 1PPS signal with a certain duty cycle (e.g. 250ms high, 750 ms high) is all you need, I would simply count to 1000 and then use that variable in the main loop.
i.e.
if (input pins indicate I should drive the clock signal ) { set pin as output if (timer_counter < 250) { set pin high } else { pin low } } else { set pin as input to not disturb other sources of the clock signal } I don't think this "remote programming" is very fruitful unless you actually do it on the real system and use an oscilloscope or logic analyzer to verify whether the system does what you expect.
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
Ooops, wrong thinking :-)
You want every 2 seconds. So it's
ISR { timerCount++; if(timerCount == 1000) { timerCount = 0; secondsCount++; // set your once a second flags } if(secondsCount == 2) { secondsCount = 0; // set your every 2 seconds flags } } -
chicken got a reaction from tripwire in How to prevent and detect stack overflow
Here's a great webinar on the topic of stack overflow from basics like stack sizing all the way to stack usage estimation and analysis, stack monitoring and stack overflow handling.
Recording:
Transcript: http://barrgroup.com/Embedded-Systems/How-To/Prevent-Detect-Stack-Overflow
Found via the Embedded Muse newsletter.
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
So, does it work wiggling P2.4?
You can read and react to inputs within the interrupt, so there's not an absolute need to communicate with the main thread. E.g, within the ISR:
if(++timerCount > 1000) { timerCount = 0; if(pin indicates mode 1) { do 1 } else if (pin indicates mode 2) { do 2 } } An alternative approach is to use the ISR just to keep track of time, and move everything else into the main loop. You may add another flag to indicate that a second passed. e.g. in the ISR:
if (++timerCount > 1000) { timerCount = 0; secondFlag = 1; } Then in the main loop:
forever { if(secondFlag == 1) { // wait for flag to be set secondFlag = 0; // do whatever you need to do once a second } } You could maintain other flags if you need to support more time periods. Make sure to use the volatile keyword when declaring variables that you want to pass between the ISR and main loop.
An even more refined program structure would set a mode variable depending on inputs, then have a switch statement covering the different modes.
forever { if(secondFlag == 1) { secondFlag = 0; mode = depending on input pins; switch(mode) { case 1: do what we need to do for mode 1; break; case 2: do what we need to do for mode 2; break; default: do nothing; } } } And just like that, you wrote your first state machine. You may move the secondFlag check into the case statements if the modes don't share the timing requirements.
PS: You clear the pin 2 interrupt flag (P2IFG) in your ISR. This register is not related to timer interrupts. So no need to clear it.
PS2: Busy-waiting in the main loop is not very efficient in regards to power consumption, but we will leave optimizing that to the very end when everything else works.
-
chicken got a reaction from dubnet in Generate 1 pulse per second using MSP430
So, does it work wiggling P2.4?
You can read and react to inputs within the interrupt, so there's not an absolute need to communicate with the main thread. E.g, within the ISR:
if(++timerCount > 1000) { timerCount = 0; if(pin indicates mode 1) { do 1 } else if (pin indicates mode 2) { do 2 } } An alternative approach is to use the ISR just to keep track of time, and move everything else into the main loop. You may add another flag to indicate that a second passed. e.g. in the ISR:
if (++timerCount > 1000) { timerCount = 0; secondFlag = 1; } Then in the main loop:
forever { if(secondFlag == 1) { // wait for flag to be set secondFlag = 0; // do whatever you need to do once a second } } You could maintain other flags if you need to support more time periods. Make sure to use the volatile keyword when declaring variables that you want to pass between the ISR and main loop.
An even more refined program structure would set a mode variable depending on inputs, then have a switch statement covering the different modes.
forever { if(secondFlag == 1) { secondFlag = 0; mode = depending on input pins; switch(mode) { case 1: do what we need to do for mode 1; break; case 2: do what we need to do for mode 2; break; default: do nothing; } } } And just like that, you wrote your first state machine. You may move the secondFlag check into the case statements if the modes don't share the timing requirements.
PS: You clear the pin 2 interrupt flag (P2IFG) in your ISR. This register is not related to timer interrupts. So no need to clear it.
PS2: Busy-waiting in the main loop is not very efficient in regards to power consumption, but we will leave optimizing that to the very end when everything else works.
-
chicken got a reaction from Fmilburn in Generate 1 pulse per second using MSP430
So, does it work wiggling P2.4?
You can read and react to inputs within the interrupt, so there's not an absolute need to communicate with the main thread. E.g, within the ISR:
if(++timerCount > 1000) { timerCount = 0; if(pin indicates mode 1) { do 1 } else if (pin indicates mode 2) { do 2 } } An alternative approach is to use the ISR just to keep track of time, and move everything else into the main loop. You may add another flag to indicate that a second passed. e.g. in the ISR:
if (++timerCount > 1000) { timerCount = 0; secondFlag = 1; } Then in the main loop:
forever { if(secondFlag == 1) { // wait for flag to be set secondFlag = 0; // do whatever you need to do once a second } } You could maintain other flags if you need to support more time periods. Make sure to use the volatile keyword when declaring variables that you want to pass between the ISR and main loop.
An even more refined program structure would set a mode variable depending on inputs, then have a switch statement covering the different modes.
forever { if(secondFlag == 1) { secondFlag = 0; mode = depending on input pins; switch(mode) { case 1: do what we need to do for mode 1; break; case 2: do what we need to do for mode 2; break; default: do nothing; } } } And just like that, you wrote your first state machine. You may move the secondFlag check into the case statements if the modes don't share the timing requirements.
PS: You clear the pin 2 interrupt flag (P2IFG) in your ISR. This register is not related to timer interrupts. So no need to clear it.
PS2: Busy-waiting in the main loop is not very efficient in regards to power consumption, but we will leave optimizing that to the very end when everything else works.
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
You could do that. But with your simple task, it is probably easier to use an interrupt.
The most common approach for simple pin wiggling based on the timer is to setup a timer interrupt that fires every millisecond and maintaining a millisecond counter.
Main:
- set a millisecond counter variable to 0
- setup timer to up mode, divide clock by 8, etc. (TA0CTL)
- set compare register to 1600, so that the timer interrupt occurs 1000 times per second (12.8M / 8 / 1600 = 1000) (TA0CCR0)
- enable timer interrupt
- go into endless loop
Inside the interrupt:
- increase millisecond counter variable
- if it reaches 1000, 1 second passed
-- reset your millisecond counter to 0
-- do your thing depending on state of input pin
See MSP430 family guide chapter 17.2 through 17.2.3.1.1
http://www.ti.com/lit/ug/slau208p/slau208p.pdf
Here's a very similar example. Note that the timer registers may have slightly different names as it's for a different MCU.
http://www.crash-bang.com/getting-started-msp430-timers-3/
PS: You only need to include msp430.h. Together with the MCU selection in the CCS project, it will take care to include the correct files.
-
chicken got a reaction from dubnet in MSP430 Wearable with Radio
For transmitter / master, I was thinking more of something at this scale
The relevant keyword for Ebay is IR illuminator
-
chicken got a reaction from oPossum in Generate 1 pulse per second using MSP430
You could do that. But with your simple task, it is probably easier to use an interrupt.
The most common approach for simple pin wiggling based on the timer is to setup a timer interrupt that fires every millisecond and maintaining a millisecond counter.
Main:
- set a millisecond counter variable to 0
- setup timer to up mode, divide clock by 8, etc. (TA0CTL)
- set compare register to 1600, so that the timer interrupt occurs 1000 times per second (12.8M / 8 / 1600 = 1000) (TA0CCR0)
- enable timer interrupt
- go into endless loop
Inside the interrupt:
- increase millisecond counter variable
- if it reaches 1000, 1 second passed
-- reset your millisecond counter to 0
-- do your thing depending on state of input pin
See MSP430 family guide chapter 17.2 through 17.2.3.1.1
http://www.ti.com/lit/ug/slau208p/slau208p.pdf
Here's a very similar example. Note that the timer registers may have slightly different names as it's for a different MCU.
http://www.crash-bang.com/getting-started-msp430-timers-3/
PS: You only need to include msp430.h. Together with the MCU selection in the CCS project, it will take care to include the correct files.
-
chicken got a reaction from energia in SPI between MSP430/432 and MCP3911
Grounds are often connected accidentally, e.g. when both devices are powered from the same USB hub. But to avoid any problems, it's better to explicitly make the connection.
Looking at your picture, I wonder if there's another MCU in that device that is connected to the MCP3911. If so, it will fight the MSP430 for control over SPI and lead to unexpected results.
-
chicken got a reaction from energia in SPI between MSP430/432 and MCP3911
You will need to connect with DGND / GNDB.
GND is the reference point to decide whether a signal is high or low. In electronics, connected GND is almost always required/assumed with only a few exceptions.
Did you also check SS with the oscilloscope?
Typically, SPI does not require pull-ups/downs. Unless explicitly mentioned in the datasheet of the MCP3911 or related evaluation boards, you probably don't need them.
-
chicken got a reaction from energia in SPI between MSP430/432 and MCP3911
What LaunchPad and what version of Energia are you using?
Looking at MSP430F5529 as an example, SS/SCK/MISO/MOSI are on pins 33/34/14/15 for SPI(0) and 8/7/9/10 for SPI(1).
-
chicken got a reaction from Fmilburn in MSP430 Wearable with Radio
For transmitter / master, I was thinking more of something at this scale
The relevant keyword for Ebay is IR illuminator
-
chicken got a reaction from omerdf in Generate 1 pulse per second using MSP430
PS: You may want to start with a basic tutorial on timer interrupts. E.g.
https://www.embeddedrelated.com/showarticle/182.php