Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
98 changes: 76 additions & 22 deletions .github/workflows/utest_auto_run.yml
Original file line number Diff line number Diff line change
Expand Up @@ -59,14 +59,51 @@ jobs:
- "default.cfg"

include:
# only run on qemu-vexpress-a9
# run kernel utest set on all QEMU boards
- platform: { UTEST: "A9", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "A9", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "A9", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"

- platform: { UTEST: "A9-rtsmart", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "A9-rtsmart", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "A9-rtsmart", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "A9-smp", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"smp" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "A9-smp", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"smp" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "A9-smp", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"smp" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "RISCV", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "RISCV", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "RISCV", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "RISCV-rtsmart", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "RISCV-rtsmart", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "RISCV-rtsmart", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "XUANTIE-rtsmart", RTT_BSP: "bsp/xuantie/virt64/c906", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/kernel_basic.cfg"
- platform: { UTEST: "XUANTIE-rtsmart", RTT_BSP: "bsp/xuantie/virt64/c906", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/ipc.cfg"
- platform: { UTEST: "XUANTIE-rtsmart", RTT_BSP: "bsp/xuantie/virt64/c906", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "RISCV-smp", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "standard", "SMP_RUN":"smp" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "AARCH64", RTT_BSP: "bsp/qemu-virt64-aarch64", QEMU_ARCH: "aarch64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "AARCH64-rtsmart", RTT_BSP: "bsp/qemu-virt64-aarch64", QEMU_ARCH: "aarch64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "rtsmart", "SMP_RUN":"" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "AARCH64-smp", RTT_BSP: "bsp/qemu-virt64-aarch64", QEMU_ARCH: "aarch64", QEMU_MACHINE: "virt", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"smp" }
config_file: "kernel/mem.cfg"
- platform: { UTEST: "A9", RTT_BSP: "bsp/qemu-vexpress-a9", QEMU_ARCH: "arm", QEMU_MACHINE: "vexpress-a9", SD_FILE: "sd.bin", KERNEL: "standard", "SMP_RUN":"" }
config_file: "kernel/atomic_c11.cfg"
- platform: { UTEST: "RISCV", RTT_BSP: "bsp/qemu-virt64-riscv", QEMU_ARCH: "riscv64", QEMU_MACHINE: "virt", SD_FILE: "None", KERNEL: "standard", "SMP_RUN":"" }
Expand Down Expand Up @@ -273,38 +310,55 @@ jobs:

- name: Monitor qemu log
if: ${{ env.TOOLCHAIN_INSTALLED != '' && success() }}
timeout-minutes: 20
run: |
FAILURE_DETECTED=false
ERROR_LOGS=""
export FAILURE_DETECTED ERROR_LOGS

echo "=========================================================================================="
echo " || || "
echo " || Start automatic running of Utest || "
echo " VV VV "
echo "=========================================================================================="
tail -n 0 -f qemu_output_$TEST_QEMU_ARCH.log | while read line; do
echo $line
if [[ "$line" == *"[ FAILED ] [ result ]"* ]]; then
ERROR_LOGS="$ERROR_LOGS$line"$'\n'
FAILURE_DETECTED=true
fi

if [[ "$line" == *"[==========] [ utest ] finished"* ]]; then
if $FAILURE_DETECTED; then
timeout 20m bash -c '
tail -n 0 -f "qemu_output_${TEST_QEMU_ARCH}.log" | while IFS= read -r line; do
echo "$line"
if [[ "$line" == *"[ FAILED ] [ result ]"* ]]; then
ERROR_LOGS="${ERROR_LOGS}${line}"$'\''\n'\''
FAILURE_DETECTED=true
fi

if [[ "$line" == *"[==========] [ utest ] finished"* ]]; then
if [[ "$FAILURE_DETECTED" == "true" ]]; then
echo "=========================================================================================="
echo " || || "
echo " || Error: Failures detected in logs. Below are the failure details... || "
echo " VV VV "
echo "=========================================================================================="
echo "$ERROR_LOGS"
exit 1
fi
echo "=========================================================================================="
echo " || || "
echo " || Error: Failures detected in logs. Below are the failure details... || "
echo " VV VV "
echo " Successed: Utest run completed. Exiting log monitoring "
echo "=========================================================================================="
echo "$ERROR_LOGS"
exit 1
break
fi
echo "=========================================================================================="
echo " Successed: Utest run completed. Exiting log monitoring "
echo "=========================================================================================="
break
fi
done
done
'
monitor_status=$?

if [[ $monitor_status -eq 124 ]]; then
echo "=========================================================================================="
echo " || || "
echo " || Error: Utest run timed out after 20 minutes. Exiting... || "
echo " VV VV "
echo "=========================================================================================="
pkill -f "qemu-system-${TEST_QEMU_ARCH}.*${TEST_BSP_ROOT}/rtthread.bin" || true
exit 1
fi

exit $monitor_status
# # Post CI status to PR comment
# post-ci-status:
# needs: test
Expand Down
3 changes: 3 additions & 0 deletions examples/utest/configs/kernel/ipc.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,9 @@ CONFIG_RT_UTEST_SIGNAL=y
CONFIG_RT_UTEST_MUTEX=y
CONFIG_RT_UTEST_MAILBOX=y

CONFIG_RT_UTEST_COMPLETION=y
CONFIG_RT_UTEST_WORKQUEUE=y

CONFIG_RT_USING_SEMAPHORE=y
CONFIG_RT_USING_EVENT=y
CONFIG_RT_USING_MESSAGEQUEUE=y
Expand Down
2 changes: 2 additions & 0 deletions examples/utest/configs/kernel/kernel_basic.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
CONFIG_RT_CONSOLEBUF_SIZE=1024
CONFIG_RT_USING_CI_ACTION=y

CONFIG_RT_UTEST_TIMER=y
CONFIG_RT_UTEST_TC_USING_KLIBC=y
CONFIG_RT_UTEST_OBJECT=y
CONFIG_RT_UTEST_IRQ=y
CONFIG_RT_UTEST_THREAD=y
Expand Down
25 changes: 22 additions & 3 deletions src/utest/object_tc.c
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@
#define TEST_RT_NAME_MAX RT_NAME_MAX
#define OBJECT_STRESS_BATCH 24
#define OBJECT_STRESS_ROUNDS 3
#define OBJECT_THREAD_STACK_SIZE 1024

#ifndef ARRAY_SIZE
#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
Expand Down Expand Up @@ -140,6 +141,16 @@ static rt_err_t generate_unique_name(char *buf,
return -RT_ENOMEM;
}

static void object_find_test_thread_entry(void *parameter)
{
RT_UNUSED(parameter);

while (1)
{
rt_thread_mdelay(10);
}
}

static void test_object_name_handling(void)
{
struct rt_object static_obj;
Expand Down Expand Up @@ -187,6 +198,7 @@ static void test_object_find_operations(void)
rt_thread_t found_thread;
rt_object_t found;
char missing_name[] = "object.not.exists";
rt_err_t ret;

uassert_true(generate_unique_name(name, sizeof(name), "sobj", RT_Object_Class_Thread) == RT_EOK);
rt_object_init(&static_obj, RT_Object_Class_Thread, name);
Expand All @@ -197,14 +209,21 @@ static void test_object_find_operations(void)
rt_object_detach(&static_obj);

uassert_true(generate_unique_name(name, sizeof(name), "thr", RT_Object_Class_Thread) == RT_EOK);
thread = rt_thread_create(name, RT_NULL, RT_NULL, 512, RT_THREAD_PRIORITY_MAX / 2, 10);
thread = rt_thread_create(name, object_find_test_thread_entry, RT_NULL,
OBJECT_THREAD_STACK_SIZE, RT_THREAD_PRIORITY_MAX / 2, 10);
uassert_not_null(thread);
ret = rt_thread_startup(thread);
uassert_int_equal(ret, RT_EOK);
found_thread = rt_thread_find(name);
uassert_not_null(found_thread);
uassert_ptr_equal(found_thread, thread);
uassert_str_equal(found_thread->parent.name, name);
rt_thread_delete(thread);
rt_thread_mdelay(10);
ret = rt_thread_delete(thread);
uassert_int_equal(ret, RT_EOK);
for (int i = 0; i < 10 && rt_thread_find(name) != RT_NULL; i++)
{
rt_thread_mdelay(100);
}
uassert_null(rt_thread_find(name));

#ifdef RT_USING_DEVICE
Expand Down
1 change: 0 additions & 1 deletion src/utest/perf/thread_mbox_tc.c
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,6 @@ static void perf_thread_mbox1(void *parameter)
static void perf_thread_mbox2(void *parameter)
{
rt_perf_t *perf = (rt_perf_t *)parameter;
rt_err_t ret = RT_EOK;
while (1)
{
if (perf->count >= RT_UTEST_SYS_PERF_TC_COUNT)
Expand Down
39 changes: 26 additions & 13 deletions src/utest/thread_overflow_tc.c
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
#include "utest.h"

#define UTEST_NAME "thread_overflow_tc"
#define TEST_STACK_SIZE 512
#define TEST_STACK_SIZE UTEST_THR_STACK_SIZE

/* Test thread stack overflow */
static rt_thread_t test_thread = RT_NULL;
Expand All @@ -34,7 +34,7 @@ static rt_err_t stack_overflow_hook(struct rt_thread *thread)
static void stack_usage_test(void)
{
rt_thread_t current_thread;
rt_uint32_t total_stack, used_stack;
rt_uintptr_t total_stack, used_stack;

current_thread = rt_thread_self();
uassert_not_null(current_thread);
Expand All @@ -49,10 +49,10 @@ static void stack_usage_test(void)

#ifdef ARCH_CPU_STACK_GROWS_UPWARD
/* For upward growing stacks */
used_stack = (rt_uint32_t)current_thread->sp - (rt_uint32_t)current_thread->stack_addr;
used_stack = (rt_uintptr_t)current_thread->sp - (rt_uintptr_t)current_thread->stack_addr;
#else
/* For downward growing stacks (most common) */
used_stack = (rt_uint32_t)current_thread->stack_addr + total_stack - (rt_uint32_t)current_thread->sp;
used_stack = (rt_uintptr_t)current_thread->stack_addr + total_stack - (rt_uintptr_t)current_thread->sp;
#endif

rt_kprintf("Used stack: %d bytes (%d%%)\n",
Expand Down Expand Up @@ -142,11 +142,11 @@ static void stack_overflow_hook_test(void)
/* Fake thread test entry function */
static void fake_thread_entry(void *parameter)
{
/* This function should never actually run */
rt_kprintf("Fake thread is running - this should not happen!\n");
RT_UNUSED(parameter);

while (1)
{
rt_thread_mdelay(1000);
rt_thread_mdelay(100);
}
}

Expand Down Expand Up @@ -178,14 +178,18 @@ static void fake_thread_stack_overflow_test(void)
}

rt_kprintf("Fake thread created successfully\n");
uassert_int_equal(rt_thread_startup(fake_thread), RT_EOK);
rt_thread_mdelay(10);

rt_kprintf("Corrupting fake thread stack with pattern 0x11...\n");
rt_memset(fake_thread->stack_addr, 0x11, fake_thread->stack_size);

/* Also corrupt the magic number area if stack checking is enabled */
rt_kprintf("Corrupting fake thread stack sentinel...\n");
#ifdef RT_USING_OVERFLOW_CHECK
/* For downward growing stacks, magic is typically at the beginning */
rt_memset(fake_thread->stack_addr, 0x11, 4); /* Corrupt first 4 bytes */
/* Only corrupt the sentinel bytes used by overflow detection. */
#ifdef ARCH_CPU_STACK_GROWS_UPWARD
rt_memset((rt_uint8_t *)fake_thread->stack_addr + fake_thread->stack_size - sizeof(rt_ubase_t),
0x11, sizeof(rt_ubase_t));
#else
rt_memset(fake_thread->stack_addr, 0x11, sizeof(rt_ubase_t));
#endif
rt_kprintf("Stack magic number area corrupted\n");
#endif

Expand All @@ -204,6 +208,11 @@ static void fake_thread_stack_overflow_test(void)
if (fake_thread != RT_NULL)
{
rt_thread_delete(fake_thread);
for (int i = 0; i < 10 && rt_thread_find("fake_thread") != RT_NULL; i++)
{
rt_thread_mdelay(10);
}
uassert_null(rt_thread_find("fake_thread"));
fake_thread = RT_NULL;
rt_kprintf("Fake thread deleted\n");
}
Expand Down Expand Up @@ -250,6 +259,10 @@ static rt_err_t utest_tc_cleanup(void)
if (fake_thread != RT_NULL)
{
rt_thread_delete(fake_thread);
for (int i = 0; i < 10 && rt_thread_find("fake_thread") != RT_NULL; i++)
{
rt_thread_mdelay(10);
}
fake_thread = RT_NULL;
}

Expand Down
Loading