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

Implement Protothreads as Fibers #1001

Merged
merged 9 commits into from
May 14, 2023
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
28 changes: 15 additions & 13 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,8 @@ git clone --recurse-submodules --jobs 8 https://github.com/modm-io/modm.git
- UART, I<sup>2</sup>C, SPI, CAN and Ethernet.
- Interfaces and drivers for many external I<sup>2</sup>C and SPI sensors and devices.
- Debug/logging system with IOStream and printf interface.
- Lightweight, stackless threads and resumable functions using cooperative multitasking.
- Cooperative, stackless protothreads and resumable functions.
- Cooperative, stackful fibers and scheduler.
- Functional (partial) libstdc++ implementation for AVRs.
- Useful filter, interpolation and geometric algorithms.
- Lightweight unit testing system (suitable for AVRs).
Expand Down Expand Up @@ -723,86 +724,87 @@ you specific needs.
<td align="center"><a href="https://modm.io/reference/module/modm-driver-bmp085">BMP085</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-bno055">BNO055</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-cat24aa">CAT24AA</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-cycle_counter">CYCLE-COUNTER</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-drv832x_spi">DRV832X</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ds1302">DS1302</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ds1302">DS1302</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ds1631">DS1631</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ds18b20">DS18B20</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ea_dog">EA-DOG</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-encoder_input">Encoder Input</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-encoder_input-bitbang">Encoder Input BitBang</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-encoder_output-bitbang">Encoder Output BitBang</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-encoder_output-bitbang">Encoder Output BitBang</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ft245">FT245</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ft6x06">FT6x06</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-gpio_sampler">Gpio Sampler</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hclax">HCLAx</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hd44780">HD44780</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hmc58x">HMC58x</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hmc58x">HMC58x</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hmc6343">HMC6343</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-hx711">HX711</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-i2c-eeprom">I2C-EEPROM</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ili9341">ILI9341</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-is31fl3733">IS31FL3733</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-itg3200">ITG3200</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-itg3200">ITG3200</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-l3gd20">L3GD20</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lan8720a">LAN8720A</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lawicel">LAWICEL</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lis302dl">LIS302DL</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lis3dsh">LIS3DSH</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lis3mdl">LIS3MDL</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lis3mdl">LIS3MDL</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lm75">LM75</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lp503x">LP503x</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lsm303a">LSM303A</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lsm6ds33">LSM6DS33</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-lsm6dso">LSM6DSO</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ltc2984">LTC2984</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ltc2984">LTC2984</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-max31855">MAX31855</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-max31865">MAX31865</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-max6966">MAX6966</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-max7219">MAX7219</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mcp23x17">MCP23x17</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mcp2515">MCP2515</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mcp2515">MCP2515</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mcp7941x">MCP7941x</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mcp990x">MCP990X</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-mmc5603">MMC5603</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ms5611">MS5611</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ms5837">MS5837</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-nokia5110">NOKIA5110</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-nokia5110">NOKIA5110</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-nrf24">NRF24</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-parallel_tft_display">TFT-DISPLAY</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pat9125el">PAT9125EL</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pca8574">PCA8574</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pca9535">PCA9535</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pca9548a">PCA9548A</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pca9548a">PCA9548A</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-pca9685">PCA9685</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sh1106">SH1106</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-siemens_s65">SIEMENS-S65</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-siemens_s75">SIEMENS-S75</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sk6812">SK6812</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sk9822">SK9822</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sk9822">SK9822</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-ssd1306">SSD1306</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-st7586s">ST7586S</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-st7789">ST7789</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-stts22h">STTS22H</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-stusb4500">STUSB4500</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sx1276">SX1276</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-sx1276">SX1276</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tcs3414">TCS3414</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tcs3472">TCS3472</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tlc594x">TLC594x</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tmp102">TMP102</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tmp12x">TMP12x</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tmp175">TMP175</a></td>
</tr><tr>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-tmp175">TMP175</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-touch2046">TOUCH2046</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-vl53l0">VL53L0</a></td>
<td align="center"><a href="https://modm.io/reference/module/modm-driver-vl6180">VL6180</a></td>
Expand Down
23 changes: 14 additions & 9 deletions examples/avr/fiber/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -54,14 +54,10 @@ struct Test
volatile uint32_t f4counter{0};
} test;

modm::fiber::Stack<128> stack1;
modm::fiber::Stack<128> stack2;
modm::fiber::Stack<128> stack3;
modm::fiber::Stack<128> stack4;
modm::Fiber fiber1(stack1, fiber_function1);
modm::Fiber fiber2(stack2, [](){ fiber_function2(cycles); });
modm::Fiber fiber3(stack3, [](){ test.fiber_function3(); });
modm::Fiber fiber4(stack4, [cyc=uint32_t(cycles)]() mutable { cyc++; test.fiber_function4(cyc); });
modm::Fiber<> fiber1(fiber_function1);
modm::Fiber<> fiber2(+[](){ fiber_function2(cycles); });
modm::Fiber<> fiber3(+[](){ test.fiber_function3(); });
modm::Fiber<> fiber4([cyc=uint32_t(cycles)]() mutable { cyc++; test.fiber_function4(cyc); });

// ATmega2560@16MHz: 239996 yields in 2492668us, 96280 yields per second, 10386ns per yield
int
Expand All @@ -72,6 +68,11 @@ main()
MODM_LOG_INFO << "Starting fiber modm::yield benchmark..." << modm::endl;
MODM_LOG_INFO.flush();

fiber1.watermark_stack();
fiber2.watermark_stack();
fiber3.watermark_stack();
fiber4.watermark_stack();

const modm::PreciseTimestamp start = modm::PreciseClock::now();
modm::fiber::Scheduler::run();
const auto diff = (modm::PreciseClock::now() - start);
Expand All @@ -82,7 +83,11 @@ main()
MODM_LOG_INFO << " yields per second, ";
MODM_LOG_INFO << uint32_t(std::chrono::nanoseconds(diff).count() / total_counter);
MODM_LOG_INFO << "ns per yield" << modm::endl;
MODM_LOG_INFO.flush();

MODM_LOG_INFO << "Stack usage 1 = " << fiber1.stack_usage() << modm::endl;
MODM_LOG_INFO << "Stack usage 2 = " << fiber2.stack_usage() << modm::endl;
MODM_LOG_INFO << "Stack usage 3 = " << fiber3.stack_usage() << modm::endl;
MODM_LOG_INFO << "Stack usage 4 = " << fiber4.stack_usage() << modm::endl;

while(1) ;
return 0;
Expand Down
1 change: 0 additions & 1 deletion examples/avr/fiber/project.xml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
<!-- <extends>modm:arduino-nano</extends> -->
<options>
<option name="modm:build:build.path">../../../build/avr/fiber</option>
<option name="modm:__fibers">yes</option>
</options>
<modules>
<module>modm:build:scons</module>
Expand Down
65 changes: 14 additions & 51 deletions examples/generic/delay/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
// ----------------------------------------------------------------------------

#include <modm/board.hpp>
#include <modm/driver/time/cycle_counter.hpp>

using namespace Board;

Expand All @@ -18,6 +19,7 @@ using namespace Board;
modm::IODeviceWrapper<UsbUart0, modm::IOBuffer::DiscardIfFull> usb_io_device;
modm::log::Logger modm::log::info(usb_io_device);
#endif
modm_fastdata modm::CycleCounter counter;
#ifdef TCNT1
constexpr uint32_t SystemCoreClock = F_CPU;
#endif
Expand All @@ -27,39 +29,19 @@ run_delay_ns(uint32_t ns)
{
#ifdef CFG_TUSB_MCU
tud_task();
#endif
#ifdef TCNT1
uint16_t start, stop;
#else
uint32_t start, stop;
#endif
{
modm::atomic::Lock _;
#ifdef TCNT1
start = TCNT1;
#elif defined DWT
start = DWT->CYCCNT;
#else
SysTick->CTRL = SysTick_CTRL_ENABLE_Msk | SysTick_CTRL_CLKSOURCE_Msk;
SysTick->LOAD = (1ul << 23);
SysTick->VAL = 0;
stop = SysTick->VAL;
#endif
counter.start();
modm::delay_ns(ns);
#ifdef TCNT1
stop = TCNT1;
#elif defined DWT
stop = DWT->CYCCNT;
#else
start = SysTick->VAL;
#endif
counter.stop();
}
#ifdef CFG_TUSB_MCU
tud_task();
#endif
const uint32_t cycles = (stop - start) - 4;
const uint32_t cycles = counter.cycles();
const uint32_t expected = uint64_t(SystemCoreClock) * ns / 1'000'000'000ull;
const uint32_t real = cycles * 1'000'000'000ull / SystemCoreClock;
const uint32_t real = counter.nanoseconds();
MODM_LOG_INFO.printf("%8lu | %7lu | %7lu | %8lu %c\n", ns, expected, cycles, real,
(cycles < expected*1.2f ? (cycles > expected*0.8f ? ' ' : '<') : '>')) << modm::flush;
#ifdef CFG_TUSB_MCU
Expand All @@ -72,39 +54,19 @@ run_delay_us(uint32_t us)
{
#ifdef CFG_TUSB_MCU
tud_task();
#endif
#ifdef TCNT1
uint16_t start, stop;
#else
uint32_t start, stop;
#endif
{
modm::atomic::Lock _;
#ifdef TCNT1
start = TCNT1;
#elif defined DWT
start = DWT->CYCCNT;
#else
SysTick->CTRL = SysTick_CTRL_ENABLE_Msk | SysTick_CTRL_CLKSOURCE_Msk;
SysTick->LOAD = (1ul << 23);
SysTick->VAL = 0;
stop = SysTick->VAL;
#endif
counter.start();
modm::delay_us(us);
#ifdef TCNT1
stop = TCNT1;
#elif defined DWT
stop = DWT->CYCCNT;
#else
start = SysTick->VAL;
#endif
counter.stop();
}
#ifdef CFG_TUSB_MCU
tud_task();
#endif
const uint32_t cycles = (stop - start) - 4;
const uint32_t cycles = counter.cycles();
const uint32_t expected = uint64_t(SystemCoreClock) * us / 1'000'000ull;
const uint32_t real = cycles * 1'000'000ull / SystemCoreClock;
const uint32_t real = counter.microseconds();
MODM_LOG_INFO.printf("%8lu | %8lu | %8lu | %8lu %c\n", us, expected, cycles, real,
(cycles < expected*1.2f ? (cycles > expected*0.8f ? ' ' : '<') : '>')) << modm::flush;
#ifdef CFG_TUSB_MCU
Expand Down Expand Up @@ -174,9 +136,7 @@ run_test_us(bool short_test=false)
int main()
{
Board::initialize();

TCCR1A = 0;
TCCR1B = (1 << CS10);
counter.initialize();

run_test_ns();
run_test_us();
Expand All @@ -192,6 +152,7 @@ int main()
{
Board::initialize();
Board::initializeUsbFs();
counter.initialize(true);
tusb_init();

MODM_LOG_INFO << "Hello World\n";
Expand Down Expand Up @@ -229,11 +190,13 @@ int main()
{
Board::stlink::Uart::connect<Board::stlink::Tx::Tx>();
Board::stlink::Uart::initialize<BootClock, 115200_Bd, 5_pct>();
counter.initialize(true);

run_test_ns();
run_test_us();

Board::initialize();
counter.initialize(true);

run_test_ns();
run_test_us();
Expand Down
1 change: 1 addition & 0 deletions examples/generic/delay/project.xml
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
<modules>
<module>modm:build:scons</module>
<module>modm:debug</module>
<module>modm:driver:cycle_counter</module>
<!-- <module>modm:tinyusb</module> -->
</modules>
</library>
Loading