3 //=============================================================================
5 * @file XtAthenaReactor_Test.cpp
7 * This is a simple test that illustrates the possibility to integrate
8 * ACE to the X Main Loop. This program uses ACE_XtReactor class to
9 * schedule three additional event sources:
10 * 1. Events from button "Stop Test" (registed with XtAddCallback)
11 * 2. Events from button "Press Me" (registed with XtAddCallback)
12 * 3. Events from X timer (registed with XtAppAddTimeOut)
13 * 4. Events from ACE timer (registed with ACE_XtReactor::schedule_timer)
14 * 5. Events from the TCP/IP channel using ACE_Acceptor
15 * No command line arguments are needed to run the test.
16 * Programs needs Athena Widgets to be compiled and run.
18 * @author Kirill Rybaltchenko <Kirill.Rybaltchenko@cern.ch>
20 //=============================================================================
23 #include "test_config.h"
24 #include "ace/XtReactor/XtReactor.h"
25 #include "ace/Event_Handler.h"
26 #include "ace/Acceptor.h"
27 #include "ace/SOCK_Acceptor.h"
28 #include "ace/SOCK_Connector.h"
29 #include "ace/Service_Config.h"
30 #include "ace/Thread_Manager.h"
32 #include "ace/OS_NS_unistd.h"
34 #include /**/ <X11/Intrinsic.h>
35 #include /**/ <X11/Xatom.h>
36 #include /**/ <X11/Shell.h>
37 #include /**/ <X11/StringDefs.h>
39 #if defined (ACE_HAS_ATHENA3D)
40 # include /**/ <X11/Xaw3d/Command.h>
41 # include /**/ <X11/Xaw3d/Label.h>
42 # include /**/ <X11/Xaw3d/Box.h>
44 # include /**/ <X11/Xaw/Command.h>
45 # include /**/ <X11/Xaw/Label.h>
46 # include /**/ <X11/Xaw/Box.h>
49 static void set_label(Widget w
, const char *p
)
51 XtVaSetValues (w
, XtNlabel
, p
, static_cast<void *>(0));
53 #define LABEL_WIDGET labelWidgetClass
54 #define BUTTON_WIDGET commandWidgetClass
55 #define PRESS_ME_CALLBACK XtNcallback
56 static Widget
create_box(Widget parent
, const char * name
)
58 return XtCreateWidget( (char*) name
, boxWidgetClass
, parent
, 0, 0);
62 static const u_short SERV_TCP_PORT
= 6670;
64 // counter for events from "Press Me" button.
65 static int count1
= 0;
67 // counter for events from X Timer.
68 static int count2
= 0;
70 // counter for events from ACE Timer.
71 static int count3
= 0;
73 // Callback for "Stop Test" buton - quit the program.
75 Quit (Widget
, XtPointer
, XtPointer
)
88 " (%P) Client: Starting...\n"));
90 ACE_SOCK_Stream stream
;
91 ACE_SOCK_Connector connector
;
92 ACE_OS::snprintf (buf
, 100, "Client: the life was good!");
94 mes_len
= (int) htonl (ACE_OS::strlen (buf
) + 1);
96 if (connector
.connect (stream
,
97 ACE_INET_Addr (SERV_TCP_PORT
,
98 ACE_DEFAULT_SERVER_HOST
)) == -1)
107 ACE_OS::strlen (buf
) + 1) == -1)
109 ACE_ERROR ((LM_ERROR
,
113 if (stream
.close () == -1)
114 ACE_ERROR ((LM_ERROR
,
118 ACE_DEBUG ((LM_DEBUG
,
119 "(%P) Client: Message has been sent, about to exit...\n"));
123 // Callback for "Press Me" button.
126 inc_count (Widget
, XtPointer client_data
, XtPointer
)
130 ACE_OS::snprintf (new_string
, 80, "Events: [%d] [%d] [%d]",
131 count1
++, count2
, count3
);
133 set_label((Widget
) client_data
, new_string
);
136 // Callback for X Timer.
139 inc_tmo (void *w
,XtIntervalId
*)
145 ACE_OS::snprintf (new_string
, 80, "Events: [%d] [%d] [%d]",
146 count1
, count2
++, count3
);
148 set_label((Widget
) w
, new_string
);
150 (void) XtAppAddTimeOut (XtWidgetToApplicationContext ((Widget
) w
),
156 class EV_handler
: public ACE_Event_Handler
159 virtual int handle_timeout (const ACE_Time_Value
&,
163 ACE_OS::snprintf (new_string
, 80, "Events: [%d] [%d] [%d]",
164 count1
, count2
, count3
++);
165 set_label((Widget
) arg
, new_string
);
170 class Connection_Handler
: public ACE_Svc_Handler
<ACE_SOCK_STREAM
, ACE_NULL_SYNCH
>
173 //FUZZ: disable check_for_lack_ACE_OS
174 virtual int open (void *)
176 //FUZZ: enable check_for_lack_ACE_OS
179 ssize_t ret
= this->peer ().recv_n ((char *) &head
,
181 if (ret
!= sizeof (int))
182 ACE_ERROR_RETURN ((LM_ERROR
,
187 ret
= this->peer ().recv_n (buf
,
190 if (ret
!= (int) ntohl (head
))
191 ACE_ERROR_RETURN ((LM_ERROR
,
195 ACE_DEBUG ((LM_DEBUG
,
196 " (%P)Server (ACE_SOCKET channel message): [%s]\n",
202 #if defined (HummingBird_X)
203 extern "C" void HCLXmInit ();
204 #endif /* HummingBird_X */
207 run_main (int argc
, ACE_TCHAR
*argv
[])
209 ACE_START_TEST (ACE_TEXT ("XtAthenaReactor_Test"));
211 XtAppContext app_context
;
212 Widget topLevel
, goodbye
, PressMe
, lbl
, digits_rc
;
215 #if defined (HummingBird_X)
217 #endif /* HummingBird_X */
218 topLevel
= XtVaAppInitialize (&app_context
,
225 static_cast<void *>(0));
227 digits_rc
= create_box(topLevel
, "digits_rc");
229 //"Stop Test" button.
230 goodbye
= XtCreateWidget ( (char *) "goodbye",
235 set_label(goodbye
, "Stop Test");
238 PressMe
= XtCreateWidget ((char *) "PressMe",
244 //Display for event counter
245 lbl
= XtCreateWidget ((char *) "label_for_event_one",
250 set_label(lbl
, "label_for_all_events");
252 children
[ac
++] = goodbye
;
253 children
[ac
++] = PressMe
;
254 children
[ac
++] = lbl
;
255 XtManageChildren (children
, ac
);
256 XtManageChild (digits_rc
);
258 //Register callback for "Stop Test" button
259 XtAddCallback (goodbye
, PRESS_ME_CALLBACK
, Quit
, 0);
261 //Register callback for "Press Me" button
262 XtAddCallback (PressMe
,
267 // Register callback for X Timer
268 (void) XtAppAddTimeOut (app_context
,
273 XtRealizeWidget (topLevel
);
275 // It will perform X Main Loop
276 ACE_XtReactor
reactor (app_context
);
278 ACE_Reactor
r (&reactor
);
280 //Event Handler for ACE Timer.
283 ACE_Acceptor
<Connection_Handler
, ACE_SOCK_ACCEPTOR
> acceptor
;
285 if (acceptor
.open (ACE_INET_Addr ((u_short
) SERV_TCP_PORT
),
287 ACE_ERROR_RETURN ((LM_ERROR
,
292 if (reactor
.schedule_timer (&evh
,
295 ACE_Time_Value (2))==-1)
296 ACE_ERROR_RETURN ((LM_ERROR
,
297 " (%P|%t) can't register with reactor\n"),
300 ACE_Thread_Manager::instance ()->spawn ((ACE_THR_FUNC
) client
,
302 THR_NEW_LWP
| THR_DETACHED
);
304 XtAppMainLoop (XtWidgetToApplicationContext (topLevel
));