[tuxdroid-svn] r730 - in firmware: tuxaudio/trunk tuxdefs
Status: Beta
Brought to you by:
ks156
From: Paul_R <c2m...@c2...> - 2007-11-27 09:38:38
|
Author: Paul_R Date: 2007-11-27 10:38:35 +0100 (Tue, 27 Nov 2007) New Revision: 730 Modified: firmware/tuxaudio/trunk/AT26F004.c firmware/tuxaudio/trunk/AT26F004.h firmware/tuxaudio/trunk/PC_communication.c firmware/tuxaudio/trunk/flash.c firmware/tuxaudio/trunk/flash.h firmware/tuxaudio/trunk/main.c firmware/tuxaudio/trunk/varis.c firmware/tuxaudio/trunk/varis.h firmware/tuxdefs/api.h firmware/tuxdefs/commands.h Log: * The way to store the sounds in the memory has changed : Now, the indexes aren't not sent by the PC, but they are computed by the firmware. The sound's track are stored one by one in the memory. When the storage is done, the program waits for a confirmation. If the storage is confirmed, the indexes are written, else the sound is directly erased. The status have changed. Two new status commands have been created, one for the playback, the other for the recording. The number of sounds stored in the memory and the last used block are also sent to the PC each time they're changing. Modified: firmware/tuxaudio/trunk/AT26F004.c =================================================================== --- firmware/tuxaudio/trunk/AT26F004.c 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/AT26F004.c 2007-11-27 09:38:35 UTC (rev 730) @@ -24,9 +24,10 @@ #include "hardware.h" #include "spi.h" +static void unprotect_sectors(void); /** * \ingroup at26f004 - * \brief initialize a table with the sectors adresses values + * \brief initialize a table with the sector adresses values */ static uint8_t sector_adress[11][3] = { {SECTOR0}, @@ -117,6 +118,17 @@ */ void erase_flash(void) { + + unprotect_sectors(); + write_enable(); /* Enable the writing */ + + flash_select(); + spiSend(CHIP_ERASE); /* Send Erase Bulk command */ + flash_unselect(); +} + +static void unprotect_sectors(void) +{ uint8_t i; write_status(0x00); /* Disable sector protection register */ for (i=0; i<=10; i++) @@ -124,14 +136,7 @@ write_enable(); /* Enable the writing */ unprotect_sector(sector_adress[i][0], sector_adress[i][1],sector_adress[i][2]); } - - write_enable(); /* Enable the writing */ - - flash_select(); - spiSend(CHIP_ERASE); /* Send Erase Bulk command */ - flash_unselect(); } - /** * \ingroup at26f004 \param ad2 high address part @@ -168,7 +173,6 @@ { uint8_t data1; - flash_enable(); // Set the HOLD signal flash_select(); spiSend(READ_ARRAY_LOW_F); /* Send Read Page Command */ /* Send address */ @@ -177,10 +181,41 @@ spiSend(ad0); data1 = spiSend(NOP); /* Wait response */ flash_unselect(); - flash_onhold(); // Reset the HOLD signal return data1; } +/** + * \ingroup at26f004 + \param first_block The first block to erase + \param last_block The last block to erase + \brief This function erase a specified area in the memory. The memory will be erased by 4kB's blocks. + */ +void blockErase(uint8_t first_block, uint8_t last_block) +{ + uint8_t diff, ad0, ad1; + // unprotect all sectors + unprotect_sectors(); + // diff is the number of block to erase + diff = last_block - first_block + 1; + while(diff) + { + // Erase a 4kB block + write_enable(); + flash_select(); + ad0 = (last_block >> 4); + ad1 = (last_block << 4); + spiSend(BLOCK_ERASE_4K); /* Send Erase Bulk command */ + spiSend(ad0); + spiSend(ad1); + spiSend(0x00); + flash_unselect(); + + diff --; + last_block --; + while (read_status() & BUSY); + } +} + Modified: firmware/tuxaudio/trunk/AT26F004.h =================================================================== --- firmware/tuxaudio/trunk/AT26F004.h 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/AT26F004.h 2007-11-27 09:38:35 UTC (rev 730) @@ -146,6 +146,7 @@ /** \name Misc. functions * @{ */ extern void erase_flash(void); +extern void blockErase(uint8_t first_block, uint8_t last_block); extern void unprotect_sector(uint8_t const ad2, uint8_t const ad1, uint8_t const ad0); /* @} */ Modified: firmware/tuxaudio/trunk/PC_communication.c =================================================================== --- firmware/tuxaudio/trunk/PC_communication.c 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/PC_communication.c 2007-11-27 09:38:35 UTC (rev 730) @@ -44,7 +44,7 @@ asm volatile /* Clear the SPI interrupt flag */ ("in __tmp_reg__, %0" "\n\t" "in __tmp_reg__, %1" "\n\t":: "I" (_SFR_IO_ADDR(SPSR)), "I"(_SFR_IO_ADDR(SPDR))); - + flash_onhold(); PORTB &= ~0x04; // Chip select while (1) { @@ -113,6 +113,20 @@ spi_lenght_data = 34; else spi_lenght_data = 17; + if (spi_master_config == 0x08 || spi_master_config == 0x00) + { + if (frame_without_sound) + frame_without_sound --; + + else + sound_played = 0; + } + else + { + sound_played = 1; + frame_without_sound = frame_without_sound_timeout; + } + spi_master = PUT_SOUND_FIFO; // Go to the next state if (!programmingFlash && !flashPlay) // XXX code must be review it's very strange ..... @@ -169,6 +183,7 @@ } } } + flash_enable(); } } Modified: firmware/tuxaudio/trunk/flash.c =================================================================== --- firmware/tuxaudio/trunk/flash.c 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/flash.c 2007-11-27 09:38:35 UTC (rev 730) @@ -27,101 +27,248 @@ #include "i2c.h" #include "flash.h" #include "AT26F004.h" +#include "common/api.h" + /* Declarations */ -/* Theses functions are declared with the static attribute, so they're - * accessible only by this module */ - -static void erasingFlash(void); -static void programmingNumSound(void); -static void programmingToc(void); -static void initSoundProgramming(void); -static void soundProgramming(void); -static void endProgramming(void); - +static void init_programming(uint8_t adi0, uint8_t adi1, uint8_t adi2); +static void programming_sound(void); static void playInit(uint8_t const nsound); static void playingSound(void); static void stopPlaying(void); -uint8_t f_state; uint8_t flash_state; -uint8_t ad0, ad1, ad2, i, j; - uint8_t soundNum; +static uint16_t index; +static uint8_t sound_stored = 0; +static uint8_t count, ad0, ad1; +static uint8_t first_block; -/* Public functions */ /** * \ingroup flash - \brief This function is used to reprogram sound flash memory.. - - This function is structured like a state machine. The six states are : - - ERASE_STATE which perform a full chip erase. This state turn off the PWM - and disable I2C interrupt. - - FIRST_PROG_STATE write the number of sounds to be stored. - - PROG_TOC_STATE write the sound's indexes each time a INDEX COMMAND is - received. The last indexes are stored. - - INIT_SOUND_PROG_STATE initiate the memory to a sequential programming. The - first sound byte is writed in the flash. - - SOUND_PROG_STATE store all the sound data received. - - END_STATE clear all variable used to control the programming task, and - reswitch-on the I2C and the PWM timer. + \brief Read the number of sound in the flash memory. + This function scan the sound's indexes, and return the number of sound stored + in the flash memory. */ -void flashProgramming(void) -{ - SPCR = 0x00; - SPCR = 0X50; - PORTB |= 0x01; - if (f_state == ERASE_STATE) +uint8_t readFlashNumber(void) +{ + uint8_t i; + ad0 = 0x01; + ad1 = 0x00; + count = 0; + while(1) { - if (flash_state) - erasingFlash(); - - else if (!(read_status() & BUSY)) + if (read_data(0x00, ad1, ad0) == 0xFF) { - send_status(STATUS_AUDIO_CMD, 0, 2, 0); - f_state ++; + count --; + return count; } + else + { + for (i = 0; i < 3; i++) + { + ad0 ++; + if (ad0 == 0) + ad1++; + } + } + count ++; } - else if (f_state == FIRST_PROG_STATE) + return 0; +} + +uint8_t readLastBlock(uint8_t num) +{ + index = (numSound * 3) + 1; + ad[0] = read_data(0x00, (index>>8), (index & 0xFF)); + index ++; + ad[1] = read_data(0x00, (index>>8), (index & 0xFF)); + index ++; + ad[2] = read_data(0x00, (index>>8), (index & 0xFF)); + return (ad[0] << 4) + (ad[1] >> 4); +} +/** + * \ingroup flash + \brief Store a sound in the memory. + + This function contain 5 states : + + DETECT_INDEXES : Detect if the memory is empty or not, and determine where the sound must be stored. + + PROG_INIT : Start the programmation cycle with the indexes determinated in the first state. + + PROGRAMMING : Program the memory with the sound byte received by the RF. + + PROG_TOC : If the programming sequence is finished, the indexes are written. + + PROG_END : Restore the context. + + \note Each sound starts at the first byte of a 4kB block. To do this, the + lower address byte is reset, and the medium address byte is incremented. + +*/ + +void programming(void) +{ + uint8_t static programming_state = DETECT_INDEXES; + if (programming_state == DETECT_INDEXES) { - send_status(STATUS_AUDIO_CMD, 0, 3, 0); - programmingNumSound(); - send_status(STATUS_AUDIO_CMD, 0, 4, 0); - f_state ++; - } - else if (f_state == PROG_TOC_STATE) - { - if (TOCRX) + TIMSK0 = 0x00; + //numSound = readFlashNumber(); + if (numSound == 0) { - programmingToc(); + /* The flash memory is empty. The first address is 0x000400 */ + ad[0] = 0x00; + ad[1] = 0x04; + ad[2] = 0x00; + first_block = 0; } + else + { + /* One or more sounds are programmed in the flash memory. + * The next sound must be stored after the others */ + index = (numSound * 3) + 1; + ad[0] = read_data(0x00, (index>>8), (index & 0xFF)); + index ++; + ad[1] = read_data(0x00, (index>>8), (index & 0xFF)); + index ++; + ad[2] = read_data(0x00, (index>>8), (index & 0xFF)); - if (flash_state) - f_state ++; + // Goto the next 4kB block. + ad[1] += 0x10; + ad[1] &= ~0x0F; + if (ad[1] == 0) + ad[0] ++; + ad[2] = 0; + first_block = (ad[0] << 4) + (ad[1] >> 4); + } + resetFifo(&PWMFifo); + + if (ad[0] > 0x07) + { + programming_state = PROG_END; + send_status(STATUS_FLASH_PROG_CMD, FLASH_FULL, 0, 0); + } + else + programming_state ++; + + frame_without_sound = 5000; + frame_without_sound_timeout = 5000; + send_status(STATUS_FLASH_PROG_CMD, IN_PROGRESS, ad[0], ad[1]); } - else if (f_state == INIT_SOUND_PROG_STATE) + + else if (programming_state == PROG_INIT) { - initSoundProgramming(); + init_programming(ad[0], ad[1], ad[2]); + programming_state ++; + flash_state = 1; + sound_stored = 0; + } + else if (programming_state == PROGRAMMING) + { if (flash_state) + programming_sound(); + + else { - send_status(STATUS_AUDIO_CMD, 0, 5, 0); - f_state ++; + write_disable(); + if (sound_stored) + { + last_block = (ad[0] << 4) + (ad[1] >> 4); + send_status(STATUS_FLASH_PROG_CMD, WAITING_FOR_CONFIRMATION, last_block - first_block, 0); + programming_state ++; + } + else + { + send_status(STATUS_FLASH_PROG_CMD, NO_SOUND, 0, 0); + programming_state = PROG_END; + } } + } + else if (programming_state == WAITING_STATE) + { + if (write_toc == 1) + { + programming_state = PROG_TOC; + } + else if (write_toc == 2) + { + send_status(STATUS_FLASH_PROG_CMD, ERASING_LAST_SOUND, 0, 0); + if (first_block == 0) + { + eraseFlag = 1; + frame_without_sound_timeout = TTS_TIMEOUT; + programming_state = 0; + programmingFlash = 0; + } + else + { + last_block = (ad[0] << 4) + (ad[1] >> 4); + blockErase(first_block, last_block); + programming_state = PROG_END; + } + } + write_toc = 0; } - if (f_state == SOUND_PROG_STATE) + else if (programming_state == PROG_TOC) { - soundProgramming(); + send_status(STATUS_FLASH_PROG_CMD, WRITE_TOC, 0, 0); + numSound ++; + index = (numSound * 3) + 1; + program_flash(0x00, (index>>8), (index & 0xFF), ad[0]); + index ++; + program_flash(0x00, (index>>8), (index & 0xFF), ad[1]); + index ++; + program_flash(0x00, (index>>8), (index & 0xFF), ad[2]); + last_block = (ad[0] << 4) + (ad[1] >> 4); + programming_state ++; + } + else if (programming_state == PROG_END) + { + numSound = readFlashNumber(); + frame_without_sound_timeout = TTS_TIMEOUT; + programming_state = 0; + programmingFlash = 0; + TIMSK0 = 0x01; + //info_flg = 1; + send_status(STATUS_FLASH_PROG_CMD, STANDBY, 0, 0); + send_status(SOUND_VAR_CMD, numSound, last_block, 0); + } +} - if (flash_state) - f_state ++; +/** + * \ingroup flash + \brief Erase the flash memory. + + The first step is to send the command to erase the flash. + After, the status is polled while the erase process isn't finished. + When the BUSY flag is null, the erase sequence is stopped. +*/ +void erase(void) +{ + uint8_t static enter = 1; + if (enter) + { + erase_flash(); + enter = 0; } - else if (f_state == END_STATE) + else if (!(read_status() & BUSY)) { - endProgramming(); - send_status(STATUS_AUDIO_CMD, 0, 0, 0); - f_state = 0; + //send_status(STATUS_FLASH_PROG_CMD, STANDBY, 0, 0); + enter = 1; + eraseFlag = 0; + program_flash(0x00, 0x00, 0x00, 0xFE); + program_flash(0x00, 0x00, 0x01, 0x00); + program_flash(0x00, 0x00, 0x02, 0x04); + program_flash(0x00, 0x00, 0x03, 0x00); + numSound = 0; + last_block = 0; + send_status(STATUS_FLASH_PROG_CMD, STANDBY, 0, 0); + send_status(SOUND_VAR_CMD, numSound, last_block, 0); + //info_flg = 1; + TIMSK0 = 0x01; } } @@ -132,20 +279,18 @@ The first step (playInit) is to initialize the flash memory with the selected sound to play. Many tests are made to ensure that the sound to play exist, the indexes are correct, etc. - The second step (playingSound) is to fill the fifo with the sound's bytes, and to verify the adresses. + The second step (playingSound) is to fill the fifo with the sound's bytes, and to verify the addresses. + */ - */ + void playSound(void) { if (flash_state) - playInit(soundNum); + playInit(soundToPlay); else playingSound(); } - - - /* Static functions */ /** * \ingroup flash @@ -163,50 +308,54 @@ static void playInit(uint8_t const nsound) { - uint8_t count, i; - uint8_t adp1, adp0, sounds_stored; // Address pointer varaible - flash_enable(); - sounds_stored = read_data(0x00, 0x00, 0x00); - if (sounds_stored == 0xFF) /* if unprogrammed we have 0xFF stored in flash */ + uint8_t i; + + if (numSound == 0x00) /* if unprogrammed we have 0xFF stored in flash */ { flashPlay = 0; return; } - if (!nsound || (nsound > sounds_stored)) /* check the limits */ + if (!nsound || (nsound > numSound)) /* check the limits */ { flashPlay = 0; return; } count = 1; - adp1 = 0x00; - adp0 = 0x01; + ad1 = 0x00; + ad0 = 0x01; while (count != nsound) // Compute address { for (i = 0; i < 3; i++) { - adp0++; - if (adp0 == 0) - adp1++; + ad0++; + if (ad0 == 0) + ad1++; } count++; } - flash_select(); // Chip Select - flash_enable(); spiSend(READ_ARRAY_LOW_F); // Send Read Page Command spiSend(0x00); // Send Address - spiSend(adp1); - spiSend(adp0); + spiSend(ad1); + spiSend(ad0); for (i = 0; i < 6; i++) { ad[i] = spiSend(NOP); // Read start and stop sound address } + if (nsound > 1) + { + ad[1] += 0x10; + ad[1] &= ~0x0F; + if (ad[1] == 0) + ad[0] ++; + ad[2] = 0; + } flash_unselect(); // Chip Deselect - /* Check adresses */ + /* Check addresses */ if (ad[0] > TOP_A2) { flashPlay = 0; @@ -255,7 +404,6 @@ spiSend(ad[0]); // Send Address spiSend(ad[1]); spiSend(ad[2]); - flash_onhold(); // Reset the HOLD signal OCR0A = 250; // Normal operation for PWM if fifo adaptative is on flash_state = 0; @@ -273,7 +421,6 @@ static void playingSound(void) { uint8_t sound; - flash_enable(); while (!spi_start && !isFifoFull(&PWMFifo)) { sound = spiSend(0x00); // Wait response @@ -302,7 +449,6 @@ break; } } - flash_onhold(); } /* Static functions */ @@ -311,181 +457,99 @@ \brief Stop the play sequence. */ - static void stopPlaying(void) { + soundToPlay = 0; flashPlay = 0; send_status(STATUS_AUDIO_CMD, 0, 0, 0); PORTB |= 0x01; // Set the HOLD signal PORTB |= 0x02; // Chip Deselect } - /** * \ingroup flash - * \brief Erase the flash memory. - * - * This funtion perform a full erase of the flash memory and initiate the sound - * flash programming. - */ -static void erasingFlash(void) + \brief Init the programming sequence + + To perform a sequential programming, the first step is to send the correct OP + code, and the three address bytes where the first data byte must be stored. + The second step is to send the OP code and a data to write. + + This function perform the first step. + */ +static void init_programming(uint8_t adi0, uint8_t adi1, uint8_t adi2) { - /* Desactivate the PWM */ - TCCR0A = 0x00; - TCCR0B = 0x00; - OCR0A = 0x00; - TIMSK0 = 0x00; - - - resetFifo(&PWMFifo); /* Reinitialise the PWM fifo */ - erase_flash(); /* Erase the flash */ - flash_state = 0; + write_enable(); + flash_select(); + spiSend(SEQU_PROGRAM); + spiSend(adi0); + spiSend(adi1); + spiSend(adi2); + if (!isFifoEmpty(&PWMFifo)) + spiSend(pullFifo(&PWMFifo)); + else + spiSend(0x80); + + flash_unselect(); // Chip Deselect } + /** * \ingroup flash - * \brief Write the number of sound to be stored. - * - This function store the first TOC byte (numSound), received with the flash - program command, at the first memory adress. - */ + \brief Program the sound's data into the flash memory -static void programmingNumSound(void) -{ - program_flash(0x00, 0x00, 0x00, numSound); // Write first byte of the TOC + This function is executed while the SPI start command is not present. Each + cycle, one byte is popped from the PWM fifo and stored in the sound flash. - ad0 = 0x01; // Init TOC address - ad1 = 0x00; - ad2 = 0x00; - i = 0; -} -/** - * \ingroup flash - * \brief Write the TOC in the memory. - * - * This function store the the indexes into the memory. - */ + The frame_without_sound variable is decremented each time the RF receive a + frame without sound. When this variable is null, the sound process is + stopped. -static void programmingToc(void) -{ - TOCRX = 0; - flash_state = 0; - for (j = 0; j < 3; j++) - { - program_flash(ad2, ad1, ad0, TOCadress[j]); - ad0++; // Increment new adress - if (ad0 == 0x00) - ad1++; - } - i++; + If a programming sequence starts, but no sound is received, the cycle is + stopped. - /* Store the final adress */ - if (i == numSound + 1) - { - ad[0] = TOCadress[2]; - ad[1] = TOCadress[1]; - ad[2] = TOCadress[0]; + If the address is equal to 0x07FFFF (the last memory address), the programming + cycle is stopped. - /* Init the first sound byte adress */ - ad2 = 0x00; - ad1 = 0x04; - ad0 = 0x00; - - flash_state = 1; - } -} -/** - * \ingroup flash - * \brief Initiate the sound programming. - * - * This function initiate the sound flash memory for a sequential programming. + The sound_stored flag is set when at least one byte is stored in the memory. + Else, this variable is null. */ -static void initSoundProgramming (void) +static void programming_sound(void) { - flash_state = 0; - write_enable(); - flash_select(); - spiSend(SEQU_PROGRAM); - spiSend(ad2); - spiSend(ad1); - spiSend(ad0); - while (!spi_start) // Send first byte into the page flash + while (!spi_start) { - if (!isFifoEmpty(&PWMFifo)) // Fifo not empty + if (!isFifoEmpty(&PWMFifo)) { - spiSend(pullFifo(&PWMFifo)); // Write data in flash - ad0++; - flash_state = 1; // End of firt command - break; - } - else - flash_state = 0; - } - flash_unselect(); // Chip Deselect -} + sound_stored = 1; + frame_without_sound = STOP_FRAME_NUMBER; + frame_without_sound_timeout = STOP_FRAME_NUMBER; -/** - * \ingroup flash - * \brief Program the sound in the flash memory. - * - * This function store the sound in the flash memory. - */ -static void soundProgramming(void) -{ - flash_state = 0; - while (!spi_start) - { - if (!isFifoEmpty(&PWMFifo)) // Fifo not empty - { - flash_select(); // Chip Select - spiSend(SEQU_PROGRAM); // Send Sequencial Program Command - spiSend(pullFifo(&PWMFifo)); // Write data in flash - flash_unselect(); // Chip DeselecT - ad0++; // Increment address byte - if (ad0 == 0x00) + flash_select(); + spiSend(SEQU_PROGRAM); + spiSend(pullFifo(&PWMFifo)); + flash_unselect(); + + ad[2] ++; + if (ad[2] == 0x00) { - ad1++; - if (ad1 == 0x00) - ad2++; + ad[1]++; + if (ad[1] == 0x00) + ad[0]++; } - while (read_status() & BUSY) ; // Wait Page Program Cycle + while (read_status() & BUSY) ; } /* Check for the last sound byte */ - if (ad2 == ad[2]) + if (!(frame_without_sound)) { - if (ad1 == ad[1]) - { - if (ad0 == ad[0]) - { - flash_state = 1; - break; // Stop programming flash - } - } + flash_state = 0; + break; } + if (ad[0] == 0x07 && ad[1] == 0xFF && ad[2] == 0xFF) + { + flash_state = 0; + break; + } } } -/** - * \ingroup flash - * \brief This function end the flash programming task. - * - * This function restore all the parameters. - */ - -static void endProgramming (void) -{ - write_disable(); // Disable wrtie flash - flash_state = 0; - TCCR0A = 0x23; // Reactivate PWM - TCCR0B = 0x09; - OCR0A = 249; /* we need TOP=250 to get a 8kHz sampling frequency */ - TIMSK0 = 0x01; - - TWCR = (TWCR & TWCR_CMD_MASK) | _BV(TWIE); // Reactivate I2C - - programmingFlash = 0; // Reset the flag to suspend the task -} - - Modified: firmware/tuxaudio/trunk/flash.h =================================================================== --- firmware/tuxaudio/trunk/flash.h 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/flash.h 2007-11-27 09:38:35 UTC (rev 730) @@ -36,18 +36,43 @@ /** \name Flash programming states @{ */ -#define ERASE_STATE 0 -#define FIRST_PROG_STATE 1 -#define PROG_TOC_STATE 2 -#define INIT_SOUND_PROG_STATE 3 -#define SOUND_PROG_STATE 4 -#define END_STATE 5 +enum { + DETECT_INDEXES = 0, + PROG_INIT, + PROGRAMMING, + WAITING_STATE, + PROG_TOC, + PROG_END, +}; /* @} */ +/** \name No sound in frame timeout + @{ */ +#define STOP_FRAME_NUMBER 10 +#define TTS_TIMEOUT 10 +#define START_FRAME_NUMBER 100 +/* @} */ +/** \name Flash programming status + @{ */ +/* +enum { + STANDBY = 0, + IN_PROGRESS, + WAITING_FOR_CONFIRMATION, + WRITE_TOC, + ERASING_LAST_SOUND, + FLASH_FULL, + NO_SOUND, +}; +*/ +/* @} */ -extern void flashProgramming(void); +extern void programming(void); extern void playSound(void); +extern void erase(void); +extern uint8_t readFlashNumber(void); +extern uint8_t readLastBlock(uint8_t num); /** start / end flash states flag */ extern uint8_t flash_state; Modified: firmware/tuxaudio/trunk/main.c =================================================================== --- firmware/tuxaudio/trunk/main.c 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/main.c 2007-11-27 09:38:35 UTC (rev 730) @@ -54,7 +54,7 @@ {REVISION_CMD, SVN_REV, RELEASE_TYPE}; const version_t tag_version __attribute__ ((section("version.1"))) = {VERSION_CMD, CPU_VER_JOIN(CPU_NUMBER, VER_MAJOR), VER_MINOR, VER_UPDATE}; -static uint8_t info_flg = 0; /* indicates if version information should be sent */ + static uint8_t pre_sleep_delay = 0; /* set when sleep should be entered */ void send_info(void) @@ -70,8 +70,8 @@ i2cSlaveReceiveService(4, buf + 8); sei(); buf[0] = SOUND_VAR_CMD; - buf[1] = read_data(0x00, 0x00, 0x00); - buf[2] = 0; + buf[1] = numSound; + buf[2] = last_block; buf[3] = 0; cli(); i2cSlaveReceiveService(4, buf); @@ -164,7 +164,7 @@ return; audioLevel = audioBuf[2]; //playingAudio(audioBuf[1]); /* start playing the sound */ - soundNum = audioBuf[1]; + soundToPlay = audioBuf[1]; send_status(STATUS_AUDIO_CMD, audioBuf[1], 0, 0); flashPlay = 1; flash_state = 1; @@ -201,30 +201,26 @@ { if (flashPlay) flashPlay = 0; - /* param: command[1] : number of sounds */ - numSound = command[1]; - f_state =0; /* First programming state */ flash_state = 1; /* Erasing flash flag */ - send_status(STATUS_AUDIO_CMD, 0, 1, 0); programmingFlash = 1; /* Set the flag to enter programming sequence */ } - else if (command[0] == STORE_INDEX_CMD) + else if (command[0] == ERASE_FLASH_CMD) { - /* param: command[1] : lower address byte */ - /* command[2] : middle address byte */ - /* command[3] : higher address byte */ - TOCadress[2] = command[3]; // High address - TOCadress[1] = command[2]; // Medium address - TOCadress[0] = command[1]; // Lower address - TOCRX = 1; // Set TOC incoming flag - command[0] = 0; + eraseFlag = 1; } /* Version */ else if (command[0] == INFO_TUXAUDIO_CMD) + info_flg = 1; /* info should be sent when the buffer will be free */ + + else if (command[0] == CONFIRM_STORAGE_CMD) { - info_flg = 1; /* info should be sent when the buffer will be free */ + if (command[1]) + write_toc = 1; + else + write_toc = 2; } + else pushCommands(command); /* push the command set on the filo stack */ } @@ -244,8 +240,11 @@ if (PINB & 0x40) command[1] |= 0x20; command[1] ^= 0x9B; /* some bits should be inverted */ - command[2] = audio_level; - command[3] = battery_level; + command[2] = soundToPlay; + if (soundToPlay || sound_played) + command[3] = 1; + else + command[3] = 0; pushCommands(command); /* push the command set on the filo stack */ } @@ -256,8 +255,10 @@ resetFifo(&PWMFifo); /* Initialise the PWM fifo */ resetFifo(&ADCFifo); /* Initialise the ADC fifo */ config_init(); /* load the configuration defaults from EEPROM */ - + numSound = readFlashNumber(); + last_block = readLastBlock(numSound); i2cCommunicationInit(); /* I2C initialization */ + frame_without_sound_timeout = TTS_TIMEOUT; sei(); /* Init global interrupt */ @@ -297,11 +298,14 @@ } if (programmingFlash) // Restora all the context for flash programming - flashProgramming(); + programming(); if (flashPlay) playSound(); + if (eraseFlag) + erase(); + if (sendSensorsFlag) { sendSensorsFlag = 0; Modified: firmware/tuxaudio/trunk/varis.c =================================================================== --- firmware/tuxaudio/trunk/varis.c 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/varis.c 2007-11-27 09:38:35 UTC (rev 730) @@ -51,15 +51,15 @@ fifo_t ADCFifo = { (uint8_t *) ADCbuffer, sizeof ADCbuffer - 1, 0, 0 }; // Flash programming +uint8_t eraseFlag = 0; volatile unsigned char programmingFlash = 0; -volatile unsigned char numSound; -volatile unsigned char TOCadress[3]; -volatile unsigned char TOCRX = 0; +volatile uint8_t numSound; // Flash Variables volatile unsigned char flashPlay = 0; volatile unsigned char ad[6]; volatile unsigned char audioLevel; +uint8_t soundToPlay; unsigned char sendSensorsCmpt, sendSensorsFlag; unsigned char audio_level, battery_level; @@ -70,3 +70,12 @@ volatile unsigned char lockAdaptFifo = 1; volatile unsigned char Fifoinert = 0; + +uint16_t frame_without_sound = 0; +uint16_t frame_without_sound_timeout= 0; +uint8_t sound_played = 0; +uint8_t last_block = 0; + +// General flags +uint8_t info_flg = 0; /* indicates if version information should be sent */ +uint8_t write_toc = 0; Modified: firmware/tuxaudio/trunk/varis.h =================================================================== --- firmware/tuxaudio/trunk/varis.h 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxaudio/trunk/varis.h 2007-11-27 09:38:35 UTC (rev 730) @@ -59,15 +59,16 @@ extern fifo_t ADCFifo; // Flash programming + +extern uint8_t eraseFlag; extern volatile unsigned char programmingFlash; -extern volatile unsigned char numSound; -extern volatile unsigned char TOCadress[3]; -extern volatile unsigned char TOCRX; +extern volatile uint8_t numSound; // Flash Variables extern unsigned char flashPlay; extern volatile unsigned char ad[6]; extern volatile unsigned char audioLevel; +extern uint8_t soundToPlay; extern unsigned char sendSensorsCmpt, sendSensorsFlag; extern unsigned char audio_level, battery_level; @@ -80,5 +81,12 @@ extern volatile unsigned char lockAdaptFifo; extern volatile unsigned char Fifoinert; +extern uint16_t frame_without_sound; +extern uint16_t frame_without_sound_timeout; +extern uint8_t sound_played; +extern uint8_t last_block; +// General flags +extern uint8_t info_flg; +extern uint8_t write_toc; #endif Modified: firmware/tuxdefs/api.h =================================================================== --- firmware/tuxdefs/api.h 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxdefs/api.h 2007-11-27 09:38:35 UTC (rev 730) @@ -188,6 +188,18 @@ */ #define SOUND_VAR_CMD 0xCB +/** States of the audio recording (flash programming) process */ +typedef enum audiorec_status +{ + STANDBY = 0, + IN_PROGRESS, + WAITING_FOR_CONFIRMATION, + WRITE_TOC, + ERASING_LAST_SOUND, + FLASH_FULL, + NO_SOUND, +} audiorec_status_t; + /*! @} */ /*! @} */ Modified: firmware/tuxdefs/commands.h =================================================================== --- firmware/tuxdefs/commands.h 2007-11-27 09:09:53 UTC (rev 729) +++ firmware/tuxdefs/commands.h 2007-11-27 09:38:35 UTC (rev 730) @@ -99,12 +99,14 @@ #define PLAY_SOUND_CMD 0x90 /* play a sound from the flash sound bank */ /* 1st parameter: sound number */ /* 2nd parameter: sound volume */ -#define STORE_SOUND_CMD 0x52 /* start flash sound bank storage [1] */ -/* 1st parameter: number of sounds to store */ -#define STORE_INDEX_CMD 0xD0 /* get indexes of the flash sound bank [1] */ -/* 1st parameter: lower address byte */ -/* 2nd parameter: middle address byte */ -/* 3rd parameter: higher address byte */ +#define STORE_SOUND_CMD 0x52 + +#define CONFIRM_STORAGE_CMD 0x53 +/* 1st parameter: 1 to write the sound + * 0 to not write the sound*/ + +#define ERASE_FLASH_CMD 0xD0 /* get indexes of the flash sound bank [1] */ + #define TEST_SOUND_CMD 0x10 /* test the audio input and output [1] */ #define MUTE_CMD 0x92 /* mute/unmute the audio amplifier */ /* 1st parameter: mute state 0:unmute 1:mute */ @@ -122,8 +124,7 @@ #define SLEEP_CMD 0xB7 /* set the CPU in sleep mode */ /* 1st parameter: reserved */ /* 2nd parameter: type of sleep mode */ -#define DEEPSLEEP_MODE 1 /* minimal power consumption, can't wake-up from this - mode */ +#define DEEPSLEEP_MODE 1 /* minimal power consumption, can't wake-up from this mode */ #define SLEEP_MODE 2 /* standard sleep mode */ #define SLEEP_ACK_CMD 0xF7 /* acknowledge of the sleep mode command */ /* 1st parameter: acknowledge of tuxcore */ @@ -167,7 +168,7 @@ /* send sensors status of the audio CPU to the core CPU */ #define SEND_AUDIOSENSORS_CMD 0xF0 -/* send sensors status of the audio CPU to the computer */ +/* send the playback status */ #define STATUS_SENSORS1_CMD 0xC1 /* 1st parameter: switches and status from the audio CPU * .0: left wing push button @@ -188,9 +189,17 @@ #define STATUS_RF_MK 0x20 #define STATUS_VCC_MK 0x20 #define STATUS_MUTE_MK 0x80 -/* 2nd parameter: microphone level */ -/* 3rd parameter: battery level */ +/* 2nd parameter: sound played from the flash + * 3rd parameter: audio activity + * .0: True if a sound is played from the flash memory, TTS or streaming. + */ +/* send the programming state from the audio CPU */ +#define STATUS_FLASH_PROG_CMD 0xCD +/* 1st parameter: The current state (see flash.h) + * 2nd parameter: The size of the last sound (1 = 4kB) + */ + #define STATUS_LIGHT_CMD 0xC2 /* 1st parameter: light level high byte */ /* 2nd parameter: light level low byte */ |