ANTIRTOS
ANTIRTOS is an ultra-lightweight, universal C++ library designed for task management in embedded and IoT applications, particularly suitable for the Arduino platform. Developed by Aleksei Tertychnyi, ANTIRTOS offers an efficient way to handle multitasking without the complexity and overhead associated with RTOS. It is specifically crafted to keep interrupts fast and non-blocking, making it ideal for resource-constrained environments.
Key Features
-
Function Queues:
- ANTIRTOS utilizes function queues to manage tasks. These queues allow function pointers to be stored and executed in an orderly manner.
- Queues can handle functions with or without parameters, and templated queues enable handling functions with specific parameter types.
-
Non-Blocking Interrupts:
- One of the standout features of ANTIRTOS is its ability to keep interrupts fast and non-blocking. Tasks can be pushed to queues from within Interrupt Service Routines (ISRs), deferring the execution to the main loop.
-
Delayed Execution:
- ANTIRTOS supports delayed execution of tasks, allowing functions to be scheduled to run after a specified delay.
-
Ease of Integration:
- The library is designed to be lightweight and easy to integrate into existing projects. It consists of a single, small file of about 5KB, making it easy to include and use.
-
Modularity and Scalability:
- ANTIRTOS's modular design ensures that it can be scaled to fit various applications, from simple microcontrollers to more complex embedded systems.
Usage
Basic Example with Interrupts
To demonstrate the power of ANTIRTOS in handling interrupts, we can use two digital input pins with interrupts and dedicated queues for each:
#include <antirtos.h>
#include <TimerOne.h> // Include the TimerOne library
// Define two function queues for handling tasks
fQ F1(8); // Queue for the first interrupt
fQ F2(8); // Queue for the second interrupt
// Task function for the first interrupt
void task1() {
Serial.println("Task 1 executed");
}
// Task function for the second interrupt
void task2() {
Serial.println("Task 2 executed");
}
// Interrupt Service Routine (ISR) for the first digital input
void ISR1() {
F1.push(task1); // Push the task to the first queue
}
// Interrupt Service Routine (ISR) for the second digital input
void ISR2() {
F2.push(task2); // Push the task to the second queue
}
void setup() {
Serial.begin(9600);
pinMode(2, INPUT_PULLUP); // Set up the first digital input pin
pinMode(3, INPUT_PULLUP); // Set up the second digital input pin
attachInterrupt(digitalPinToInterrupt(2), ISR1, FALLING); // Attach ISR1 to pin 2
attachInterrupt(digitalPinToInterrupt(3), ISR2, FALLING); // Attach ISR2 to pin 3
}
void loop() {
F1.pull(); // Execute tasks from the first queue
F2.pull(); // Execute tasks from the second queue
}
Handling Interrupts and Delayed Execution
ANTIRTOS excels at keeping interrupts non-blocking. By pushing tasks to queues within ISRs, the actual task processing is deferred to the main loop, ensuring that the interrupts are handled swiftly and efficiently.
Example with Timer and Button Interrupts
Here's an enhanced example demonstrating how to use ANTIRTOS with a timer interrupt for delayed execution and a button press interrupt:
#include <antirtos.h>
#include <TimerOne.h> // Include the TimerOne library
// Define a templated queue for functions with an int32_t parameter
fQP<int32_t> F4(10);
// Define a delayed function queue
del_fQ F5(8);
// Example task function that takes an int32_t parameter
void taskFunction(int32_t param) {
Serial.print("Task executed with parameter: ");
Serial.println(param);
}
// Interrupt Service Routine (ISR) for timer
void timerISR() {
F5.tick(); // Increment the internal timer for delayed execution
}
// Example task to push from a button press
void buttonTask() {
int32_t value = analogRead(A0); // Read a value from an analog pin
F4.push(taskFunction, value); // Push the...
Read more »
Instead of "wait by doing" can we call WFI?