Skip to content

Commit fedf070

Browse files
author
dave
committed
Some IDEs do not seem to remove old files, only update / add files. So I've re-added TaskManager.cpp and TaskManager.h just in case, they are both pretty much empty files to avoid problems.
1 parent 4a594b2 commit fedf070

File tree

3 files changed

+314
-320
lines changed

3 files changed

+314
-320
lines changed

src/TaskManager.h

Lines changed: 7 additions & 310 deletions
Original file line numberDiff line numberDiff line change
@@ -3,315 +3,12 @@
33
* This product is licensed under an Apache license, see the LICENSE file in the top-level directory.
44
*/
55

6-
#ifndef TASKMANAGER_IO_H
7-
#define TASKMANAGER_IO_H
6+
#ifndef TASKMANAGER_COMPAT_H
7+
#define TASKMANAGER_COMPAT_H
88

9-
#include "TaskPlatformDeps.h"
10-
#include "TaskTypes.h"
11-
#include "TaskBlock.h"
9+
//
10+
// Provides compatibility with old task manager if needed
11+
//
12+
#include "TaskManagerIO.h"
1213

13-
/**
14-
* @file TaskManager.h
15-
*
16-
* Task manager is a simple co-routine style implementation for Arduino which supports scheduling work to be done
17-
* at a given time, repeating tasks, interrupt marshalling and events. It is generally thread safe such that code
18-
* outside of task manager can add, remove and manage tasks even while task manager is running.
19-
*
20-
* Note that you should never add tasks from a raw ISR, instead use task manager's marshalling of interrupts or
21-
* use an event that triggers on the interrupt occurring.
22-
*
23-
* The API for this class is compatible across Arduino, ESP and mbed. It is mainly thread safe on tested platforms.
24-
*
25-
* Both Commercial and Community support for task manager are available from http://www.thecoderscorner.com
26-
*/
27-
28-
#ifdef IOA_USE_MBED
29-
#include <cstdint>
30-
/** MBED ONLY: This defines the yield function for mbed boards, as per framework on Arduino */
31-
void yield();
32-
/** MBED ONLY: This defines the millis function for mbed boards by using a timer, as per framework on Arduino */
33-
uint32_t millis();
34-
/** MBED ONLY: This defines the micros function to use the standard mbed us timer, as per framework on Arduino */
35-
uint32_t micros();
36-
#endif // IOA_USE_MBED
37-
38-
/**
39-
* the definition of an interrupt handler function, to be called back when an interrupt occurs.
40-
*/
41-
typedef void (*RawIntHandler)();
42-
43-
/**
44-
* Definition of a function to be called back when an interrupt is detected, marshalled by task manager into a task.
45-
* The pin that caused the interrupt is passed in the parameter on a best efforts basis.
46-
* @param pin the pin on which the interrupt occurred (best efforts)
47-
*/
48-
typedef void (*InterruptFn)(pintype_t pin);
49-
50-
/**
51-
* Abstracts the method by which interrupts are registered on the platform. Generally speaking this is implemented by
52-
* all IoAbstractionRef implementations, so having any abstraction means you already have one of these. You can either
53-
* implement your own variant of this, or use IoAbstraction to do it for you.
54-
*
55-
* For example if using IoAbstraction then the IO object returned by internalDigitalIo() implements this.
56-
*/
57-
class InterruptAbstraction {
58-
public:
59-
/**
60-
* Register an interrupt handler to a specific pin on the device, such that the interrupt handler function will
61-
* be triggered when mode is true. Mode can be one of CHANGE, RISING, FALLING.
62-
* @param pin the pin on the device to attach an interrupt to
63-
* @param fn the raw interrupt ISR function
64-
* @param mode either RISING, FALLING or CHANGE
65-
*/
66-
virtual void attachInterrupt(pintype_t pin, RawIntHandler fn, uint8_t mode) = 0;
67-
};
68-
69-
#ifdef IOA_USE_ARDUINO
70-
/**
71-
* For Arduino devices when NOT using IoAbstraction, this is the minimum possible implementation that can call
72-
* through to the Arduino platform ::attachInterrupt call. You can pass a pointer to one of these to the task manager
73-
* interrupt functions. If you are using IoAbstraction, all IoAbstractionRef's implement InterruptAbstraction.
74-
*/
75-
class BasicArduinoInterruptAbstraction : public InterruptAbstraction {
76-
void attachInterrupt(pintype_t pin, RawIntHandler fn, uint8_t mode) override {
77-
#ifdef ARDUINO_MBED_MODE
78-
::attachInterrupt(pin, fn, (PinStatus)mode);
79-
#else
80-
::attachInterrupt(pin, fn, mode);
81-
#endif // ARDUINO_MBED_MODE
82-
}
83-
};
84-
#endif // IOA_USE_ARDUINO - Arduino Only
85-
86-
/**
87-
* TaskManager is a lightweight cooperative co-routine implementation for Arduino, it works by scheduling tasks to be
88-
* done either immediately, or at a future point in time. It is quite efficient at scheduling tasks as internally tasks
89-
* are arranged in time order in a linked list. Tasks can be provided as either a function to be called, or a class
90-
* that implements the Executable interface. Tasks can be scheduled to run either ASAP, once, or repeated.
91-
*
92-
* Events can be added based on extensions of the BaseEvent class, these can be triggered outside of task manager and
93-
* they can then "wake up" task manager, events can also be polled. In addition interrupts can be marshalled through
94-
* task manager, any interrupt managed by task manager will be marshalled into a task. IE outside of an ISR.
95-
*
96-
* There is a globally defined variable called `taskManager` and you should attach this to your main loop. You can
97-
* create other task managers on different threads if required. For most use cases, the class is thread safe.
98-
*/
99-
class TaskManager {
100-
protected:
101-
// the memory that holds all the tasks is an array of task blocks, allocated on demand
102-
TaskBlock* volatile taskBlocks[DEFAULT_TASK_BLOCKS]; // task blocks never ever move in memory, they are not volatile but the pointer is
103-
volatile taskid_t numberOfBlocks; // this holds the current number of blocks available.
104-
105-
// here we have a linked list of tasks, this linked list is in time order, nearest task first.
106-
tm_internal::TimerTaskAtomicPtr first;
107-
108-
// interrupt handling variables, store the interrupt state and probable pin cause if applicable
109-
volatile pintype_t lastInterruptTrigger;
110-
volatile bool interrupted;
111-
volatile InterruptFn interruptCallback;
112-
113-
tm_internal::TmAtomicBool memLockerFlag; // memory and list operations are locked by this flag using the TmSpinLocker
114-
public:
115-
/**
116-
* On all platforms there is a default instance of TaskManager called taskManager. You can create other instances
117-
* that can run on other threads, for example to process long running tasks that should be processed separately.
118-
*/
119-
TaskManager();
120-
~TaskManager();
121-
122-
/**
123-
* Executes a task manager task as soon as possible. Useful to add work into task manager from another thread of
124-
* execution. Shorthand for scheduleOnce(0, task);
125-
* @param workToDo the work to be done
126-
* @return the task ID that can be queried and cancelled.
127-
*/
128-
inline taskid_t execute(TimerFn workToDo) {
129-
return scheduleOnce(0, workToDo);
130-
}
131-
132-
/**
133-
* Executes a task manager task as soon as possible. Useful to add work into task manager from another thread of
134-
* execution. Shorthand for scheduleOnce(0, task);
135-
* @param execToDo the work to be done
136-
* @param deleteWhenDone default to false, task manager will reclaim the memory when done with this executable.
137-
* @return the task ID that can be queried and cancelled.
138-
*/
139-
inline taskid_t execute(Executable* execToDo, bool deleteWhenDone = false) {
140-
return scheduleOnce(0, execToDo, TIME_MICROS, deleteWhenDone);
141-
}
142-
143-
/**
144-
* Schedules a task for one shot execution in the timeframe provided.
145-
* @param millis the time frame in which to schedule the task
146-
* @param timerFunction the function to run at that time
147-
* @param timeUnit defaults to TIME_MILLIS but can be any of the possible values.
148-
*/
149-
taskid_t scheduleOnce(uint32_t when, TimerFn timerFunction, TimerUnit timeUnit = TIME_MILLIS);
150-
151-
/**
152-
* Schedules a task for one shot execution in the timeframe provided calling back the exec
153-
* function on the provided class extending Executable.
154-
* @param millis the time frame in which to schedule the task
155-
* @param execRef a reference to a class extending Executable
156-
* @param timeUnit defaults to TIME_MILLIS but can be any of the possible values.
157-
* @param deleteWhenDone default to false, task manager will reclaim the memory when done with this executable.
158-
*/
159-
taskid_t scheduleOnce(uint32_t when, Executable* execRef, TimerUnit timeUnit = TIME_MILLIS, bool deleteWhenDone = false);
160-
161-
/**
162-
* Schedules a task for repeated execution at the frequency provided.
163-
* @param millis the frequency at which to execute
164-
* @param timerFunction the function to run at that time
165-
* @param timeUnit defaults to TIME_MILLIS but can be any of the possible values.
166-
*/
167-
taskid_t scheduleFixedRate(uint32_t when, TimerFn timerFunction, TimerUnit timeUnit = TIME_MILLIS);
168-
169-
/**
170-
* Schedules a task for repeated execution at the frequency provided calling back the exec
171-
* method on the provided class extending Executable.
172-
* @param millis the frequency at which to execute
173-
* @param execRef a reference to a class extending Executable
174-
* @param timeUnit defaults to TIME_MILLIS but can be any of the possible values.
175-
* @param deleteWhenDone true if taskManager should call delete on the object when done, otherwise false.
176-
*/
177-
taskid_t scheduleFixedRate(uint32_t when, Executable* execRef, TimerUnit timeUnit = TIME_MILLIS, bool deleteWhenDone = false);
178-
179-
/**
180-
* Adds an event to task manager that can be triggered either once or can be repeated. See the
181-
* BaseEvent interface for more details of the interaction with taskManager.
182-
* @param eventToAdd the event that is added to task manager
183-
* @param deleteWhenDone true if taskManager should call delete on the object when done, otherwise false.
184-
*/
185-
taskid_t registerEvent(BaseEvent* eventToAdd, bool deleteWhenDone = false);
186-
187-
/**
188-
* Generally used by the BaseEvent class in the markTriggeredAndNotify to indicate that at least
189-
* one event has now triggered and needs to be evaluated.
190-
*/
191-
void triggerEvents() {
192-
lastInterruptTrigger = 0xff; // 0xff is the shorthand for event trigger basically.
193-
interrupted = true;
194-
}
195-
196-
/**
197-
* Adds an interrupt that will be handled by task manager, such that it's marshalled into a task.
198-
* This registers an interrupt with any IoAbstractionRef.
199-
* @param ref the Interrupt abstraction (or IoAbstractionRef) that we want to register the interrupt for
200-
* @param pin the pin upon which to register (on the IoDevice above)
201-
* @param mode the mode in which to register, eg. CHANGE, RISING, FALLING
202-
*/
203-
void addInterrupt(InterruptAbstraction* interruptAbstraction, pintype_t pin, uint8_t mode);
204-
205-
/**
206-
* Sets the interrupt callback to be used when an interrupt is signalled. Note that you will be
207-
* called back by task manager, and you are safe to use any variables as normal. Task manager
208-
* marshalls the interrupt for you.
209-
* @param handler the interrupt handler
210-
*/
211-
void setInterruptCallback(InterruptFn handler);
212-
213-
/**
214-
* Stop a task from executing or cancel it from executing again if it is a repeating task
215-
* @param task the task ID returned from the schedule call
216-
*/
217-
void cancelTask(taskid_t task);
218-
219-
/**
220-
* Use instead of delays or wait loops inside code that needs to perform timing functions. It will
221-
* not call back until at least `micros` time has passed.
222-
* @param micros the number of microseconds to wait.
223-
*/
224-
virtual void yieldForMicros(uint32_t micros);
225-
226-
/**
227-
* This should be called in the loop() method of your sketch, ensure that your loop method does
228-
* not do anything that will unduly delay calling this method.
229-
*/
230-
void runLoop();
231-
232-
/**
233-
* Used internally by the interrupt handlers to tell task manager an interrupt is waiting. Not for external use.
234-
*/
235-
static void markInterrupted(pintype_t interruptNo);
236-
237-
/**
238-
* Reset the task manager such that all current tasks are cleared, back to power on state.
239-
*/
240-
void reset() {
241-
// all the slots should be cleared
242-
for(taskid_t i =0; i<numberOfBlocks; i++) {
243-
taskBlocks[i]->clearAll();
244-
}
245-
// the queue must be completely cleared too.
246-
tm_internal::atomicWritePtr(&first, nullptr);
247-
}
248-
249-
/**
250-
* This method fills slotData with the current running conditions of each available task slot.
251-
* Useful for debugging purposes, where each task the .
252-
* Key:
253-
* * 'R' repeating task ('r' when currently running)
254-
* * 'U' one shot task ('u' when currently running)
255-
* * 'F' free slot (should never be 'f')
256-
* @param slotData the char array to fill in with task information. Must be as long as number of tasks + 1.
257-
* @param slotDataSize the size of the array passed in (normally using sizeof).
258-
*/
259-
char* checkAvailableSlots(char* slotData, size_t slotDataSize) const;
260-
261-
/**
262-
* Gets the first task in the run queue. Not often useful outside of testing.
263-
*/
264-
TimerTask* getFirstTask() {
265-
return tm_internal::atomicReadPtr(&first);
266-
}
267-
268-
/**
269-
* Gets the underlying TimerTask variable associated with this task ID.
270-
* @param task the task's ID
271-
* @return the task or nullptr.
272-
*/
273-
TimerTask* getTask(taskid_t task);
274-
275-
/**
276-
* Gets the number of microseconds as an unsigned long to the next task execution.
277-
* To convert to milliseconds: divide by 1000, to seconds divide by 1,000,000.
278-
* @return the microseconds from now to next execution
279-
*/
280-
uint32_t microsToNextTask() {
281-
auto maybeTask = tm_internal::atomicReadPtr(&first);
282-
if(maybeTask == nullptr) return 600 * 1000000U; // wait for 10 minutes if there's nothing to do
283-
else return maybeTask->microsFromNow();
284-
}
285-
private:
286-
/**
287-
* Finds and allocates the next free task, once this returns a task will either have been allocated, making task
288-
* manager storage bigger if needed, or it will return TASKMGR_INVALIDID otherwise.
289-
* @return either a taskID or TASKMGR_INVALIDID if a slot could not be allocated
290-
*/
291-
taskid_t findFreeTask();
292-
293-
/**
294-
* Removes an item from the task queue, so it is no longer in the run linked list. Note that there is a certain
295-
* amount of concurrency and it's possible that this may coincide with the task running.
296-
*
297-
* Thread safety: Must only be called on the queue
298-
* @param task the task to remove
299-
*/
300-
void removeFromQueue(TimerTask* task);
301-
302-
/**
303-
* Puts an item into the queue in time order, so the first to execute is at the top of the list.
304-
* @param tm the task to be added.
305-
*/
306-
void putItemIntoQueue(TimerTask* tm);
307-
308-
/**
309-
* When an interrupt occurs, this goes through all active tasks
310-
*/
311-
void dealWithInterrupt();
312-
};
313-
314-
/** the global task manager, this would normally be associated with the main runLoop. */
315-
extern TaskManager taskManager;
316-
317-
#endif //TASKMANAGER_IO_H
14+
#endif //TASKMANAGER_COMPAT_H

src/TaskManager.cpp renamed to src/TaskManagerIO.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
*/
55

66
#include "TaskPlatformDeps.h"
7-
#include "TaskManager.h"
7+
#include "TaskManagerIO.h"
88
#include "ExecWithParameter.h"
99

1010
TaskManager taskManager;

0 commit comments

Comments
 (0)