From 73a5a6974a98aa73ab392272b4d69d285c85dee5 Mon Sep 17 00:00:00 2001 From: Selene ToyKeeper Date: Sat, 19 Aug 2017 17:20:46 -0600 Subject: Completely reorganized SpaghettiMonster code into smaller logical pieces: fsm-*.c and fsm-*.h. --- spaghetti-monster/fsm-states.c | 108 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 108 insertions(+) create mode 100644 spaghetti-monster/fsm-states.c (limited to 'spaghetti-monster/fsm-states.c') diff --git a/spaghetti-monster/fsm-states.c b/spaghetti-monster/fsm-states.c new file mode 100644 index 0000000..652a9f2 --- /dev/null +++ b/spaghetti-monster/fsm-states.c @@ -0,0 +1,108 @@ +/* + * fsm-states.c: State-handling functions for SpaghettiMonster. + * + * Copyright (C) 2017 Selene ToyKeeper + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#ifndef FSM_STATES_C +#define FSM_STATES_C + +#include "fsm-states.h" +#include "fsm-adc.h" + +// TODO: if callback doesn't handle current event, +// pass event to next state on stack? +// Callback return values: +// 0: event handled normally +// 1: event not handled +// 255: error (not sure what this would even mean though, or what difference it would make) +// TODO: function to call stacked callbacks until one returns "handled" + +void _set_state(StatePtr new_state, uint16_t arg) { + // call old state-exit hook (don't use stack) + if (current_state != NULL) current_state(EV_leave_state, arg); + // set new state + current_state = new_state; + // call new state-enter hook (don't use stack) + if (new_state != NULL) current_state(EV_enter_state, arg); +} + +int8_t push_state(StatePtr new_state, uint16_t arg) { + if (state_stack_len < STATE_STACK_SIZE) { + // TODO: call old state's exit hook? + // new hook for non-exit recursion into child? + state_stack[state_stack_len] = new_state; + state_stack_len ++; + _set_state(new_state, arg); + return state_stack_len; + } else { + // TODO: um... how is a flashlight supposed to handle a recursion depth error? + return -1; + } +} + +StatePtr pop_state() { + // TODO: how to handle pop from empty stack? + StatePtr old_state = NULL; + StatePtr new_state = NULL; + if (state_stack_len > 0) { + state_stack_len --; + old_state = state_stack[state_stack_len]; + } + if (state_stack_len > 0) { + new_state = state_stack[state_stack_len-1]; + } + // FIXME: what should 'arg' be? + // FIXME: do we need a EV_reenter_state? + _set_state(new_state, 0); + return old_state; +} + +uint8_t set_state(StatePtr new_state, uint16_t arg) { + // FIXME: this calls exit/enter hooks it shouldn't + pop_state(); + return push_state(new_state, arg); +} + +// bottom state on stack +// handles default actions for LVP, thermal regulation, etc +uint8_t default_state(EventPtr event, uint16_t arg) { + if (0) {} + + #ifdef USE_LVP + else if (event == EV_voltage_low) { + low_voltage(); + return 0; + } + #endif + + #ifdef USE_THERMAL_REGULATION + else if (event == EV_temperature_high) { + high_temperature(); + return 0; + } + + else if (event == EV_temperature_low) { + low_temperature(); + return 0; + } + #endif + + // event not handled + return 1; +} + +#endif -- cgit v1.2.3 From 5631564b329d0445fb282e5e387217ba4e4ff191 Mon Sep 17 00:00:00 2001 From: Selene ToyKeeper Date: Wed, 23 Aug 2017 19:22:22 -0600 Subject: Added thermal regulation to SpaghettiMonster / Baton. Made some LVP values configurable. Removed high_temperature() / low_temperature() shortcuts for now. --- spaghetti-monster/fsm-states.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'spaghetti-monster/fsm-states.c') diff --git a/spaghetti-monster/fsm-states.c b/spaghetti-monster/fsm-states.c index 652a9f2..ec24dc8 100644 --- a/spaghetti-monster/fsm-states.c +++ b/spaghetti-monster/fsm-states.c @@ -89,6 +89,7 @@ uint8_t default_state(EventPtr event, uint16_t arg) { } #endif + #if 0 #ifdef USE_THERMAL_REGULATION else if (event == EV_temperature_high) { high_temperature(); @@ -100,6 +101,7 @@ uint8_t default_state(EventPtr event, uint16_t arg) { return 0; } #endif + #endif // event not handled return 1; -- cgit v1.2.3 From dce497bf15799133bf336ab46c3e39d7b0d92839 Mon Sep 17 00:00:00 2001 From: Selene ToyKeeper Date: Sun, 27 Aug 2017 19:40:40 -0600 Subject: Ramp config mode actually works now... Added EV_reenter_state event to indicate an obscuring state was popped off the stack and the underlying one is now on top again. --- spaghetti-monster/fsm-states.c | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) (limited to 'spaghetti-monster/fsm-states.c') diff --git a/spaghetti-monster/fsm-states.c b/spaghetti-monster/fsm-states.c index ec24dc8..2939475 100644 --- a/spaghetti-monster/fsm-states.c +++ b/spaghetti-monster/fsm-states.c @@ -31,13 +31,14 @@ // 255: error (not sure what this would even mean though, or what difference it would make) // TODO: function to call stacked callbacks until one returns "handled" -void _set_state(StatePtr new_state, uint16_t arg) { +void _set_state(StatePtr new_state, uint16_t arg, + EventPtr exit_event, EventPtr enter_event) { // call old state-exit hook (don't use stack) - if (current_state != NULL) current_state(EV_leave_state, arg); + if (current_state != NULL) current_state(exit_event, arg); // set new state current_state = new_state; // call new state-enter hook (don't use stack) - if (new_state != NULL) current_state(EV_enter_state, arg); + if (new_state != NULL) current_state(enter_event, arg); } int8_t push_state(StatePtr new_state, uint16_t arg) { @@ -46,7 +47,8 @@ int8_t push_state(StatePtr new_state, uint16_t arg) { // new hook for non-exit recursion into child? state_stack[state_stack_len] = new_state; state_stack_len ++; - _set_state(new_state, arg); + // FIXME: use EV_stacked_state? + _set_state(new_state, arg, EV_leave_state, EV_enter_state); return state_stack_len; } else { // TODO: um... how is a flashlight supposed to handle a recursion depth error? @@ -66,8 +68,7 @@ StatePtr pop_state() { new_state = state_stack[state_stack_len-1]; } // FIXME: what should 'arg' be? - // FIXME: do we need a EV_reenter_state? - _set_state(new_state, 0); + _set_state(new_state, 0, EV_leave_state, EV_reenter_state); return old_state; } -- cgit v1.2.3 From a419850e536f00549120255a627137faffded47a Mon Sep 17 00:00:00 2001 From: Selene ToyKeeper Date: Sun, 3 Sep 2017 14:58:22 -0600 Subject: Got the 4th PWM channel to work, ish. (channel 4 is inverted though) Moved go_to_suspend thing into main() instead of making each UI handle that during loop(). Made default_state() optional. Fixed bug where battcheck and other number readouts could interfere with the state which interrupted them. (they would sometimes turn the LED off after the new state had already started) Updated darkhorse's moon levels to match new ramp on D4 hardware. --- spaghetti-monster/fsm-states.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) (limited to 'spaghetti-monster/fsm-states.c') diff --git a/spaghetti-monster/fsm-states.c b/spaghetti-monster/fsm-states.c index 2939475..09ae804 100644 --- a/spaghetti-monster/fsm-states.c +++ b/spaghetti-monster/fsm-states.c @@ -67,26 +67,28 @@ StatePtr pop_state() { if (state_stack_len > 0) { new_state = state_stack[state_stack_len-1]; } - // FIXME: what should 'arg' be? + // FIXME: what should 'arg' be? (maybe re-entry should be entry with arg+1?) _set_state(new_state, 0, EV_leave_state, EV_reenter_state); return old_state; } uint8_t set_state(StatePtr new_state, uint16_t arg) { // FIXME: this calls exit/enter hooks it shouldn't + // (for the layer underneath the top) pop_state(); return push_state(new_state, arg); } +#ifndef DONT_USE_DEFAULT_STATE // bottom state on stack // handles default actions for LVP, thermal regulation, etc uint8_t default_state(EventPtr event, uint16_t arg) { - if (0) {} + if (0) {} // this should get compiled out #ifdef USE_LVP else if (event == EV_voltage_low) { low_voltage(); - return 0; + return EVENT_HANDLED; } #endif @@ -105,7 +107,8 @@ uint8_t default_state(EventPtr event, uint16_t arg) { #endif // event not handled - return 1; + return EVENT_NOT_HANDLED; } +#endif #endif -- cgit v1.2.3