summaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
authorVincent Palatin <vpalatin@chromium.org>2011-12-07 18:58:43 +0000
committerVincent Palatin <vpalatin@chromium.org>2011-12-07 19:10:02 +0000
commite24fa592d2a215d8ae67917c1d89e68cdf847a03 (patch)
tree47fbe4c55e7f4089cad7d619eded337da3bae999 /test
parent6396911897e4cd40f52636d710cee2865acf15e3 (diff)
downloadchrome-ec-e24fa592d2a215d8ae67917c1d89e68cdf847a03.tar.gz
Initial sources import 3/3
source files mainly done by Vincent. Signed-off-by: Vincent Palatin <vpalatin@chromium.org> Change-Id: Ic2d1becd400c9b4b4a14d4a243af1bdf77d9c1e2
Diffstat (limited to 'test')
-rw-r--r--test/build.mk11
-rw-r--r--test/hello.py16
-rw-r--r--test/hello.tasklist21
-rw-r--r--test/pingpong.c43
-rw-r--r--test/pingpong.py27
-rw-r--r--test/pingpong.tasklist15
-rw-r--r--test/powerdemo.c186
-rw-r--r--test/powerdemo.tasklist6
-rw-r--r--test/timer_calib.c55
-rw-r--r--test/timer_calib.py54
-rw-r--r--test/timer_calib.tasklist12
-rw-r--r--test/timer_dos.c39
-rw-r--r--test/timer_dos.py41
-rw-r--r--test/timer_dos.tasklist15
14 files changed, 541 insertions, 0 deletions
diff --git a/test/build.mk b/test/build.mk
new file mode 100644
index 0000000000..20df88c04b
--- /dev/null
+++ b/test/build.mk
@@ -0,0 +1,11 @@
+#
+# on-board test binaries build
+#
+
+test-list=hello pingpong timer_calib timer_dos
+#disable: powerdemo
+
+pingpong-objs=pingpong.o
+powerdemo-objs=powerdemo.o
+timer_calib-objs=timer_calib.o
+timer_dos-objs=timer_dos.o
diff --git a/test/hello.py b/test/hello.py
new file mode 100644
index 0000000000..861cbf0bb4
--- /dev/null
+++ b/test/hello.py
@@ -0,0 +1,16 @@
+# Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+#
+# Simple test as an example
+#
+
+def test(helper):
+ helper.wait_output("--- Chrome EC initialized! ---")
+ helper.wait_prompt()
+ helper.ec_command("version")
+ ro = helper.wait_output("RO version:\s*(?P<ro>\S+)", use_re=True)["ro"]
+ wa = helper.wait_output("RW-A version:\s*(?P<a>\S+)", use_re=True)["a"]
+ wb = helper.wait_output("RW-B version:\s*(?P<b>\S+)", use_re=True)["b"]
+ helper.trace("Version (RO/A/B) %s / %s / %s\n" % (ro, wa, wb))
+ return True # PASS !
diff --git a/test/hello.tasklist b/test/hello.tasklist
new file mode 100644
index 0000000000..8ad338a873
--- /dev/null
+++ b/test/hello.tasklist
@@ -0,0 +1,21 @@
+/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+/**
+ * List of enabled tasks in the priority order
+ *
+ * The first one has the lowest priority.
+ *
+ * For each task, use the macro TASK(n, r, d) where :
+ * 'n' in the name of the task
+ * 'r' in the main routine of the task
+ * 'd' in an opaque parameter passed to the routine at startup
+ */
+#define CONFIG_TASK_LIST \
+ TASK(BLINK, UserLedBlink, NULL) \
+ TASK(KEYSCAN, keyboard_scan_task, NULL) \
+ TASK(CONSOLE, console_task, NULL) \
+ TASK(HOSTCMD, host_command_task, NULL) \
+ TASK(I8042CMD, i8042_command_task, NULL)
diff --git a/test/pingpong.c b/test/pingpong.c
new file mode 100644
index 0000000000..18115060d3
--- /dev/null
+++ b/test/pingpong.c
@@ -0,0 +1,43 @@
+/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ * Copyright 2011 Google Inc.
+ *
+ * Tasks for scheduling test.
+ */
+
+#include "common.h"
+#include "uart.h"
+#include "task.h"
+#include "timer.h"
+
+int TaskAbc(void *data)
+{
+ char letter = (char)(unsigned)data;
+ char string[2] = {letter, '\0' };
+ task_id_t next = task_get_current() + 1;
+ if (next > TASK_ID_TESTC)
+ next = TASK_ID_TESTA;
+
+ uart_printf("\n[starting Task %c]\n", letter);
+
+ while (1) {
+ uart_puts(string);
+ uart_flush_output();
+ task_send_msg(next, TASK_ID_CURRENT, 1);
+ }
+
+ return EC_SUCCESS;
+}
+
+int TaskTick(void *data)
+{
+ uart_set_console_mode(1);
+ uart_printf("\n[starting Task T]\n");
+ /* Print T every tick */
+ while (1) {
+ /* Wait for timer interrupt message */
+ usleep(3000);
+ uart_puts("T\n");
+ }
+}
diff --git a/test/pingpong.py b/test/pingpong.py
new file mode 100644
index 0000000000..df7d4b38c5
--- /dev/null
+++ b/test/pingpong.py
@@ -0,0 +1,27 @@
+# Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+#
+# Task scheduling test
+#
+
+import time
+
+# Test during 5s
+DURATION=5
+
+def test(helper):
+ helper.wait_output("[starting Task T]")
+ helper.wait_output("[starting Task C]")
+ helper.wait_output("[starting Task B]")
+ helper.wait_output("[starting Task A]")
+ deadline = time.time() + DURATION
+ count = []
+ while time.time() < deadline:
+ sched = helper.wait_output("(?P<a>(?:ABC){3,200})T", use_re=True,
+ timeout=1)["a"]
+ count.append(len(sched) / 3)
+
+ helper.trace("IRQ count %d, cycles count min %d max %d\n" %
+ (len(count), min(count), max(count)))
+ return True # PASS !
diff --git a/test/pingpong.tasklist b/test/pingpong.tasklist
new file mode 100644
index 0000000000..1f91eb0993
--- /dev/null
+++ b/test/pingpong.tasklist
@@ -0,0 +1,15 @@
+
+/**
+ * List of enabled tasks in the priority order
+ *
+ * The first one has the lowest priority.
+ */
+#define CONFIG_TASK_LIST \
+ TASK(BLINK, UserLedBlink, NULL) \
+ TASK(CONSOLE, console_task, NULL) \
+ TASK(TESTA, TaskAbc, (void *)'A') \
+ TASK(TESTB, TaskAbc, (void *)'B') \
+ TASK(TESTC, TaskAbc, (void *)'C') \
+ TASK(TESTT, TaskTick, (void *)'T')\
+ TASK(HOSTCMD, host_command_task, NULL) \
+ TASK(I8042CMD, i8042_command_task, NULL)
diff --git a/test/powerdemo.c b/test/powerdemo.c
new file mode 100644
index 0000000000..9074f3505b
--- /dev/null
+++ b/test/powerdemo.c
@@ -0,0 +1,186 @@
+/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ */
+
+/* Power state machine demo module for Chrome EC */
+
+#include "board.h"
+#include "powerdemo.h"
+#include "task.h"
+#include "timer.h"
+#include "uart.h"
+#include "registers.h"
+
+
+#define US_PER_SECOND 1000000
+/* Divider to get microsecond for the clock */
+#define CLOCKSOURCE_DIVIDER (CPU_CLOCK/US_PER_SECOND)
+
+static volatile enum {
+ POWER_STATE_IDLE = 0, /* Idle */
+ POWER_STATE_DOWN1, /* Assert output for 1ms */
+ POWER_STATE_UP1, /* Deassert output for 1ms */
+ POWER_STATE_DOWN10, /* Assert output for 10ms */
+ POWER_STATE_UP5, /* Deassert output for 5ms */
+ POWER_STATE_DOWN15, /* Assert output for 15ms */
+ POWER_STATE_WAIT, /* Wait for button to be released */
+ POWER_STATE_DOWN2 /* Assert output for 2ms */
+} state = POWER_STATE_IDLE;
+
+
+/* Stops the timer. */
+static void __stop_timer(void)
+{
+ /* Disable timer A */
+ LM4_TIMER_CTL(W1) &= ~0x01;
+ /* Clear any pending interrupts */
+ LM4_TIMER_ICR(W1) = LM4_TIMER_RIS(W1);
+}
+
+
+/* Starts the timer with the specified delay. If the timer is already
+ * started, resets it. */
+static void __start_timer(int usec)
+{
+ /* Stop the timer, if it was started */
+ __stop_timer();
+ /* Set the delay, counting function overhead */
+ LM4_TIMER_TAILR(W1) = usec;
+ /* Start timer A */
+ LM4_TIMER_CTL(W1) |= 0x01;
+}
+
+
+static void __set_state(int new_state, int pin_value, int timeout)
+{
+ LM4_GPIO_DATA_BITS(D, 0x08 << 2) = (pin_value ? 0x08 : 0);
+ if (timeout)
+ __start_timer(timeout);
+ else
+ __stop_timer();
+ state = new_state;
+}
+
+
+int power_demo_init(void)
+{
+ volatile uint32_t scratch __attribute__((unused));
+
+ /* Set up TIMER1 as our state timer */
+ /* Enable TIMER1 clock */
+ LM4_SYSTEM_RCGCWTIMER |= 0x02;
+ /* wait 3 clock cycles before using the module */
+ scratch = LM4_SYSTEM_RCGCWTIMER;
+ /* Ensure timer is disabled : TAEN = TBEN = 0 */
+ LM4_TIMER_CTL(W1) &= ~0x101;
+ /* 32-bit timer mode */
+ LM4_TIMER_CFG(W1) = 4;
+ /* Set the prescaler to increment every microsecond */
+ LM4_TIMER_TAPR(W1) = CLOCKSOURCE_DIVIDER;
+ /* One-shot, counting down */
+ LM4_TIMER_TAMR(W1) = 0x01;
+ /* Set overflow interrupt */
+ LM4_TIMER_IMR(W1) = 0x1;
+
+ /* Enable clock to GPIO module D */
+ LM4_SYSTEM_RCGCGPIO |= 0x0008;
+
+ /* Clear GPIOAFSEL and enable digital function for pins 0-3 */
+ LM4_GPIO_AFSEL(D) &= ~0x0f;
+ LM4_GPIO_DEN(D) |= 0x0f;
+
+ /* Set pins 0-2 as input, pin 3 as output */
+ LM4_GPIO_DIR(D) = (LM4_GPIO_DIR(D) & ~0x0f) | 0x08;
+
+ /* Set pin 0 to edge-sensitive, both edges, pull-up */
+ LM4_GPIO_IS(D) &= ~0x01;
+ LM4_GPIO_IBE(D) |= 0x01;
+ LM4_GPIO_PUR(D) |= 0x01;
+
+ /* Move to idle state */
+ __set_state(POWER_STATE_IDLE, 1, 0);
+
+ /* Enable interrupt on pin 0 */
+ LM4_GPIO_IM(D) |= 0x01;
+
+ return EC_SUCCESS;
+}
+
+
+/* GPIO interrupt handler */
+static void __gpio_d_interrupt(void)
+{
+ uint32_t mis = LM4_GPIO_MIS(D);
+
+ /* Clear the interrupt bits we're handling */
+ LM4_GPIO_ICR(D) = mis;
+
+ /* Handle edges */
+ if (mis & 0x01) {
+ if (LM4_GPIO_DATA_BITS(D, 0x01 << 2)) {
+ if (state == POWER_STATE_WAIT)
+ __set_state(POWER_STATE_DOWN2, 0, 2000 - 28);
+ } else {
+ if (state == POWER_STATE_IDLE)
+ __set_state(POWER_STATE_DOWN1, 0, 1000 - 28);
+ }
+ }
+}
+
+DECLARE_IRQ(3, __gpio_d_interrupt, 1);
+
+
+/* Timer interrupt handler */
+static void __timer_w1_interrupt(void)
+{
+ uint32_t mis = LM4_TIMER_RIS(W1);
+ /* Clear the interrupt reasons we're handling */
+ LM4_TIMER_ICR(W1) = mis;
+
+ /* Transition to next state */
+ switch (state) {
+ case POWER_STATE_IDLE:
+ case POWER_STATE_WAIT:
+ /* Ignore timer events when waiting for GPIO edges */
+ break;
+ case POWER_STATE_DOWN1:
+ __set_state(POWER_STATE_UP1, 1, 1000 - 28);
+ break;
+ case POWER_STATE_UP1:
+ __set_state(POWER_STATE_DOWN10, 0, 10000 - 228);
+ break;
+ case POWER_STATE_DOWN10:
+ __set_state(POWER_STATE_UP5, 1, 5000 - 128);
+ break;
+ case POWER_STATE_UP5:
+ __set_state(POWER_STATE_DOWN15, 0, 15000 - 328);
+ break;
+ case POWER_STATE_DOWN15:
+ if (LM4_GPIO_DATA_BITS(D, 0x01 << 2)) {
+ /* Button has already been released; go straight to
+ * idle */
+ __set_state(POWER_STATE_IDLE, 1, 0);
+ } else {
+ /* Wait for button release */
+ __set_state(POWER_STATE_WAIT, 1, 0);
+ }
+ break;
+ case POWER_STATE_DOWN2:
+ __set_state(POWER_STATE_IDLE, 1, 0);
+ break;
+ }
+}
+
+DECLARE_IRQ(96, __timer_w1_interrupt, 1);
+
+int power_demo_task(void)
+{
+ /* Initialize the peripherals */
+ power_demo_init();
+
+ /* suspend this task forever */
+ task_wait_msg(-1);
+
+ return EC_SUCCESS;
+}
diff --git a/test/powerdemo.tasklist b/test/powerdemo.tasklist
new file mode 100644
index 0000000000..60c77a8285
--- /dev/null
+++ b/test/powerdemo.tasklist
@@ -0,0 +1,6 @@
+
+#define CONFIG_TASK_LIST \
+ TASK(CONSOLE, console_task, NULL) \
+ TASK(HOSTCMD, host_command_task, NULL) \
+ TASK(I8042CMD, i8042_command_task, NULL) \
+ TASK(POWERDEMO, power_demo_task, NULL)
diff --git a/test/timer_calib.c b/test/timer_calib.c
new file mode 100644
index 0000000000..1169491c86
--- /dev/null
+++ b/test/timer_calib.c
@@ -0,0 +1,55 @@
+/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ * Copyright 2011 Google Inc.
+ *
+ * Tasks for scheduling test.
+ */
+
+#include "common.h"
+#include "uart.h"
+#include "task.h"
+#include "timer.h"
+
+uint32_t difftime(timestamp_t t0, timestamp_t t1)
+{
+ return (uint32_t)(t1.val-t0.val);
+}
+
+int timer_calib_task(void *data)
+{
+ timestamp_t t0, t1;
+ unsigned d;
+
+ uart_printf("\n=== Timer calibration ===\n");
+
+ t0 = get_time();
+ t1 = get_time();
+ uart_printf("- back-to-back get_time : %d us\n", difftime(t0, t1));
+
+ /* Sleep for 5 seconds */
+ uart_printf("- sleep 1s :\n ");
+ uart_flush_output();
+ uart_printf("Go...");
+ t0 = get_time();
+ usleep(1000000);
+ t1 = get_time();
+ uart_printf("done. delay = %d us\n", difftime(t0, t1));
+
+ /* try small usleep */
+ uart_printf("- short sleep :\n");
+ uart_flush_output();
+ for (d=128 ; d > 0; d = d / 2) {
+ t0 = get_time();
+ usleep(d);
+ t1 = get_time();
+ uart_printf(" %d us => %d us\n", d, difftime(t0, t1));
+ uart_flush_output();
+ }
+
+ uart_printf("Done.\n");
+ /* sleep forever */
+ task_wait_msg(-1);
+
+ return EC_SUCCESS;
+}
diff --git a/test/timer_calib.py b/test/timer_calib.py
new file mode 100644
index 0000000000..d62e9f7634
--- /dev/null
+++ b/test/timer_calib.py
@@ -0,0 +1,54 @@
+# Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+#
+# Check timers behavior
+#
+
+import time
+
+def one_pass(helper):
+ helper.wait_output("=== Timer calibration ===")
+ res = helper.wait_output("back-to-back get_time : (?P<lat>[0-9]+) us",
+ use_re=True)["lat"]
+ minlat = int(res)
+ helper.trace("get_time latency %d us\n" % minlat)
+
+ helper.wait_output("sleep 1s")
+ t0 = time.time()
+ second = helper.wait_output("done. delay = (?P<second>[0-9]+) us",
+ use_re=True)["second"]
+ t1 = time.time()
+ secondreal = t1 - t0
+ secondlat = int(second) - 1000000
+ helper.trace("1s timer latency %d us / real time %f s\n" % (secondlat,
+ secondreal))
+
+
+ us = {}
+ for pow2 in range(7):
+ delay = 1 << (7-pow2)
+ us[delay] = helper.wait_output("%d us => (?P<us>[0-9]+) us" % delay,
+ use_re=True)["us"]
+ helper.wait_output("Done.")
+
+ return minlat, secondlat, secondreal
+
+
+def test(helper):
+ one_pass(helper)
+
+ helper.ec_command("reboot")
+ helper.wait_output("--- Chrome EC initialized! ---")
+
+ # get the timing results on the second pass
+ # to avoid binary translation overhead
+ minlat, secondlat, secondreal = one_pass(helper)
+
+ # check that the timings somewhat make sense
+ if minlat > 220 or secondlat > 500 or abs(secondreal-1.0) > 0.200:
+ helper.fail("imprecise timings " +
+ "(get_time %d us sleep %d us / real time %.3f s)" %
+ (minlat, secondlat, secondreal))
+
+ return True # PASS !
diff --git a/test/timer_calib.tasklist b/test/timer_calib.tasklist
new file mode 100644
index 0000000000..d5f529188c
--- /dev/null
+++ b/test/timer_calib.tasklist
@@ -0,0 +1,12 @@
+
+/**
+ * List of enabled tasks in the priority order
+ *
+ * The first one has the lowest priority.
+ */
+#define CONFIG_TASK_LIST \
+ TASK(BLINK, UserLedBlink, NULL) \
+ TASK(TESTTMR, timer_calib_task, (void *)'T')\
+ TASK(CONSOLE, console_task, NULL) \
+ TASK(HOSTCMD, host_command_task, NULL) \
+ TASK(I8042CMD, i8042_command_task, NULL)
diff --git a/test/timer_dos.c b/test/timer_dos.c
new file mode 100644
index 0000000000..b0c37a4eaf
--- /dev/null
+++ b/test/timer_dos.c
@@ -0,0 +1,39 @@
+/* Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+ * Use of this source code is governed by a BSD-style license that can be
+ * found in the LICENSE file.
+ * Copyright 2011 Google Inc.
+ *
+ * Tasks for timer test.
+ */
+
+#include "common.h"
+#include "uart.h"
+#include "task.h"
+#include "timer.h"
+
+/* Linear congruential pseudo random number generator*/
+static uint32_t prng(uint32_t x)
+{
+ return 22695477 * x + 1;
+}
+
+/* period between 500us and 128ms */
+#define PERIOD_US(num) (((num % 256) + 1) * 500)
+
+int TaskTimer(void *seed)
+{
+ uint32_t num = (uint32_t)seed;
+ task_id_t id = task_get_current();
+
+ uart_printf("\n[Timer task %d]\n", id);
+
+ while (1) {
+ /* Wait for a "random" period */
+ task_wait_msg(PERIOD_US(num));
+ uart_printf("%01d\n", id);
+ /* next pseudo random delay */
+ num = prng(num);
+ }
+
+ return EC_SUCCESS;
+}
diff --git a/test/timer_dos.py b/test/timer_dos.py
new file mode 100644
index 0000000000..86d9b7ab49
--- /dev/null
+++ b/test/timer_dos.py
@@ -0,0 +1,41 @@
+# Copyright (c) 2011 The Chromium OS Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+#
+# Timers test
+#
+
+import time
+
+# Test during 5s
+DURATION=5
+
+# Linear congruential pseudo random number generator*/
+def prng(x):
+ return (22695477 * x + 1) & 0xffffffff
+
+# period between 500us and 128ms
+def period_us(num):
+ return (((num % 256) + 1) * 500)
+
+# build the same pseudo random sequence as the target
+def build_sequence():
+ #TODO
+ return []
+
+def test(helper):
+ helper.wait_output("[Timer task ")
+ deadline = time.time() + DURATION
+ seq = []
+ while time.time() < deadline:
+ tmr = helper.wait_output("(?P<t>[0-9])", use_re=True,
+ timeout=1)["t"]
+ seq.append(tmr)
+
+ # Check the results
+ model = build_sequence()
+ #TODO
+
+ helper.trace("Got %d timer IRQ\n" % len(seq))
+
+ return True # PASS !
diff --git a/test/timer_dos.tasklist b/test/timer_dos.tasklist
new file mode 100644
index 0000000000..483e497e7b
--- /dev/null
+++ b/test/timer_dos.tasklist
@@ -0,0 +1,15 @@
+
+/**
+ * List of enabled tasks in the priority order
+ *
+ * The first one has the lowest priority.
+ */
+#define CONFIG_TASK_LIST \
+ TASK(BLINK, UserLedBlink, NULL) \
+ TASK(CONSOLE, console_task, NULL) \
+ TASK(TMRA, TaskTimer, (void *)1234) \
+ TASK(TMRB, TaskTimer, (void *)5678) \
+ TASK(TMRC, TaskTimer, (void *)8462) \
+ TASK(TMRD, TaskTimer, (void *)3719) \
+ TASK(HOSTCMD, host_command_task, NULL)\
+ TASK(I8042CMD, i8042_command_task, NULL)