From ab1870534e480007c9ee0e4fec2493bbf417f946 Mon Sep 17 00:00:00 2001 From: tunix Date: Sun, 17 Jun 2012 22:49:06 +0200 Subject: [PATCH] refact0red awake-app, standby-packets are now sent continously --- firmware/applications/awake.c | 198 ++++++++++++++++++++-------------- 1 file changed, 118 insertions(+), 80 deletions(-) diff --git a/firmware/applications/awake.c b/firmware/applications/awake.c index f212ba3..a7593e3 100644 --- a/firmware/applications/awake.c +++ b/firmware/applications/awake.c @@ -10,21 +10,29 @@ #define AWAKE_PACKET_RETRIES 20 #define AWAKE_MIN_WINNERS 3 #define AWAKE_FONT_HEIGHT 8 +#define BTN_HBUS (1 << 7) -typedef enum packet_type_e { - PCKT_WINNER0, - PCKT_WINNER1, - PCKT_WINNER2, - PCKT_WINNER3, - PCKT_WINNER4, - PCKT_WINNER5, - PCKT_WINNER6, - PCKT_WINNER7, - PCKT_WAKEUP, - PCKT_STANDBY, - PCKT_NONE -} packet_type_t; +typedef enum awake_state_e { + AWAKE_STATE_STANDBY, + AWAKE_STATE_PLAYING, + AWAKE_STATE_WON +} awake_state_t; + + +typedef enum awake_packet_e { + AWAKE_PCKT_WINNER0, + AWAKE_PCKT_WINNER1, + AWAKE_PCKT_WINNER2, + AWAKE_PCKT_WINNER3, + AWAKE_PCKT_WINNER4, + AWAKE_PCKT_WINNER5, + AWAKE_PCKT_WINNER6, + AWAKE_PCKT_WINNER7, + AWAKE_PCKT_WAKEUP, + AWAKE_PCKT_STANDBY, + AWAKE_PCKT_NONE +} awake_packet_t; static char const *const awake_gPackets[] = { @@ -61,10 +69,10 @@ static void awake_initNrf(void) { /** * Polls for a special packet which indicates the success of a player. */ -static packet_type_t awake_waitForPacket(void) { +static awake_packet_t awake_waitForPacket(void) { uint8_t buffer[32]; if (nrf_rcv_pkt_time(100, 32, buffer) == 32) { - for (packet_type_t p = PCKT_WINNER0; p < PCKT_NONE; ++p) { + for (awake_packet_t p = AWAKE_PCKT_WINNER0; p < AWAKE_PCKT_NONE; ++p) { unsigned int bEqual = 1; for (unsigned int i = 0; i < 8; ++i) { if (buffer[i] != awake_gPackets[p][i]) { @@ -77,45 +85,49 @@ static packet_type_t awake_waitForPacket(void) { } } } - return PCKT_NONE; + return AWAKE_PCKT_NONE; } /** - * Waits for either pushed buttons or a signal on the hacker bus. + * Checks for pushed buttons and signals on RB_HB0. */ -static void awake_waitForKeyPressOrHackerbus(void) { - gpioSetDir(RB_HB0, gpioDirection_Input); - // watch out for pushed buttons and/or hacker bus activity - while (gpioGetValue(RB_HB0) != 0) { - if (getInput() != BTN_NONE) { +static uint8_t awake_getInputNonBlocking(void) { + volatile uint32_t rb_hb0 = gpioGetValue(RB_HB0); + if (rb_hb0 == 0) { + while (gpioGetValue(RB_HB0) == 0); + return BTN_HBUS; + } else { + uint8_t input = getInput(); + if (input != BTN_NONE) { getInputWaitRelease(); - break; } + return input; } - while (gpioGetValue(RB_HB0) == 0); } /** * The greeter! */ -static void awake_promptUserBegin(void) { - gpioSetDir(RB_HB0, gpioDirection_Input); - +static void awake_promptBegin(void) { lcdFill(0); - DoString(0, 0, "Eine Taste"); - DoString(0, 8, "druecken um"); - DoString(0,16, "das Spiel"); - DoString(0,24, "zu starten!"); + DoString(0, 0, "Standby-Modus"); + DoString(0,16, "Override mit"); + DoString(0,24, "Tastendruck."); lcdDisplay(); +} - awake_waitForKeyPressOrHackerbus(); +/** + * You don't say? + */ +static void awake_promptGameRunning(void) { lcdFill(0); DoString(0, 0, "Spiel laeuft!"); DoString(0, 16, "FEUERTASTE"); DoString(0, 24, "fuer Standby"); + DoInt(0, 32, 0); lcdDisplay(); } @@ -129,8 +141,30 @@ static void awake_promptUserEnd(void){ DoString(0, 8, "nug Gewinner "); DoString(0, 16, "ermittelt! "); lcdDisplay(); +} - // toggle RB_HB1 pin from 0V to 3,3 for 200ms + +/** + * Prepare hacker bus for our evil plans. + */ +static void awake_initHackerBus(void) { + // set RB_HB0 to input mode + gpioSetDir(RB_HB0, gpioDirection_Input); + + // set RB_HB1 to GPIO mode... + #define IOCON_PIO0_10 (*((REG32*) (0x40044068))) + IOCON_PIO0_10 &= ~(00000007); + IOCON_PIO0_10 |= 0x00000001; + // ...and to output low + GPIO_GPIO0DIR |= (1 << 10); + GPIO_GPIO0DATA &= ~(1 << 10); +} + + +/** + * Toggle RB_HB1 pin from 0V to 3,3 for 200ms. + */ +static void awake_toggleRbHb1(void) { GPIO_GPIO0DATA |= (1u << 10); delayms_queue(200); GPIO_GPIO0DATA &= ~(1u << 10); @@ -139,72 +173,76 @@ static void awake_promptUserEnd(void){ /** - * Explains a brief moment of unresponsiveness. + * Sends the specified packet. + * @param packet_type The kind of packet to be sent. */ -static void awake_promptStandby(void){ - lcdFill(0); - DoString(0, 0, "Bitte warten!"); - DoString(0, 8, "Sende Standby"); - DoString(0, 16, "Pakete... "); - lcdDisplay(); +static void awake_sendPacket(awake_packet_t packet_type) { + uint8_t packet[32]; + memcpy(packet, awake_gPackets[packet_type], 32); + nrf_snd_pkt_crc(32, packet); + delayms(10); } -void awake_initHackerBus() { - // set RB_HB1 to GPIO mode (output) - #define IOCON_PIO0_10 (*((REG32*) (0x40044068))) - IOCON_PIO0_10 &= ~(00000007); - IOCON_PIO0_10 |= 0x00000001; - GPIO_GPIO0DIR |= (1 << 10); - GPIO_GPIO0DATA &= ~(1 << 10); -} - /** * Main function of the l0dable. */ void main_awake(void) { awake_initNrf(); awake_initHackerBus(); + unsigned int nWinnerFlags = 0, nWinnerCount = 0; + awake_state_t state = AWAKE_STATE_STANDBY; while (1) { - awake_promptUserBegin(); - uint8_t joyinput = BTN_NONE; - unsigned int nWinnerFlags = 0, nWinnerCount = 0; - while ((joyinput != BTN_ENTER) && (nWinnerCount < AWAKE_MIN_WINNERS)) { - if ((joyinput = getInput()) != BTN_NONE) { - getInputWaitRelease(); + switch (state) { + case AWAKE_STATE_STANDBY: + awake_promptBegin(); + // wait for key press or hacker bus signal + while (awake_getInputNonBlocking() == BTN_NONE) { + awake_sendPacket(AWAKE_PCKT_STANDBY); + delayms(50); } + state = AWAKE_STATE_PLAYING; + break; - // send a "wake up" packet every loop cycle so that in case a r0ket - // is rebooted, the player can continue the game - uint8_t packet[32]; - memcpy(packet, awake_gPackets[PCKT_WAKEUP], 32); - delayms(10); - nrf_snd_pkt_crc(32, packet); + case AWAKE_STATE_PLAYING: + nWinnerFlags = 0; + nWinnerCount = 0; + awake_promptGameRunning(); + while (state == AWAKE_STATE_PLAYING) { + // check for manual override + if (awake_getInputNonBlocking() != BTN_NONE) { + // manual override -> back to standby mode + state = AWAKE_STATE_STANDBY; + } else { + // send a wake up packet + awake_sendPacket(AWAKE_PCKT_WAKEUP); - // watch out for winners! - packet_type_t const ePacket = awake_waitForPacket(); - unsigned int const nWinnerMask = (1 << ePacket) & 0xFF; - if ((ePacket <= PCKT_WINNER7) && !(nWinnerFlags & nWinnerMask)) { - nWinnerFlags |= nWinnerMask; - ++nWinnerCount; - DoInt(0, 32, nWinnerCount); - lcdDisplay(); + // watch out for winners! + const awake_packet_t ePacket = awake_waitForPacket(); + const unsigned int nWinnerMask = (1 << ePacket) & 0xFF; + if ((ePacket <= AWAKE_PCKT_WINNER7) && + !(nWinnerFlags & nWinnerMask)) { + nWinnerFlags |= nWinnerMask; + DoInt(0, 32, nWinnerCount); + lcdDisplay(); + if (++nWinnerCount >= AWAKE_MIN_WINNERS) { + state = AWAKE_STATE_WON; + } + } + } } - } + break; - if (nWinnerCount >= AWAKE_MIN_WINNERS) { + case AWAKE_STATE_WON: awake_promptUserEnd(); - } + awake_toggleRbHb1(); + state = AWAKE_STATE_STANDBY; + break; - awake_promptStandby(); - uint8_t packet[32]; - for (int i = 0; i < AWAKE_PACKET_RETRIES; ++i) { - delayms_queue(50); - memcpy(packet, awake_gPackets[PCKT_STANDBY], 32); - nrf_snd_pkt_crc(32, packet); + default: + state = AWAKE_STATE_STANDBY; + break; } } - - return; }