Well, I went and built some tools to help me solve some problems and this is what I found with what I built. Architecturally, I merged two state machines into one so that they can run sequentially to reduce contention. Also since there is only one interrupt vector (TIMER1), it maps better to a single state machine. The states from the Left-Right state machine and the Fore-Aft state machine now combine to become the 2D-TILTS state machine. This also makes it easier to coordinate common states like powerup, idle and powerdown. The tilt sensor states are (in IsoMax): MACHINE 2D-TILTS \ capture and measure tilt signals APPEND-STATE LR-SYNCING \ find a rising edge on first signal APPEND-STATE LR-RISING \ record a rising edge APPEND-STATE LR-FALLING \ record pulse length APPEND-STATE LR-PERIOD \ record period length APPEND-STATE FA-SYNCING \ repeat for other signal APPEND-STATE FA-RISING APPEND-STATE FA-FALLING APPEND-STATE FA-PERIOD APPEND-STATE TILT-OFF \ no measurements; can be powered off The syncing state waits for a rising edge and then discards the reading. The rising and falling states record and subtract the times to get the pulse width and then the period state takes a final rising edge measurement to gauge the period for that pulse. One signal is dealt with, then the other, changing edge triggers each state in TIMER1_CCR always writing zero in between. This worked quite well and I could trigger a reading when needed except sometimes the pulse and period would be one period longer. I cleaned up the glitch by using the previous period and modulus but that got me to digging for the source of the glitch. There are a total of 6 interrupts running on the the 2106, 4 synchronously, 2 asynchronously. I used the TIMER_TC to time how long it takes to service each interrupt and then keep the maximum time value. Then I view these values to see how long the interrupts were taking. It turns out that occasionally, one interrupt, TILT-VIEWER which did LCD graphing was taking 1.5ms, which was longer than the LR or FA periods (1ms). So I refactored the looping code from inside one state into multiple states which displayed the current value, and then graphed the historical value, for both signals sequentially and synchronously. The tilt viewer state are (in IsoMax): MACHINE TILT-VIEWER \ View tilt signals on LCD APPEND-STATE TILT-HIDE \ don't show the tilt signals APPEND-STATE TILT-SHOW \ add LCD window dressing for signals APPEND-STATE TILT-UPDATE \ update LCD tilt display periodically APPEND-STATE LR-CURRENT \ display current left right signal value APPEND-STATE LR-HISTORY \ graph last 11sec of left right signal APPEND-STATE FA-CURRENT \ display current fore-aft value APPEND-STATE FA-HISTORY \ graph last 11sec of fore-aft values Once I started slicing, dicing and synchronizing the smaller components, everything ran a whole lot smoother and faster. So far so good. Now I will attempt to get nested interrupts running which are in the system but seem to be broken which is what got me into this tool building and refactoring phase in the first place. There is no end in sight if the journey is interesting. The best thing I liked doing in hardware design was the state machines but the hardest part was getting them working just right with the least logic. Now I find with coding a real time embedded system, the state machine factoring gives me the power to create a much finer designed system, only with software it is much easier to change. Its like having a better harness on the whole program code structure. Rob
Message
real-time interrupts, states and tools
2005-01-26 by chazeltopman
Attachments
- No local attachments were found for this message.