feat: add GPIO V2 support and related tests

- Updated  to include  for testing.
- Modified  to include GPIO header and added tests for GPIO functionality.
- Created a new testbench  for GPIO V2, covering register and pad-control contracts.
- Removed obsolete  and its associated test.
- Updated  to include GPIO admin base routing.
- Added a new Python test  for GPIO V2 register and pad-control contract.
- Removed  as its functionality is now covered in .
- Updated memory map tests to ensure GPIO admin base is correctly referenced.
- Adjusted formal filelist generation to reflect changes in GPIO handling.
- Enhanced SOC topology tests to include GPIO interrupt handling.
This commit is contained in:
maksyuki committed 2026-08-08 17:59:02 +08:00
1 parent 4b40dbf262
commit d517ce0fea
53 files changed
+2512 -1200

No files matched your search

+57 -64
View File
@@ -3,6 +3,7 @@
#include <retrosoc/core/status.h>
#include <retrosoc/core/wait.h>
#include <retrosoc/hal/gpio.h>
#include <retrosoc/hal/lcd.h>
#include <retrosoc/hal/spisd.h>
#include <retrosoc/hal/timer.h>
@@ -24,17 +25,12 @@ unsigned long long __umoddi3(unsigned long long dividend, unsigned long long div
static uint8_t storage[32];
static uint32_t image_call_count;
void putch(char ch)
{
void putch(char ch) {
(void)ch;
}
void lcd_fill_image(uint16_t x_start,
uint16_t y_start,
uint16_t x_end,
uint16_t y_end,
uint32_t *data)
{
void lcd_fill_image(uint16_t x_start, uint16_t y_start, uint16_t x_end, uint16_t y_end,
uint32_t *data) {
(void)x_start;
(void)y_start;
(void)x_end;
@@ -43,8 +39,7 @@ void lcd_fill_image(uint16_t x_start,
++image_call_count;
}
rs_status_t rs_spisd_read_bytes(void *buffer, size_t byte_count, uintptr_t address)
{
rs_status_t rs_spisd_read_bytes(void *buffer, size_t byte_count, uintptr_t address) {
size_t offset;
if ((buffer == NULL) || (address < TEST_STORAGE_ADDRESS)) {
@@ -60,11 +55,8 @@ rs_status_t rs_spisd_read_bytes(void *buffer, size_t byte_count, uintptr_t addre
return RS_OK;
}
static rs_status_t test_reader_read(void *context,
uint32_t offset,
void *buffer,
size_t byte_count)
{
static rs_status_t test_reader_read(void *context, uint32_t offset, void *buffer,
size_t byte_count) {
const uint8_t *bytes = context;
if ((bytes == NULL) || (buffer == NULL)) {
@@ -76,8 +68,7 @@ static rs_status_t test_reader_read(void *context,
return RS_OK;
}
static int test_string_helpers(void)
{
static int test_string_helpers(void) {
char buffer[8] = {'x', '\0'};
int32_t value;
@@ -87,12 +78,10 @@ static int test_string_helpers(void)
if (strncmp("left", "right", 0U) != 0) {
return 2;
}
if (rs_strlcpy(buffer, "abcdefghi", sizeof(buffer)) != 9U ||
strcmp(buffer, "abcdefg") != 0) {
if (rs_strlcpy(buffer, "abcdefghi", sizeof(buffer)) != 9U || strcmp(buffer, "abcdefg") != 0) {
return 3;
}
if (rs_strlcat(buffer, "x", sizeof(buffer)) != 8U ||
strcmp(buffer, "abcdefg") != 0) {
if (rs_strlcat(buffer, "x", sizeof(buffer)) != 8U || strcmp(buffer, "abcdefg") != 0) {
return 4;
}
if (rs_strtoi32("-2147483648", &value) != RS_OK || value != INT32_MIN ||
@@ -103,12 +92,11 @@ static int test_string_helpers(void)
return 0;
}
static int test_formatter(void)
{
static int test_formatter(void) {
char buffer[32];
if (rs_snprintf(buffer, sizeof(buffer), "%#08x:%lld:%zu", 0x2AU, -42LL,
(size_t)7U) != 14 || strcmp(buffer, "0x00002a:-42:7") != 0) {
if (rs_snprintf(buffer, sizeof(buffer), "%#08x:%lld:%zu", 0x2AU, -42LL, (size_t)7U) != 14 ||
strcmp(buffer, "0x00002a:-42:7") != 0) {
return 1;
}
if (rs_snprintf(buffer, 4U, "abcdef") != 6 || strcmp(buffer, "abc") != 0) {
@@ -124,29 +112,25 @@ static int test_formatter(void)
return 0;
}
static int test_compiler_helpers(void)
{
static int test_compiler_helpers(void) {
if ((__clzsi2(0U) != 32) || (__clzsi2(1U) != 31) || (__ffssi2(0U) != 0) ||
(__ffssi2(1U) != 1) || (__ffssi2(0x10U) != 5)) {
return 1;
}
if ((__udivdi3(UINT64_MAX, 3U) != 6148914691236517205ULL) ||
(__umoddi3(UINT64_MAX, 3U) != 0U) ||
(__udivdi3(UINT64_MAX, UINT64_MAX) != 1U) ||
(__umoddi3(UINT64_MAX, 3U) != 0U) || (__udivdi3(UINT64_MAX, UINT64_MAX) != 1U) ||
(__umoddi3(100U, 7U) != 2U) || (__divdi3(-100LL, 7LL) != -14LL)) {
return 2;
}
return 0;
}
static int test_wait_helper(void)
{
static int test_wait_helper(void) {
volatile uint32_t value = 0x30U;
if (rs_wait_mask(&value, 0x30U, 0x30U, 1U) != RS_OK ||
rs_wait_mask(&value, 0x40U, 0x40U, 1U) != RS_ETIMEOUT ||
rs_wait_mask(NULL, 1U, 1U, 1U) != RS_EINVAL ||
rs_wait_value(&value, 0x30U, 1U) != RS_OK ||
rs_wait_mask(NULL, 1U, 1U, 1U) != RS_EINVAL || rs_wait_value(&value, 0x30U, 1U) != RS_OK ||
rs_wait_not_value(&value, 0U, 1U) != RS_OK ||
rs_wait_not_value(&value, 0x30U, 1U) != RS_ETIMEOUT) {
return 1;
@@ -154,8 +138,7 @@ static int test_wait_helper(void)
return 0;
}
static int test_ws2812_helpers(void)
{
static int test_ws2812_helpers(void) {
const rs_ws2812_config_t config = {
72000000U,
RS_WS2812_DEFAULT_BIT_PERIOD_NS,
@@ -168,9 +151,9 @@ static int test_ws2812_helpers(void)
rs_ws2812_timing_t timing;
if ((rs_ws2812_pack_grb(0x12U, 0x34U, 0x56U) != UINT32_C(0x341256)) ||
(rs_ws2812_timing_from_ns(&config, &timing) != RS_OK) ||
(timing.bit_cycles != 90U) || (timing.t0h_cycles != 25U) ||
(timing.t1h_cycles != 50U) || (timing.reset_cycles != 21600U)) {
(rs_ws2812_timing_from_ns(&config, &timing) != RS_OK) || (timing.bit_cycles != 90U) ||
(timing.t0h_cycles != 25U) || (timing.t1h_cycles != 50U) ||
(timing.reset_cycles != 21600U)) {
return 1;
}
invalid.t0h_ns = invalid.t1h_ns;
@@ -187,16 +170,15 @@ static int test_ws2812_helpers(void)
return 0;
}
static int test_timer_helpers(void)
{
static int test_timer_helpers(void) {
rs_timer_period_t period;
if ((rs_timer_period_from_ms(72000000U, 1U, &period) != RS_OK) ||
(period.prescale != 0U) || (period.load != 71999U)) {
if ((rs_timer_period_from_ms(72000000U, 1U, &period) != RS_OK) || (period.prescale != 0U) ||
(period.load != 71999U)) {
return 1;
}
if ((rs_timer_period_from_ms(72000000U, 1000U, &period) != RS_OK) ||
(period.prescale != 0U) || (period.load != 71999999U)) {
if ((rs_timer_period_from_ms(72000000U, 1000U, &period) != RS_OK) || (period.prescale != 0U) ||
(period.load != 71999999U)) {
return 2;
}
if ((rs_timer_period_from_ms(0U, 1U, &period) != RS_EINVAL) ||
@@ -208,13 +190,32 @@ static int test_timer_helpers(void)
return 0;
}
static int test_wav_parser(void)
{
static int test_gpio_helpers(void) {
rs_gpio_filter_timing_t timing;
if ((rs_gpio_filter_timing_from_us(72000000U, 2U, 3U, &timing) != RS_OK) ||
(timing.divider != 143U) || (timing.stable_samples != 3U)) {
return 1;
}
if ((rs_gpio_filter_timing_from_us(1U, 1U, 1U, &timing) != RS_OK) || (timing.divider != 0U)) {
return 2;
}
if ((rs_gpio_filter_timing_from_us(0U, 1U, 1U, &timing) != RS_EINVAL) ||
(rs_gpio_filter_timing_from_us(72000000U, 0U, 1U, &timing) != RS_EINVAL) ||
(rs_gpio_filter_timing_from_us(72000000U, 2U, 0U, &timing) != RS_EINVAL) ||
(rs_gpio_filter_timing_from_us(72000000U, 2U, 16U, &timing) != RS_EINVAL) ||
(rs_gpio_filter_timing_from_us(72000000U, 1000U, 3U, &timing) != RS_EINVAL) ||
(rs_gpio_filter_timing_from_us(72000000U, 2U, 3U, NULL) != RS_EINVAL)) {
return 3;
}
return 0;
}
static int test_wav_parser(void) {
static const uint8_t wav[] = {
'R', 'I', 'F', 'F', 40U, 0U, 0U, 0U, 'W', 'A', 'V', 'E',
'f', 'm', 't', ' ', 16U, 0U, 0U, 0U, 1U, 0U, 1U, 0U,
0x40U, 0x1FU, 0U, 0U, 0x80U, 0x3EU, 0U, 0U, 2U, 0U, 16U, 0U,
'd', 'a', 't', 'a', 4U, 0U, 0U, 0U, 0U, 1U, 2U, 3U,
'R', 'I', 'F', 'F', 40U, 0U, 0U, 0U, 'W', 'A', 'V', 'E', 'f', 'm', 't', ' ',
16U, 0U, 0U, 0U, 1U, 0U, 1U, 0U, 0x40U, 0x1FU, 0U, 0U, 0x80U, 0x3EU, 0U, 0U,
2U, 0U, 16U, 0U, 'd', 'a', 't', 'a', 4U, 0U, 0U, 0U, 0U, 1U, 2U, 3U,
};
rs_wav_info_t info;
const rs_wav_reader_t reader = {test_reader_read, (void *)wav, sizeof(wav)};
@@ -223,15 +224,13 @@ static int test_wav_parser(void)
info.block_align != 2U || info.data_offset != 44U || info.data_size != 4U) {
return 1;
}
if (rs_wav_parse(&(rs_wav_reader_t){test_reader_read, (void *)wav, 12U}, &info) !=
RS_EFORMAT) {
if (rs_wav_parse(&(rs_wav_reader_t){test_reader_read, (void *)wav, 12U}, &info) != RS_EFORMAT) {
return 2;
}
return 0;
}
static int test_video_parser(void)
{
static int test_video_parser(void) {
rs_video_info_t info;
(void)memset(storage, 0, sizeof(storage));
@@ -249,17 +248,11 @@ static int test_video_parser(void)
return 0;
}
int main(void)
{
int main(void) {
const int results[] = {
test_string_helpers(),
test_formatter(),
test_compiler_helpers(),
test_wait_helper(),
test_ws2812_helpers(),
test_timer_helpers(),
test_wav_parser(),
test_video_parser(),
test_string_helpers(), test_formatter(), test_compiler_helpers(),
test_wait_helper(), test_ws2812_helpers(), test_timer_helpers(),
test_gpio_helpers(), test_wav_parser(), test_video_parser(),
};
for (size_t index = 0U; index < (sizeof(results) / sizeof(results[0])); ++index) {