RemoteDrawingEngine: Reduce RP_READ_BITMAP result timeout.
[haiku.git] / src / kits / tracker / TaskLoop.h
blobcca285273eeefe6f804682e323525adba6baa340
1 /*
2 Open Tracker License
4 Terms and Conditions
6 Copyright (c) 1991-2000, Be Incorporated. All rights reserved.
8 Permission is hereby granted, free of charge, to any person obtaining a copy of
9 this software and associated documentation files (the "Software"), to deal in
10 the Software without restriction, including without limitation the rights to
11 use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
12 of the Software, and to permit persons to whom the Software is furnished to do
13 so, subject to the following conditions:
15 The above copyright notice and this permission notice applies to all licensees
16 and shall be included in all copies or substantial portions of the Software.
18 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF TITLE, MERCHANTABILITY,
20 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 BE INCORPORATED BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF, OR IN CONNECTION
23 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 Except as contained in this notice, the name of Be Incorporated shall not be
26 used in advertising or otherwise to promote the sale, use or other dealings in
27 this Software without prior written authorization from Be Incorporated.
29 Tracker(TM), Be(R), BeOS(R), and BeIA(TM) are trademarks or registered trademarks
30 of Be Incorporated in the United States and other countries. Other brand product
31 names are registered trademarks or trademarks of their respective holders.
32 All rights reserved.
34 #ifndef _TASK_LOOP_H
35 #define _TASK_LOOP_H
38 // Delayed Tasks, Periodic Delayed Tasks, Periodic Delayed Tasks with timeout,
39 // Run when idle tasks, accumulating delayed tasks
42 #include <Locker.h>
43 #include <ObjectList.h>
45 #include "FunctionObject.h"
48 namespace BPrivate {
50 // Task flavors
52 class DelayedTask {
53 public:
54 DelayedTask(bigtime_t delay);
55 virtual ~DelayedTask();
57 virtual bool RunIfNeeded(bigtime_t currentTime) = 0;
58 // returns true if done and should not be called again
60 bigtime_t RunAfterTime() const;
62 protected:
63 bigtime_t fRunAfter;
67 // called once after a specified delay
68 class OneShotDelayedTask : public DelayedTask {
69 public:
70 OneShotDelayedTask(FunctionObject* functor, bigtime_t delay);
71 virtual ~OneShotDelayedTask();
73 virtual bool RunIfNeeded(bigtime_t currentTime);
75 protected:
76 FunctionObject* fFunctor;
80 // called periodically till functor return true
81 class PeriodicDelayedTask : public DelayedTask {
82 public:
83 PeriodicDelayedTask(FunctionObjectWithResult<bool>* functor,
84 bigtime_t initialDelay, bigtime_t period);
85 virtual ~PeriodicDelayedTask();
87 virtual bool RunIfNeeded(bigtime_t currentTime);
89 protected:
90 bigtime_t fPeriod;
91 FunctionObjectWithResult<bool>* fFunctor;
95 // called periodically till functor returns true or till time out
96 class PeriodicDelayedTaskWithTimeout : public PeriodicDelayedTask {
97 public:
98 PeriodicDelayedTaskWithTimeout(FunctionObjectWithResult<bool>* functor,
99 bigtime_t initialDelay, bigtime_t period, bigtime_t timeout);
101 virtual bool RunIfNeeded(bigtime_t currentTime);
103 protected:
104 bigtime_t fTimeoutAfter;
108 // after initial delay starts periodically calling functor if system is idle
109 // until functor returns true
110 class RunWhenIdleTask : public PeriodicDelayedTask {
111 public:
112 RunWhenIdleTask(FunctionObjectWithResult<bool>* functor,
113 bigtime_t initialDelay, bigtime_t idleFor, bigtime_t heartBeat);
114 virtual ~RunWhenIdleTask();
116 virtual bool RunIfNeeded(bigtime_t currentTime);
118 protected:
119 void ResetIdleTimer(bigtime_t currentTime);
120 bool IdleTimerExpired(bigtime_t currentTime);
121 bool StillIdle(bigtime_t currentTime);
122 bool IsIdle(bigtime_t currentTime, float taskOverhead);
124 bigtime_t fIdleFor;
126 enum State {
127 kInitialDelay,
128 kInitialIdleWait,
129 kInIdleState
132 State fState;
133 bigtime_t fActivityLevelStart;
134 bigtime_t fActivityLevel;
135 bigtime_t fLastCPUTooBusyTime;
137 private:
138 typedef PeriodicDelayedTask _inherited;
142 // This class is used for clumping up function objects that
143 // can be done as a single object. For instance the mime
144 // notification mechanism sends out multiple notifications on
145 // a single change and we need to accumulate the resulting
146 // icon update into a single one
147 class AccumulatingFunctionObject : public FunctionObject {
148 public:
149 virtual bool CanAccumulate(const AccumulatingFunctionObject*) const = 0;
150 virtual void Accumulate(AccumulatingFunctionObject*) = 0;
154 // task loop is a separate thread that hosts tasks that keep getting called
155 // periodically; if a task returns true, it is done - it gets removed from
156 // the list and deleted
157 class TaskLoop {
158 public:
159 TaskLoop(bigtime_t heartBeat = 10000);
160 virtual ~TaskLoop();
162 void RunLater(DelayedTask*);
163 void RunLater(FunctionObject* functor, bigtime_t delay);
164 // execute a function object after a delay
166 void RunLater(FunctionObjectWithResult<bool>* functor, bigtime_t delay,
167 bigtime_t period);
168 // periodically execute function object after initial delay until
169 // function object returns true
171 void RunLater(FunctionObjectWithResult<bool>* functor, bigtime_t delay,
172 bigtime_t period, bigtime_t timeout);
173 // periodically execute function object after initial delay until
174 // function object returns true or timeout is reached
176 void AccumulatedRunLater(AccumulatingFunctionObject* functor,
177 bigtime_t delay, bigtime_t maxAccumulatingTime = 0,
178 int32 maxAccumulateCount = 0);
179 // will search the delayed task loop for other accumulating functors
180 // and will accumulate with them, else will create a new delayed task
181 // the task will no longer accumulate if past the
182 // <maxAccumulatingTime> delay unless <maxAccumulatingTime> is zero
183 // no more than <maxAccumulateCount> will get accumulated, unless
184 // <maxAccumulateCount> is zero
186 void RunWhenIdle(FunctionObjectWithResult<bool>* functor,
187 bigtime_t initialDelay, bigtime_t idleTime,
188 bigtime_t heartBeat = 1000000);
189 // after initialDelay starts looking for a slot when the system is
190 // idle for at least idleTime
192 protected:
193 void AddTask(DelayedTask*);
194 void RemoveTask(DelayedTask*);
196 bool Pulse();
197 // return true if quitting
198 bigtime_t LatestRunTime() const;
200 virtual bool KeepPulsingWhenEmpty() const = 0;
201 virtual void StartPulsingIfNeeded() = 0;
203 BLocker fLock;
204 BObjectList<DelayedTask> fTaskList;
205 bigtime_t fHeartBeat;
209 class StandAloneTaskLoop : public TaskLoop {
210 // this task loop can work on it's own, just instantiate it
211 // and use it; It has to start it's own thread
212 public:
213 StandAloneTaskLoop(bool keepThread, bigtime_t heartBeat = 400000);
214 ~StandAloneTaskLoop();
216 protected:
217 void AddTask(DelayedTask*);
219 private:
220 static status_t RunBinder(void*);
221 void Run();
223 virtual bool KeepPulsingWhenEmpty() const;
224 virtual void StartPulsingIfNeeded();
226 volatile bool fNeedToQuit;
227 volatile thread_id fScanThread;
228 bool fKeepThread;
230 typedef TaskLoop _inherited;
234 class PiggybackTaskLoop : public TaskLoop {
235 // this TaskLoop needs periodic calls from a viewable's Pulse
236 // or some similar pulsing mechanism
237 // it does not have to need it's own thread, instead it uses an existing
238 // thread of a looper, etc.
239 public:
240 PiggybackTaskLoop(bigtime_t heartBeat = 100000);
241 ~PiggybackTaskLoop();
242 virtual void PulseMe();
243 private:
244 virtual bool KeepPulsingWhenEmpty() const;
245 virtual void StartPulsingIfNeeded();
247 bigtime_t fNextHeartBeatTime;
248 bool fPulseMe;
252 inline bigtime_t
253 DelayedTask::RunAfterTime() const
255 return fRunAfter;
258 } // namespace BPrivate
260 using namespace BPrivate;
263 #endif // _TASK_LOOP_H