An Overlay-based
Virtual Network Substrate
SpoVNet

source: source/ariba/utility/system/SystemQueue.h @ 7468

Last change on this file since 7468 was 7468, checked in by Christoph Mayer, 14 years ago

-timer delete fix (noch auskommentiert), -interface cleanup

File size: 7.1 KB
Line 
1// [License]
2// The Ariba-Underlay Copyright
3//
4// Copyright (c) 2008-2009, Institute of Telematics, UniversitÀt Karlsruhe (TH)
5//
6// Institute of Telematics
7// UniversitÀt Karlsruhe (TH)
8// Zirkel 2, 76128 Karlsruhe
9// Germany
10//
11// Redistribution and use in source and binary forms, with or without
12// modification, are permitted provided that the following conditions are
13// met:
14//
15// 1. Redistributions of source code must retain the above copyright
16// notice, this list of conditions and the following disclaimer.
17// 2. Redistributions in binary form must reproduce the above copyright
18// notice, this list of conditions and the following disclaimer in the
19// documentation and/or other materials provided with the distribution.
20//
21// THIS SOFTWARE IS PROVIDED BY THE INSTITUTE OF TELEMATICS ``AS IS'' AND
22// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ARIBA PROJECT OR
25// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
26// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
27// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
28// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
29// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32//
33// The views and conclusions contained in the software and documentation
34// are those of the authors and should not be interpreted as representing
35// official policies, either expressed or implied, of the Institute of
36// Telematics.
37// [License]
38
39#ifndef SYSTEMQUEUE_H_
40#define SYSTEMQUEUE_H_
41
42#include <vector>
43#include <cassert>
44#include "SystemEvent.h"
45#include "SystemEventListener.h"
46#include "ariba/utility/logging/Logging.h"
47#include <boost/date_time.hpp>
48#include <boost/cstdint.hpp>
49
50#ifdef UNDERLAY_OMNET
51  #include <csimplemodule.h>
52  #include <cmessage.h>
53  #include <macros.h>
54#else
55  #include <boost/thread/mutex.hpp>
56  #include <boost/thread/thread.hpp>
57  #include <boost/thread/condition_variable.hpp>
58  #include <boost/utility.hpp>
59  #include <boost/bind.hpp>
60#endif
61
62using std::vector;
63using boost::posix_time::ptime;
64
65namespace ariba {
66namespace utility {
67
68/**
69 * This class implements a simple system event queue to allow
70 * a simulation of cooperative multitasking. It also allows
71 * events to be scheduled from other tasks. This allows
72 * dispatching asynchronous tasks.
73 *
74 * @author Christoph Mayer, Sebastian Mies
75 */
76
77#ifndef UNDERLAY_OMNET
78class SystemQueue : private boost::noncopyable {
79#else
80class SystemQueue : public cSimpleModule {
81#endif
82       
83        use_logging_h(SystemQueue);
84        friend class EnterMethod;
85public:
86        /**
87         * Get the SystemQueue singleton instance.
88         */
89        static SystemQueue& instance() {
90                static SystemQueue _inst;
91                return _inst;
92        }
93
94#ifdef UNDERLAY_OMNET
95        /**
96         * Prevent deletion of this module
97         * by implementing the virtual method
98         * and doing nothing in it
99         */
100        virtual void deleteModule(){}
101#endif
102
103        /**
104         * This methods schedules a given event.
105         *
106         * @param The event to be scheduled
107         * @param The delay in milli-seconds
108         */
109        void scheduleEvent( const SystemEvent& event, uint32_t delay = 0 );
110
111        /**
112         * Starts the processing and waiting for events.
113         * Use <code>cancel()</code> to end system queue processing and
114         * <code>isEmpty()</code> to check wheter the queue is empty.
115         */
116        void run();
117
118        /**
119         * Cancels the system queue and ends the processing after the
120         * currently processed event is processed.
121         *
122         * This method is thread-safe.
123         */
124        void cancel();
125
126        /**
127         * Drop all queued events for that listener
128         */
129        void dropAll( const SystemEventListener* mlistener);
130
131        /**
132         * Check wheter this queue has items or not.
133         *
134         * @return True, if this queue is empty.
135         */
136        bool isEmpty();
137
138        /**
139         * Is the system queue already started and running?
140         *
141         * @return True, if the system queue is running.
142         */
143        bool isRunning();
144
145protected:
146
147        /**
148         * Aqcuire the mutex
149         */
150        void enterMethod();
151
152        /**
153         * Leave the mutex
154         */
155        void leaveMethod();
156
157        /**
158         * Constructs a system queue.
159         */
160        SystemQueue();
161
162        /**
163         * Destroys the system queue. Beware that all events
164         * are canceled
165         */
166        ~SystemQueue();
167
168#ifdef UNDERLAY_OMNET
169        virtual void handleMessage( cMessage* msg );
170#endif
171
172private:
173
174#ifndef UNDERLAY_OMNET
175        typedef vector<SystemEvent> EventQueue;
176
177        //********************************************************
178
179        class QueueThread {
180        public:
181                QueueThread(QueueThread* _transferQueue = NULL);
182                virtual ~QueueThread();
183                void run();
184                void cancel();
185                bool isEmpty();
186                void insert( const SystemEvent& event, uint32_t delay );
187                void enter();
188                void leave();
189                void dropAll( const SystemEventListener* mlistener);
190
191        protected:
192                virtual void onItemInserted( const SystemEvent& event ) = 0;
193                virtual void onNextQueueItem( const SystemEvent& event ) = 0;
194                QueueThread* transferQueue;
195                EventQueue eventsQueue;
196                boost::mutex queueMutex;
197        private:
198                boost::thread* queueThread;
199                static void threadFunc( QueueThread* obj );
200                boost::condition_variable itemsAvailable;
201                volatile bool running;
202        }; // class QueueThread
203
204        //********************************************************
205
206        class QueueThreadDirect : public QueueThread {
207        public:
208                QueueThreadDirect();
209                ~QueueThreadDirect();
210        protected:
211                virtual void onItemInserted( const SystemEvent& event );
212                virtual void onNextQueueItem( const SystemEvent& event );
213        }; // class QueueThreadDirect
214
215        //********************************************************
216
217        class QueueThreadDelay : public QueueThread {
218        public:
219                QueueThreadDelay(QueueThread* _transferQueue = NULL);
220                ~QueueThreadDelay();
221        protected:
222                virtual void onItemInserted( const SystemEvent& event );
223                virtual void onNextQueueItem( const SystemEvent& event );
224        private:
225                volatile bool isSleeping;
226                ptime sleepStart;
227                boost::mutex sleepMutex;
228                boost::condition_variable sleepCond;
229        }; // class QueueThreadDelay
230
231        //********************************************************
232
233        QueueThreadDirect directScheduler;
234        QueueThreadDelay delayScheduler;
235        volatile bool systemQueueRunning;
236#endif
237
238}; // class SystemQueue
239
240#ifdef UNDERLAY_OMNET
241
242#if 0
243        //
244        // the system queue must be a singleton in simulations, too.
245        // and to include it in the simulation the module is defined
246        // as submodule in every SpoVNet host. Therefore we hack the
247        // Define_Module (see omnet/includes/macros.h) the way we need
248        // it with our singleton ...
249        //
250        // this is the macro definition from macros.h
251        //
252        // #define Define_Module(CLASSNAME) /backslash
253        //   static cModule *CLASSNAME##__create() {return new CLASSNAME();} /backslash
254        //   EXECUTE_ON_STARTUP(CLASSNAME##__mod, modtypes.instance()->add(new cModuleType(#CLASSNAME,#CLASSNAME,(ModuleCreateFunc)CLASSNAME##__create));)
255        //
256        // and this is how we do it :)
257        //
258#endif
259
260        static cModule* SystemQueue__create() {
261                return &SystemQueue::instance();
262        }
263
264        EXECUTE_ON_STARTUP(SystemQueue__mod, modtypes.instance()->add(new cModuleType("SystemQueue","SystemQueue",(ModuleCreateFunc)SystemQueue__create));)
265
266#endif
267
268}} // spovnet, common
269
270#endif /* SYSTEMQUEUE_H_ */
Note: See TracBrowser for help on using the repository browser.