Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

cpu/sam0_common: Implement time-sharing of SERCOMs #21029

Draft
wants to merge 3 commits into
base: master
Choose a base branch
from

Conversation

maribu
Copy link
Member

@maribu maribu commented Nov 21, 2024

Contribution description

This adds a periph_sercom feature and implementation which periph_i2c, periph_uart, and periph_spi are implemented on top. This allows for sharing a single SERCOM instance to provide multiple serial interfaces (in round-robin time-sharing fashion).

Note

In practice, a SERCOM can often not be shared if it needs to provide an UART.

Background:

While code using the I2C/SPI APIs is already optimized to share the peripheral with i2c_acquire()/spi_acquire() and i2c_release()/spi_release(), UARTs are typically not shared and most users will not call uart_poweron() and uart_poweroff() to only have the SERCOM in UART mode when actually needed. Worse: For many use cases (such as stdin), the UART will need to be constantly running, as receiving data happens asynchronously at unpredictable points in time.

Testing procedure

make BOARD=adafruit-metro-m4-express flash term -C tests/periph/selftest_shield

2024-11-21 20:29:42,410 # ALL TESTS SUCCEEDED
2024-11-21 20:29:42,395 # main(): This is RIOT! (Version: 2025.01-devel-156-g1baf0-cpu/sam0_common/periph_sercom)
2024-11-21 20:29:42,396 # self-testing peripheral drivers
2024-11-21 20:29:42,396 # ===============================
2024-11-21 20:29:42,396 # Starting test for GPIO at tests/periph/selftest_shield/main.c:350
2024-11-21 20:29:42,396 # [OK]
2024-11-21 20:29:42,397 # Starting test for GPIO at tests/periph/selftest_shield/main.c:372
2024-11-21 20:29:42,397 # [OK]
2024-11-21 20:29:42,397 # Starting test for GPIO at tests/periph/selftest_shield/main.c:402
2024-11-21 20:29:42,397 # [OK]
2024-11-21 20:29:42,397 # Starting test for GPIO at tests/periph/selftest_shield/main.c:432
2024-11-21 20:29:42,397 # (skipped)
2024-11-21 20:29:42,398 # Starting test for GPIO at tests/periph/selftest_shield/main.c:458
2024-11-21 20:29:42,398 # (skipped)
2024-11-21 20:29:42,398 # Starting test for GPIO-IRQ at tests/periph/selftest_shield/main.c:505
2024-11-21 20:29:42,398 # [OK]
2024-11-21 20:29:42,399 # Starting test for GPIO-IRQ at tests/periph/selftest_shield/main.c:571
2024-11-21 20:29:42,399 # [OK]
2024-11-21 20:29:42,399 # Starting test for GPIO-IRQ at tests/periph/selftest_shield/main.c:637
2024-11-21 20:29:42,399 # [OK]
2024-11-21 20:29:42,399 # Starting test for I2C at tests/periph/selftest_shield/main.c:711
2024-11-21 20:29:42,399 # [OK]
2024-11-21 20:29:42,400 # Starting test for UART at tests/periph/selftest_shield/main.c:806
2024-11-21 20:29:42,400 # [OK]
2024-11-21 20:29:42,400 # Starting test for UART at tests/periph/selftest_shield/main.c:815
2024-11-21 20:29:42,400 # [OK]
2024-11-21 20:29:42,400 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,401 # [OK]
2024-11-21 20:29:42,401 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,401 # [OK]
2024-11-21 20:29:42,401 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,401 # [OK]
2024-11-21 20:29:42,402 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,402 # [OK]
2024-11-21 20:29:42,402 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,402 # [OK]
2024-11-21 20:29:42,402 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,402 # [OK]
2024-11-21 20:29:42,403 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,403 # [OK]
2024-11-21 20:29:42,403 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,403 # [OK]
2024-11-21 20:29:42,404 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,404 # [OK]
2024-11-21 20:29:42,404 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,404 # [OK]
2024-11-21 20:29:42,404 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,405 # [OK]
2024-11-21 20:29:42,405 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,405 # [OK]
2024-11-21 20:29:42,405 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,405 # [OK]
2024-11-21 20:29:42,406 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,406 # [OK]
2024-11-21 20:29:42,406 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,406 # [OK]
2024-11-21 20:29:42,406 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,406 # [OK]
2024-11-21 20:29:42,407 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,407 # [OK]
2024-11-21 20:29:42,407 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,407 # [OK]
2024-11-21 20:29:42,408 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,408 # [OK]
2024-11-21 20:29:42,408 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,408 # [OK]
2024-11-21 20:29:42,408 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,408 # [OK]
2024-11-21 20:29:42,409 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,409 # [OK]
2024-11-21 20:29:42,409 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,409 # [OK]
2024-11-21 20:29:42,409 # Starting test for SPI at tests/periph/selftest_shield/main.c:858
2024-11-21 20:29:42,409 # [OK]
2024-11-21 20:29:42,410 # Starting test for ADC at tests/periph/selftest_shield/main.c:1072
2024-11-21 20:29:42,410 # [OK]
2024-11-21 20:29:42,410 # 
2024-11-21 20:29:42,410 # 
2024-11-21 20:29:42,410 # ALL TESTS SUCCEEDED
2024-11-21 20:29:42,410 # { "threads": [{ "name": "main", "stack_size": 1536, "stack_used": 572}]}

Issues/PRs references

None

@github-actions github-actions bot added Platform: ARM Platform: This PR/issue effects ARM-based platforms Area: tests Area: tests and testing framework Area: build system Area: Build system Area: boards Area: Board ports labels Nov 21, 2024
@maribu maribu added the CI: ready for build If set, CI server will compile all applications for all available boards for the labeled PR label Nov 21, 2024
@github-actions github-actions bot added the Area: cpu Area: CPU/MCU ports label Nov 21, 2024
@maribu maribu changed the title Cpu/sam0 common/periph sercom cpu/sam0_common: Implement time-sharing of SERCOMs Nov 21, 2024
@riot-ci
Copy link

riot-ci commented Nov 21, 2024

Murdock results

✔️ PASSED

bd365b1 boards: fix whitespace style issues

Success Failures Total Runtime
10248 0 10249 16m:54s

Artifacts

@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from 1baf069 to f9c952d Compare November 21, 2024 21:42
cpu/sam0_common/periph/sercom.c Show resolved Hide resolved
cpu/sam0_common/periph/sercom.c Outdated Show resolved Hide resolved
@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from 56ef1ea to 08a71df Compare November 26, 2024 20:51
@github-actions github-actions bot added Area: drivers Area: Device drivers Platform: ESP Platform: This PR/issue effects ESP-based platforms and removed Area: tests Area: tests and testing framework labels Nov 26, 2024
@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch 2 times, most recently from b2bb805 to f5abef9 Compare November 26, 2024 22:30
@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from 935ac6e to 2a64955 Compare November 27, 2024 08:47
@github-actions github-actions bot added Area: network Area: Networking Area: pkg Area: External package ports labels Nov 27, 2024
@kfessel
Copy link
Contributor

kfessel commented Nov 27, 2024

please reduce static noise

there are multiple warnings like

Check warning on line 122 in boards/arduino-nano-33-iot/include/periph_conf.h
GitHub Actions / static-tests

comma should be followed by whitespace
- .rx_pin   = GPIO_PIN(PB,23),
+ .rx_pin   = GPIO_PIN(PB, 23),

@kfessel
Copy link
Contributor

kfessel commented Nov 27, 2024

boards/samd20-xpro/include/periph_conf.h
and
boards/samd21-xpro/include/periph_conf.h

also miss white space ( i don't know why these messages are not brought up at once but trickel after every commit)

the static test also don't like regular form past tens of irregular "reset"

@kfessel
Copy link
Contributor

kfessel commented Nov 27, 2024

seems like vera++ produced that noise, i reduced that list to once per file and warning

boards/samd20-xpro/include/periph_conf.h:141: warning: comma should be followed by whitespace
boards/samd21-xpro/include/periph_conf.h:143: warning: comma should be followed by whitespace
boards/samr21-xpro/include/periph_conf.h:165: warning: comma should be followed by whitespace
boards/samr30-xpro/include/periph_conf.h:63: warning: comma should be followed by whitespace
boards/sodaq-autonomo/include/periph_conf.h:45: warning: comma should be followed by whitespace
boards/sodaq-explorer/include/periph_conf.h:41: warning: comma should be followed by whitespace
boards/sodaq-one/include/periph_conf.h:44: warning: comma should be followed by whitespace
boards/sodaq-sara-aff/include/periph_conf.h:61: warning: comma should be followed by whitespace
cpu/cortexm_common/include/cpu.h:95: warning: line is longer than 100 characters
cpu/cortexm_common/include/cpu.h:[24](https://github.com/RIOT-OS/RIOT/actions/runs/12050475159/job/33599437291?pr=21029#step:6:31)4: warning: horizontal tab used
cpu/sam0_common/periph/i2c.c:209: warning: comma should not be preceded by whitespace
cpu/sam0_common/periph/i2c.c:308: warning: full block {} expected in the control structure
cpu/samd21/include/periph_cpu.h:55: warning: too many consecutive empty lines
cpu/saml1x/include/periph_cpu.h:139: warning: line is longer than 100 characters
cpu/saml21/include/periph_cpu.h:198: warning: line is longer than 100 characters
pkg/openwsn/include/openwsn_log.h:72: warning: full block {} expected in the control structure

@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from d75b27a to 6d113cd Compare November 27, 2024 17:43
@github-actions github-actions bot removed Area: network Area: Networking Area: pkg Area: External package ports Area: drivers Area: Device drivers Platform: ESP Platform: This PR/issue effects ESP-based platforms labels Nov 27, 2024
@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from 6d113cd to 0dbd13a Compare November 27, 2024 17:43
This adds a `periph_sercom` feature and implementation which
`periph_i2c`, `periph_uart`, and `periph_spi` are implemented on top.
This allows for sharing a single SERCOM instance to provide multiple
serial interfaces (in round-robin time-sharing fashion).

Note: In practice, a SERCOM can often not be shared if it needs to
      provide an UART.

Background:

While code using the I2C/SPI APIs is already optimized to share the
peripheral with `i2c_acquire()`/`spi_acquire()` and
`i2c_release()`/`spi_release()`, UARTs are typically not shared and most
users will not call `uart_poweron()` and `uart_poweroff()` to only have
the SERCOM in UART mode when actually needed. Worse: For many use cases
(such as stdin), the UART will need to be constantly running, as
receiving data happens asynchronously at unpredictable points in time.
Now that time-sharing SERCOMs is possible, we can provide the SPI on
D11/D12/D13 (backed by SERCOM3) also when the UART on D0/D1 (also backed
by SERCOM3) is used.
This adds the space missing after the comma in `GPIO_PORT(<port>,<pin>`
at multiple places
@maribu maribu force-pushed the cpu/sam0_common/periph_sercom branch from 0dbd13a to bd365b1 Compare November 27, 2024 17:49
@maribu
Copy link
Member Author

maribu commented Nov 27, 2024

vera++ should now be happy

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Area: boards Area: Board ports Area: build system Area: Build system Area: cpu Area: CPU/MCU ports CI: ready for build If set, CI server will compile all applications for all available boards for the labeled PR Platform: ARM Platform: This PR/issue effects ARM-based platforms
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants