rendered paste bodytest_queue.c
/***************************************************************************
* __________ __ ___.
* Open \______ \ ____ ____ | | _\_ |__ _______ ___
* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
* \/ \/ \/ \/ \/
* $Id$
*
* Copyright (C) 2007 Michael Sevakis
*
* All files in this archive are subject to the GNU General Public License.
* See the file COPYING in the source tree root for full license agreement.
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
* KIND, either express or implied.
*
****************************************************************************/
#include "plugin.h"
#include "oldmenuapi.h"
PLUGIN_HEADER
PLUGIN_IRAM_DECLARE
static struct plugin_api *rb NOCACHEBSS_ATTR;
static struct event_queue cop_queue NOCACHEBSS_ATTR;
static struct queue_sender_list cop_queue_senders NOCACHEBSS_ATTR;
static int cop_thread_stack[2*DEFAULT_STACK_SIZE/sizeof(int)];
#ifdef TOSHIBA_GIGABEAT_F
#define invalidate_icache()
#define flush_icache()
#endif
#if CONFIG_KEYPAD == IRIVER_H100_PAD
#define TEST_QUEUE_QUIT BUTTON_OFF
#elif CONFIG_KEYPAD == SANSA_E200_PAD
#define TEST_QUEUE_QUIT BUTTON_POWER
#elif CONFIG_KEYPAD == GIGABEAT_PAD
#define TEST_QUEUE_QUIT BUTTON_POWER
#else
#error Unsupported Keypad
#endif
void cop_thread(void)
{
struct queue_event ev;
int last_i = 0;
while (1)
{
rb->queue_wait_w_tmo(&cop_queue, &ev, 3600*HZ);
switch (ev.id)
{
case 0:
/* each data should be one greater than the last */
if (ev.data != last_i + 1)
rb->queue_reply(&cop_queue, -1);
// else
// rb->splash(0, "%ld", ev.data);
last_i = ev.data;
break;
case 777:
/* commanded to exit - reply explicitly since we won't
wait here again */
rb->queue_reply(&cop_queue, 0);
invalidate_icache();
return;
default:
rb->queue_reply(&cop_queue, -2);
}
}
}
enum plugin_status plugin_start(struct plugin_api *api, void *parameter)
{
int i, ret = 0;
PLUGIN_IRAM_INIT(api);
rb = api;
i = 0;
rb->queue_init(&cop_queue, false);
rb->queue_enable_queue_send(&cop_queue, &cop_queue_senders);
flush_icache();
rb->create_thread(cop_thread, cop_thread_stack, sizeof(cop_thread_stack),
0, "cop_thread", PRIORITY_SYSTEM IF_COP(, CPU));
rb->lcd_setfont(FONT_SYSFIXED);
rb->lcd_puts(0, 0, "Test running...");
rb->lcd_update();
i = 0;
long tick = *rb->current_tick + 10*HZ;
int loops = 0;
/* loop around sending last data+1 */
while (TIME_BEFORE(*rb->current_tick, tick)) //rb->button_get(false) != TEST_QUEUE_QUIT)
{
ret = rb->queue_send(&cop_queue, 0, ++i);
if (ret == -1)
{
rb->lcd_clear_display();
rb->lcd_puts(0, 0, "Data miss");
break;
}
else if (ret == -2)
{
rb->lcd_clear_display();
rb->lcd_puts(0, 0, "Unexpected message");
break;
}
loops++;
}
rb->splash(HZ*3, "%d.%d", loops/10, loops%10);
if (ret < 0)
{
while (rb->button_get(true) == BUTTON_NONE);
}
/* tell cop thread to exit */
rb->queue_send(&cop_queue, 777, 0);
/* give it time to leave plugin code */
rb->sleep(HZ/10);
invalidate_icache();
return PLUGIN_OK;
(void)parameter;
}
test_cache.c
/***************************************************************************
* __________ __ ___.
* Open \______ \ ____ ____ | | _\_ |__ _______ ___
* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
* \/ \/ \/ \/ \/
* $Id$
*
* Copyright (C) 2007 Michael Sevakis
*
* All files in this archive are subject to the GNU General Public License.
* See the file COPYING in the source tree root for full license agreement.
*
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
* KIND, either express or implied.
*
****************************************************************************/
#include "plugin.h"
#include "oldmenuapi.h"
PLUGIN_HEADER
PLUGIN_IRAM_DECLARE
static struct plugin_api *rb NOCACHEBSS_ATTR;
static struct event_queue cop_queue NOCACHEBSS_ATTR;
static struct queue_sender_list cop_queue_senders NOCACHEBSS_ATTR;
static int cop_thread_stack[DEFAULT_STACK_SIZE/sizeof(int)];
static uint8_t cached_buf[16];
static uint8_t uncached_buf[16] NOCACHEBSS_ATTR;
static uint8_t cop_buf[16] NOCACHEBSS_ATTR;
#ifdef TOSHIBA_GIGABEAT_F
#define invalidate_icache()
#define flush_icache()
#endif
void cop_thread(void)
{
int i;
struct queue_event ev;
while (1)
{
invalidate_icache();
rb->queue_wait_w_tmo(&cop_queue, &ev, 3600*HZ);
switch (ev.id)
{
case 0:
/* avoid memcpy/memcmp to help localize code execution */
for (i = 0; i < 16; i++)
{
if (cached_buf[i] != uncached_buf[i])
{
for (i = 0; i < 16; i++)
{
/* copy what COP sees to an uncacheable buffer */
cop_buf[i] = cached_buf[i];
}
/* return failure */
rb->queue_reply(&cop_queue, -1);
break;
}
}
break;
case 666:
/* commanded to exit - reply explicitly since we won't
wait here again */
rb->queue_reply(&cop_queue, 0);
flush_icache();
return;
}
}
}
enum plugin_status plugin_start(struct plugin_api *api, void *parameter)
{
int ret;
unsigned char buf[64];
unsigned int rand;
unsigned int test_num = 0;
PLUGIN_IRAM_INIT(api);
rb = api;
rand = *rb->current_tick;
ret = 0;
rb->queue_init(&cop_queue, false);
rb->queue_enable_queue_send(&cop_queue, &cop_queue_senders);
flush_icache();
rb->create_thread(cop_thread, cop_thread_stack, sizeof(cop_thread_stack),
0, "cop_thread", PRIORITY_SYSTEM IF_COP(, COP));
rb->lcd_setfont(FONT_SYSFIXED);
rb->lcd_puts(0, 0, "Test running...");
rb->lcd_puts(0, 1, "Will dump upon byte mismatch.");
rb->lcd_update();
while (rb->button_get(false) == BUTTON_NONE)
{
int i;
test_num++;
for (i = 0; i < 16; i++)
{
unsigned val;
rand = rand*0x0019660dL + 0x3c6ef35fL;
val = rand & 0xff;
cached_buf[i] = val;
uncached_buf[i] = val;
}
//rb->lcd_update();
invalidate_icache();
ret = rb->queue_send(&cop_queue, 0, 0);
if (ret < 0)
break;
rb->yield();
}
if (ret < 0)
{
int i, x, y = 0;
rb->lcd_clear_display();
rb->snprintf(buf, 64, "Test #%u failed:", test_num);
rb->lcd_puts(0, y++, buf);
rb->lcd_puts(0, y, "cached_buf");
rb->lcd_puts(0, y+3, "uncached_buf");
rb->lcd_puts(0, y+6, "cop_buf");
for (i = 0, x = 0, y = 2; i < 16; i++, x += 3)
{
if (i % 8 == 0)
x = 0, y++;
/* show bytes in the shared, cached buffer */
rb->snprintf(buf, 64, "%02X ", cached_buf[i]);
rb->lcd_puts(x, y+0, buf);
/* show bytes in the shared, uncached buffer */
rb->snprintf(buf, 64, "%02X ", uncached_buf[i]);
rb->lcd_puts(x, y+3, buf);
/* show bytes that cop saw in the shared, cached buffer */
rb->snprintf(buf, 64, "%02X ", cop_buf[i]);
rb->lcd_puts(x, y+6, buf);
}
rb->lcd_update();
while (rb->button_get(true) == BUTTON_NONE);
}
/* tell cop thread to exit */
rb->queue_send(&cop_queue, 666, 0);
/* give it time to leave plugin code */
rb->sleep(HZ/10);
flush_icache();
return PLUGIN_OK;
(void)parameter;
}