Skip to content
Open
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
4 changes: 4 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ jobs:
fail-fast: false
matrix:
idf: ["v5.4", "v5.5"]
assertions: ["y", "n"]
runs-on: ubuntu-latest
container:
image: espressif/idf:${{ matrix.idf }}
Expand All @@ -38,6 +39,7 @@ jobs:
run: |
. /opt/esp/idf/export.sh
cd test
echo "CONFIG_ASSERT=${{ matrix.assertions }}" >> sdkconfig.defaults
idf.py --preview set-target linux
idf.py build
./build/boreas_test.elf
Expand All @@ -47,6 +49,7 @@ jobs:
fail-fast: false
matrix:
idf: ["v5.4", "v5.5"]
assertions: ["y", "n"]
runs-on: ubuntu-latest
container:
image: espressif/idf:${{ matrix.idf }}
Expand All @@ -59,6 +62,7 @@ jobs:
run: |
. /opt/esp/idf/export.sh
cd test
echo "CONFIG_ASSERT=${{ matrix.assertions }}" >> sdkconfig.defaults
idf.py set-target esp32s3
idf.py build

Expand Down
9 changes: 9 additions & 0 deletions components/zkernel/Kconfig
Original file line number Diff line number Diff line change
@@ -1,5 +1,14 @@
menu "Boreas Kernel (zkernel)"

config ASSERT
bool "Enable runtime assertions"
default n
help
Enable __ASSERT and __ASSERT_NO_MSG checks that log and abort
on failure. Disabled assertions do not evaluate their arguments;
do not put required side effects in assertion expressions.
Mirrors upstream Zephyr's CONFIG_ASSERT default.

config RING_BUFFER_LARGE
bool "Use 32-bit ring buffer indices"
default n
Expand Down
11 changes: 11 additions & 0 deletions components/zkernel/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -315,3 +315,14 @@ index 0 stays free for ESP-IDF internals. A compile-time `#error` backstops
the requirement (Kconfig cannot set another component's int symbol
automatically: `select` is bool-only and cross-component int defaults lose
the parse-order race).

### Runtime assertions

`CONFIG_ASSERT` controls `__ASSERT` and `__ASSERT_NO_MSG`.
It defaults to `n`, matching Zephyr.

Set `CONFIG_ASSERT=y` to enable checks that log and abort on failure.
When disabled, neither the condition nor the message is evaluated.
Required operations must therefore stay outside assertion expressions.

`BUILD_ASSERT`, `K_ASSERT`, and `k_panic()` are unaffected.
1 change: 1 addition & 0 deletions components/zkernel/include/boreas/zephyr/kernel.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
#include "freertos/semphr.h"
#include "freertos/task.h"

#include "esp_rom_sys.h"
#include "esp_timer.h"

#if CONFIG_IDF_TARGET_LINUX
Expand Down
13 changes: 11 additions & 2 deletions components/zkernel/include/boreas/zephyr/sys/__assert.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,19 @@
* Zephyr-compatible runtime assertions (upstream <zephyr/sys/__assert.h>
* spellings).
*
* Divergence: upstream compiles these out unless CONFIG_ASSERT=y
* (default n); Boreas keeps them always on -- they log and abort.
* Enabled by CONFIG_ASSERT (default n), matching upstream Zephyr.
* Disabled assertions do not evaluate the condition or message.
* NOT safe from IRAM ISR context (ESP_LOGE + abort are flash-resident).
* Use k_panic() (sys/util.h) for unrecoverable errors in ISR/IRAM
* context.
*/

#pragma once

#include "sdkconfig.h"

#ifndef __ASSERT
#if defined(CONFIG_ASSERT) && CONFIG_ASSERT
#include <stdlib.h> /* abort() */

#include "esp_log.h"
Expand All @@ -25,6 +28,12 @@
abort(); \
} \
} while (0)
#else

#define __ASSERT(cond, msg) \
do { \
} while (0)
#endif
#endif

/* Assertion with no message (upstream spelling). */
Expand Down
1 change: 1 addition & 0 deletions components/zkernel/src/k_timer.c
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ void k_timer_init(struct k_timer *timer, k_timer_expiry_t expiry_fn, k_timer_sto
};
esp_err_t err = esp_timer_create(&args, &timer->handle);
__ASSERT(err == ESP_OK, "k_timer_init: esp_timer_create failed");
(void)err;
}

void k_timer_start(struct k_timer *timer, k_timeout_t duration, k_timeout_t period)
Expand Down
1 change: 1 addition & 0 deletions test/main/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
set(test_srcs
"test_assert.c"
"test_main.c"
"test_timeout.c"
"test_slist.c"
Expand Down
49 changes: 49 additions & 0 deletions test/main/test_assert.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
/*
* SPDX-License-Identifier: Apache-2.0
* Copyright 2026 Intercreate
*/

#include "unity.h"
#include "zephyr/sys/__assert.h"

static void test_assert_disabled_arguments(void)
{
#if !defined(CONFIG_ASSERT) || !CONFIG_ASSERT
int condition_calls = 0;
int message_calls = 0;

__ASSERT(++condition_calls, (++message_calls, "disabled assertion"));
__ASSERT_NO_MSG(++condition_calls);

TEST_ASSERT_EQUAL_INT(0, condition_calls);
TEST_ASSERT_EQUAL_INT(0, message_calls);

/* A false condition must not terminate the program when disabled. */
__ASSERT(0, "must not abort");
__ASSERT_NO_MSG(0);
#else
TEST_IGNORE_MESSAGE("Requires CONFIG_ASSERT=n");
#endif
}

static void test_assert_enabled_arguments(void)
{
#if defined(CONFIG_ASSERT) && CONFIG_ASSERT
int condition_calls = 0;
int message_calls = 0;

__ASSERT(++condition_calls, (++message_calls, "unused message"));
__ASSERT_NO_MSG(++condition_calls);

TEST_ASSERT_EQUAL_INT(2, condition_calls);
TEST_ASSERT_EQUAL_INT(0, message_calls);
#else
TEST_IGNORE_MESSAGE("Requires CONFIG_ASSERT=y");
#endif
}

void test_assert_group(void)
{
RUN_TEST(test_assert_disabled_arguments);
RUN_TEST(test_assert_enabled_arguments);
}
2 changes: 2 additions & 0 deletions test/main/test_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
#include "unity.h"

/* Test group declarations -- always available */
void test_assert_group(void);
void test_timeout_group(void);
void test_slist_group(void);
void test_dlist_group(void);
Expand Down Expand Up @@ -49,6 +50,7 @@ void app_main(void)
UNITY_BEGIN();

/* Layer 0: Foundation */
test_assert_group();
test_timeout_group();
test_slist_group();
test_dlist_group();
Expand Down