-
Notifications
You must be signed in to change notification settings - Fork 0
Home
Welcome to the TaskSched wiki!
TaskSched is a cooperative multitasking scheduler for Arduino processors, designed as a simpler alternative to existing schedulers like TaskScheduler. It provides a flexible and efficient way to manage multiple tasks in Arduino projects, particularly tested on ESP32 and ESP8266 processors.
A cooperative task scheduler is a system that manages the execution of multiple tasks, but with a twist compared to a traditional scheduler. Here's the key difference:
Cooperative: In a cooperative scheme, tasks are responsible for voluntarily giving up control of the processor when they're done or need to wait for something. The scheduler simply provides a starting point and trusts the tasks to behave. This is in contrast to a preemptive scheduler, where the operating system can interrupt a running task and switch to another one.
Here's a breakdown of how cooperative scheduling works:
- The scheduler starts a task.
- The task runs until it finishes its work or needs to wait for something (like user input or data from another task).
- The task then signals the scheduler that it's done or needs to wait.
- The scheduler picks another task to run. Pros and Cons:
Pros: Simpler to implement, fewer system resources needed. Cons: Unpredictable behavior if tasks don't cooperate, can lead to unresponsive systems if a task gets stuck. Use Cases:
Often used in early operating systems or embedded systems with limited resources. Can be a good choice for specific situations where tasks have well-defined execution times and don't rely on external events heavily.
- Periodic task execution: Tasks can be set to run at specified intervals, with times specified in milliseconds or seconds.
- Task enable/disable support: Tasks can be dynamically enabled or disabled.
- Iteration control: Tasks can be set to run for a specific number of iterations or indefinitely.
- Immediate or delayed execution: Tasks can be scheduled to run immediately when enabled or wait for the interval to expire.
- Task restart and parameter modification: Tasks can be restarted with original or new parameters (interval, callback function, etc.).
- Flexible timing control: The scheduler can be run periodically in the main loop.
To install TaskSched, clone the repository:
git clone https://github.com/AverageGuy/tasksched.git
Or download the ZIP file.
Tasks are created using the Task constructor:
Task *task = new Task(callback, interval, enabled, iterations, name, runImmediately);
Task *task = new Task(VoidCallBack, interval, enabled, iterations, name, runImmediately);-
TaskCallback: Function to be called (must accept aTask*parameter) -
VoidCallback: Function to be called (no parameter) -
interval: Time between calls milliseconds (default: 5000) -
enabled: Whether the task starts enabled (default: false) -
iterations: Number of times to run (0 for infinite) (default: 0) -
name: Descriptive name for the task (Default: "Unk" -
runImmediately: Whether to run immediately when enabled without waiting for interval to expire (Default: false)
Key methods for managing tasks:
-
enable(): Enable the task -
disable(): Disable the task -
restart(): Restart the task with original parameters -
setInterval(newInterval): Set a new interval -
setIterations(newIterations): Set a new iteration count -
isEnabled(): Check if the task is enabled -
isFirstIteration(): Check if it's the first iteration -
isLastIteration(): Check if it's the last iteration -
Task::formatMS(): Static function to Format an unsigned long into a string of the format MM:SS.mmm Minutes, Seconds, milliseconds
The Sched class manages multiple tasks:
Sched scheduler;
scheduler.addTask(task);
scheduler.begin();
void loop() {
scheduler.run();
}This section explains how to create and manage tasks using the TaskSched library.
A Task object represents a scheduled function execution. It defines the function to be called, the interval between executions, and other properties. Here's an example task named "OnOff" that turns an LED on and off:
C++
void turnLedOn(Task *ta) {
// Code to turn LED on
...
}
Task *t = new Task(turnLedOn, 1000, true, 20, "OnOff", true);
- turnLedOn: The function pointer to the task's execution code. This function should be of type void.
- 1000: The interval in milliseconds between task executions (optional, default is 5000).
- true: Enables immediate execution (optional, default is false).
- 20: The maximum number of times the task will be executed (optional, default is 0 for unlimited).
- "OnOff": A descriptive name for the task (optional).
- true: Enables the task initially (optional, default is false).
- function: The function to be called when the task is to be executed.
- interval: The time delay between task executions (in milliseconds).
- enabled: Whether the task is currently scheduled for execution.
- iterationLimit: The maximum number of times the task will run.
- name: A user-defined name for the task (for identification).
- immediate: Whether to run the task immediately after enabling it.
Here's a basic structure for an Arduino program using TaskSched:
C++
#include <TaskSched.h>
Sched scheduler; // Global scheduler object
// Task function definitions...
void setup() {
// ...
// Create tasks
t1 = new Task(getData, 5 * TASK_SECOND, true, 1, "Data collection", false);
t2 = new Task(firstPass, 500, true, 1, "First", true);
Task t3 = Task(periodic, 5.1 * TASK_MINUTE, true, 1, "Status", false);
// Add tasks to the scheduler
scheduler.addTask(t1);
scheduler.addTask(t2);
scheduler.addTask(&t3);
scheduler.begin();
}
void loop() {
scheduler.run();
}
There is one static method in the Task class and that is the formatMMSS() method. As it is a class method and not an object method you need to call it as:
String intervalStr=Task::formatMMSS(interval);
/** if interval = 105040 ms, then intervalStr will be 01:45.040 */
See the examples directory for basic examples of blinking an LED using TaskSched. Also the next page Examples of this wiki has a brief description of the examples.
For detailed API documentation, please refer to the Doxygen-generated documentation TaskSched.
If you encounter any issues or have feature requests, please open an issue on the GitHub repository.
If you are running the DemoTemplate32 example on a RISC-V ESP32 chip, like the -c3 or -s3 then you may encounter a problem with the TelnetSpy library. In the examples directory there is a file, telnetspy.patch that can be applied to the TelnetSpy.cpp file.
Find the source and Run "patch TelnetSpy.cpp < telnetspy.patch" to produce a working version of TelnetSpy that will compile correctly. Be sure you have the 1.41 version of TelnetSpy. The version can be found around line 6 of the TelnetSpy.cpp file.
Contributions to TaskSched are welcome. Please feel free to submit pull requests or open issues to discuss potential improvements.