Merge pull request #2309 from mitza-oci/warnings
[ACE_TAO.git] / ACE / examples / Timer_Queue / Async_Timer_Queue_Test.cpp
blobb1e1f1367bf9e37529851648e3fe649615f6fb96
2 //=============================================================================
3 /**
4 * @file Async_Timer_Queue_Test.cpp
6 * This test exercises the <ACE_Asynch_Timer_Queue_Adapter>
7 * using an <ACE_Timer_Heap>.
9 * @author Douglas C. Schmidt <d.schmidt@vanderbilt.edu> and Sergio Flores-Gaitan <sergio@cs.wustl.edu>
11 //=============================================================================
14 #include "ace/OS_NS_sys_time.h"
15 #include "ace/Signal.h"
16 #include "ace/Timer_Heap.h"
17 #include "ace/Timer_Queue_Adapters.h"
19 #include "Async_Timer_Queue_Test.h"
22 // Hook method that is called to handle the expiration of a timer.
23 int
24 Async_Timer_Handler::handle_timeout (const ACE_Time_Value &tv,
25 const void *arg)
27 // Print some information here (note that this is not strictly
28 // signal-safe since the ACE logging mechanism uses functions that
29 // aren't guaranteed to work in all signal handlers).
30 ACE_DEBUG ((LM_DEBUG,
31 "handle_timeout() = (%d, %d) %d\n",
32 tv.sec (),
33 tv.usec (),
34 arg));
36 // Commit suicide!
37 delete this;
38 return 0;
41 // Initialize the Singleton pointer.
42 Async_Timer_Queue *Async_Timer_Queue::instance_ = 0;
44 // Implement the Singleton logic.
45 Async_Timer_Queue *
46 Async_Timer_Queue::instance ()
48 if (Async_Timer_Queue::instance_ == 0)
50 // Initialize with all signals enabled.
51 ACE_Sig_Set ss (1);
53 // But, don't block out SIGQUIT since we always want that
54 // signal to interrupt the program.
55 ss.sig_del (SIGQUIT);
57 ACE_NEW_RETURN (Async_Timer_Queue::instance_, Async_Timer_Queue (&ss), 0);
59 return Async_Timer_Queue::instance_;
62 // Sets the signal set to mask, for the timer queue.
64 Async_Timer_Queue::Async_Timer_Queue (ACE_Sig_Set *ss) :
65 tq_ (ss)
69 // Dump the contents of the queue when we receive ^C.
71 void
72 Async_Timer_Queue::dump ()
74 ACE_DEBUG ((LM_DEBUG, "begin dumping timer queue\n"));
76 // This iterator is implicitly protected since SIGINT and SIGALRM
77 // signals cannot occur while it is running.
79 for (ACE_Timer_Heap_Iterator iter (this->tq_.timer_queue ());
80 iter.item () != 0;
81 iter.next ())
82 iter.item ()->dump ();
84 ACE_DEBUG ((LM_DEBUG, "end dumping timer queue\n"));
87 // Schedule a timer.
89 void
90 Async_Timer_Queue::schedule (u_int microsecs)
92 ACE_Time_Value tv (0, microsecs);
94 // Create a new Event_Handler for our timer.
96 ACE_Event_Handler *eh;
97 ACE_NEW (eh, Async_Timer_Handler);
99 // Schedule the timer to run in the future.
100 long tid = this->tq_.schedule(eh,
101 0, // Note that our "magic cookie" ACT is always NULL.
102 ACE_OS::gettimeofday () + tv);
104 if (tid == -1)
105 ACE_ERROR ((LM_ERROR, "%p\n", "schedule_timer"));
108 // Cancel a timer.
110 void
111 Async_Timer_Queue::cancel (long timer_id)
113 ACE_DEBUG ((LM_DEBUG, "canceling %d\n", timer_id));
115 const void *act = 0;
117 if (this->tq_.cancel (timer_id, &act) == -1)
118 ACE_ERROR ((LM_ERROR, "%p\n", "cancel_timer"));
120 // In this case, the act will be 0, but it could be a real pointer
121 // in other cases.
122 delete (ACE_Event_Handler *) act;
125 // Schedule timer hook method. This method is called from the driver.
128 Async_Timer_Queue::schedule_timer (void *argument)
130 u_long useconds = *(int *)argument;
132 // Schedule a timer.
133 Async_Timer_Queue::instance ()->schedule (useconds);
135 return 0;
138 // Cancel timer hook method. Is called from the driver class.
141 Async_Timer_Queue::cancel_timer (void *argument)
143 u_long id = *(int *)argument;
145 // Cancel a timer.
146 Async_Timer_Queue::instance ()->cancel (id);
148 return 0;
151 // Dummy list timer hook method. The listing of timers is done from a
152 // signal handler using SIGINT, not from the driver.
155 Async_Timer_Queue::list_timer (void *)
157 // Display an error message.
158 ACE_ERROR_RETURN ((LM_ERROR, "invalid input\n"), 0);
161 // Dummy shutdown timer hook method. The shutdown of the timer queue
162 // is done with a signal handler using SIGQUIT, not from the driver.
165 Async_Timer_Queue::shutdown_timer (void *)
167 // Display an error message.
168 ACE_ERROR_RETURN ((LM_ERROR, "invalid input\n"), 0);
171 // Handler for the SIGINT and SIGQUIT signals.
173 static void
174 signal_handler (int signum)
176 ACE_DEBUG ((LM_DEBUG, "handling signal %S\n", signum));
178 switch (signum)
180 case SIGINT:
181 Async_Timer_Queue::instance ()->dump ();
182 break;
183 /* NOTREACHED */
185 #if !defined (ACE_LACKS_UNIX_SIGNALS)
186 case SIGQUIT:
187 ACE_ERROR ((LM_ERROR, "shutting down on SIGQUIT%a\n", 1));
188 /* NOTREACHED */
189 break;
190 #endif
194 // Register the signal handlers for SIGQUIT and SIGINT. We must
195 // ensure that the SIGINT handler isn't interrupted by SIGALRM.
196 // However, SIGQUIT is never blocked...
198 static void
199 register_signal_handlers ()
201 #if !defined (ACE_LACKS_UNIX_SIGNALS)
202 // Register SIGQUIT (never blocked).
203 ACE_Sig_Action sigquit ((ACE_SignalHandler) signal_handler, SIGQUIT);
204 ACE_UNUSED_ARG (sigquit);
205 #endif
207 // Don't let the SIGALRM interrupt the SIGINT handler!
208 ACE_Sig_Set ss;
209 ss.sig_add (SIGALRM);
211 // Register SIGINT (note that system calls will be restarted
212 // automatically).
213 ACE_Sig_Action sigint ((ACE_SignalHandler) signal_handler,
214 SIGINT,
216 SA_RESTART);
217 ACE_UNUSED_ARG (sigint);
220 // constructor
222 Async_Timer_Queue_Test_Driver::Async_Timer_Queue_Test_Driver ()
226 // displays the menu of options.
229 Async_Timer_Queue_Test_Driver::display_menu ()
231 // The menu of options provided to the user.
232 static char menu[] =
233 "****\n"
234 "1) schedule timer <usecs>\n"
235 "2) cancel timer <timer_id>\n"
236 "^C list timers\n"
237 "^\\ exit program\n";
239 ACE_DEBUG ((LM_DEBUG, "%s", menu));
240 return 0;
243 // Initializes the test driver.
246 Async_Timer_Queue_Test_Driver::init ()
248 typedef Command<Async_Timer_Queue, Async_Timer_Queue::ACTION> CMD;
250 // Initialize <Command> objects with their corresponding <Input_Task> methods.
251 ACE_NEW_RETURN (schedule_cmd_,
252 CMD (*Async_Timer_Queue::instance (),
253 &Async_Timer_Queue::schedule_timer),
254 -1);
256 ACE_NEW_RETURN (cancel_cmd_,
257 CMD (*Async_Timer_Queue::instance (),
258 &Async_Timer_Queue::cancel_timer),
259 -1);
261 ACE_NEW_RETURN (list_cmd_,
262 CMD (*Async_Timer_Queue::instance (),
263 &Async_Timer_Queue::list_timer),
264 -1);
266 ACE_NEW_RETURN (shutdown_cmd_,
267 CMD (*Async_Timer_Queue::instance (),
268 &Async_Timer_Queue::shutdown_timer),
269 -1);
271 register_signal_handlers ();
273 return 0;