1 //=============================================================================
3 * @file SOCK_Dgram_Test.cpp
5 * Tests that a call to open with an any address binds to the any address
6 * for the protocol passed in.
8 * This test uses the same test setup as SOCK_Test.
10 * @author Brian Buesker (bbuesker@qualcomm.com)
12 //=============================================================================
15 #include "test_config.h"
16 #include "ace/OS_NS_string.h"
17 #include "ace/OS_NS_sys_wait.h"
18 #include "ace/Thread.h"
19 #include "ace/Thread_Manager.h"
20 #include "ace/SOCK_Dgram.h"
21 #include "ace/Log_Msg.h"
22 #include "ace/Time_Value.h"
23 #include "ace/OS_NS_unistd.h"
25 #define SERVER_PORT 20000
26 #define TEST_DATA ACE_TEXT ("UDP Open Test")
31 ACE_INET_Addr
*remote_addr
= (ACE_INET_Addr
*) arg
;
32 ACE_INET_Addr server_addr
, peer_addr
;
33 ACE_SOCK_Dgram cli_dgram
;
34 ACE_Time_Value
timeout (1);
37 ACE_TCHAR hostname_string
[100];
39 if (remote_addr
->get_type () == AF_INET
)
41 server_addr
.set (remote_addr
->get_port_number (),
44 remote_addr
->get_type ());
46 #if defined (ACE_HAS_IPV6)
49 server_addr
.set (remote_addr
->get_port_number(),
52 remote_addr
->get_type ());
54 #endif /* ACE_HAS_IPV6 */
56 server_addr
.addr_to_string (hostname_string
, 100);
58 ACE_TEXT ("(%P|%t) starting client UDP send to %s\n"),
61 if (cli_dgram
.open (ACE_Addr::sap_any
, server_addr
.get_type ()) == -1)
64 ACE_TEXT("(%P|%t) protocol %d, %p\n"),
65 server_addr
.get_type (),
66 ACE_TEXT ("SOCK_Dgram open")));
71 if (remote_addr
->get_type () == AF_INET
) {
72 #if defined (ACE_RECVPKTINFO)
74 if (cli_dgram
.set_option(IPPROTO_IP
, ACE_RECVPKTINFO
, &sockopt
, sizeof sockopt
) == -1) {
76 ACE_TEXT("(%P|%t) setsockopt failed\n")));
80 ACE_TEXT("(%P|%t) setsockopt succeeded\n")));
84 #if defined (ACE_HAS_IPV6)
86 #if defined (ACE_RECVPKTINFO6)
88 if (cli_dgram
.set_option(IPPROTO_IPV6
, ACE_RECVPKTINFO6
, &sockopt
, sizeof sockopt
) == -1) {
90 ACE_TEXT("(%P|%t) setsockopt failed\n")));
94 ACE_TEXT("(%P|%t) setsockopt succeeded\n")));
101 if (cli_dgram
.send (TEST_DATA
, sizeof (TEST_DATA
), server_addr
) == -1)
104 ACE_TEXT("(%P|%t) UDP send to %s %p\n"),
106 ACE_TEXT ("failed")));
111 ACE_INET_Addr local_addr
, to_addr
;
112 cli_dgram
.get_local_addr(local_addr
);
114 if (local_addr
.get_type () == AF_INET
)
116 local_addr
.set (local_addr
.get_port_number (),
119 local_addr
.get_type ());
120 to_addr
.set (9999, ACE_LOCALHOST
, 1, AF_INET
);
122 #if defined (ACE_HAS_IPV6)
125 local_addr
.set (local_addr
.get_port_number(),
128 local_addr
.get_type ());
129 to_addr
.set (9999, ACE_IPV6_LOCALHOST
, 1, AF_INET6
);
131 #endif /* ACE_HAS_IPV6 */
133 #if defined(ACE_LACKS_RECVMSG)
134 ssize_t rcv_cnt
= cli_dgram
.recv (buf
,
141 // Some platforms define iov_base as char* instead of void*.
142 iov
[0].iov_base
= (char *)buf
;
143 iov
[0].iov_len
= sizeof buf
;
145 ssize_t rcv_cnt
= cli_dgram
.recv (iov
,
157 ACE_TEXT("(%P|%t) UDP recv on proto %d timed out\n"),
158 server_addr
.get_type ()));
163 ACE_TEXT("(%P|%t) UDP recv on proto %d %p\n"),
164 server_addr
.get_type (),
165 ACE_TEXT("failed")));
170 // recv() ok, check data, 'from', and 'to' address
171 size_t rcv_siz
= static_cast<size_t> (rcv_cnt
);
172 if (rcv_siz
!= sizeof (TEST_DATA
))
174 ACE_ERROR ((LM_ERROR
,
175 ACE_TEXT ("(%P|%t) recv cnt %B; should be %B\n"),
177 sizeof (TEST_DATA
)));
181 buf
[rcv_siz
/sizeof (ACE_TCHAR
)] = '\0';
182 if (ACE_OS::strncmp (buf
, TEST_DATA
, ACE_OS::strlen (TEST_DATA
)))
183 ACE_ERROR ((LM_ERROR
,
184 ACE_TEXT ("(%P|%t) recv string should be %s; ")
185 ACE_TEXT (" but is %s\n"),
188 if (peer_addr
.get_type () != server_addr
.get_type ())
189 ACE_ERROR ((LM_ERROR
,
190 ACE_TEXT ("(%P|%t) recv addr type %d; should be %d\n"),
191 peer_addr
.get_type (),
192 server_addr
.get_type ()));
193 if (peer_addr
.get_size () != server_addr
.get_size ())
194 ACE_ERROR ((LM_ERROR
,
195 ACE_TEXT ("(%P|%t) recv addr size %d; should be %d\n"),
196 peer_addr
.get_size (),
197 server_addr
.get_size ()));
198 #if (defined ACE_RECVPKTINFO6 || defined ACE_RECVPKTINFO) && !defined ACE_FACE_SAFETY_EXTENDED
199 if (local_addr
!= to_addr
)
200 ACE_ERROR ((LM_ERROR
,
201 ACE_TEXT ("(%P|%t) local addr is not equal to sent-to addr\n")));
214 ACE_SOCK_Dgram
*server_dgram
= (ACE_SOCK_Dgram
*) arg
;
215 ACE_INET_Addr peer_addr
;
218 ACE_TCHAR hostname_string
[100];
221 if ((rcv_cnt
= server_dgram
->recv (buf
, sizeof (buf
), peer_addr
, 0)) == -1)
223 ACE_ERROR((LM_ERROR
, ACE_TEXT("(%P|%t) %p\n"), ACE_TEXT("server recv")));
227 // recv() ok, check data and 'from' address
228 size_t rcv_siz
= static_cast<size_t> (rcv_cnt
);
229 if (rcv_siz
!= sizeof (TEST_DATA
))
231 ACE_ERROR ((LM_ERROR
,
232 ACE_TEXT ("(%P|%t) recv cnt %B; should be %B\n"),
234 sizeof (TEST_DATA
)));
238 buf
[rcv_siz
/ sizeof (ACE_TCHAR
)] = '\0';
239 if (ACE_OS::strncmp (buf
, TEST_DATA
, ACE_OS::strlen (TEST_DATA
)))
240 ACE_ERROR ((LM_ERROR
,
241 ACE_TEXT ("(%P|%t) recv string should be %s; ")
242 ACE_TEXT (" but is %s\n"),
246 if (0 == peer_addr
.addr_to_string (hostname_string
,
247 sizeof (hostname_string
)))
248 ACE_DEBUG ((LM_DEBUG
,
249 ACE_TEXT ("(%P|%t) Echoing data to %s\n"),
252 ACE_ERROR ((LM_ERROR
,
253 ACE_TEXT ("(%P|%t) %p\n"),
254 ACE_TEXT ("addr_to_string")));
255 if (server_dgram
->send (TEST_DATA
, sizeof (TEST_DATA
),
259 ACE_TEXT("(%P|%t) %p\n"),
260 ACE_TEXT("Server UDP send failed")));
263 server_dgram
->close ();
271 ACE_SOCK_Dgram server_dgram
;
272 ACE_INET_Addr server_addr
;
274 if (proto
== AF_INET
)
276 server_addr
.set (SERVER_PORT
, ACE_LOCALHOST
, 1, proto
);
278 #if defined (ACE_HAS_IPV6)
281 server_addr
.set (SERVER_PORT
, ACE_IPV6_LOCALHOST
, 1, proto
);
283 #endif /* ACE_HAS_IPV6 */
285 // Bind UDP server to the appropriate port
286 if (server_dgram
.open (server_addr
, proto
) == -1)
288 ACE_ERROR_RETURN ((LM_ERROR
,
289 ACE_TEXT ("(%P|%t) %p\n"),
290 ACE_TEXT ("server dgram open")),
295 if (server_addr
.get_port_number() != SERVER_PORT
)
297 ACE_TCHAR hostname_string
[100];
298 server_addr
.addr_to_string (hostname_string
, 100);
299 ACE_ERROR_RETURN ((LM_ERROR
,
300 ACE_TEXT("(%P|%t) Portnumber has unexpected value of %d on host %s\n"),
301 server_addr
.get_port_number(), hostname_string
), 1);
305 ACE_DEBUG ((LM_DEBUG
,
306 ACE_TEXT ("(%P|%t) started server at proto %d, port %d\n"),
308 server_addr
.get_port_number ()));
309 #if !defined (ACE_LACKS_FORK)
310 switch (ACE_OS::fork (ACE_TEXT ("child")))
313 ACE_ERROR_BREAK ((LM_ERROR
,
314 ACE_TEXT ("(%P|%t) %p\n"),
315 ACE_TEXT ("fork failed")));
318 client (&server_addr
);
322 server ((void *) &server_dgram
);
325 #elif defined (ACE_HAS_THREADS)
326 if (ACE_Thread_Manager::instance ()->spawn
327 (ACE_THR_FUNC (server
),
328 (void *) &server_dgram
,
329 THR_NEW_LWP
| THR_DETACHED
) == -1)
330 ACE_ERROR_RETURN ((LM_ERROR
,
331 ACE_TEXT ("(%P|%t) %p\n"),
332 ACE_TEXT ("thread create failed")),
335 if (ACE_Thread_Manager::instance ()->spawn
336 (ACE_THR_FUNC (client
),
337 (void *) &server_addr
,
338 THR_NEW_LWP
| THR_DETACHED
) == -1)
339 ACE_ERROR_RETURN ((LM_ERROR
,
340 ACE_TEXT ("(%P|%t) %p\n"),
341 ACE_TEXT ("thread create failed")),
344 // Wait for the threads to exit.
345 ACE_Thread_Manager::instance ()->wait ();
348 ACE_TEXT ("(%P|%t) ")
349 ACE_TEXT ("only one thread may be run ")
350 ACE_TEXT ("in a process on this platform\n")));
351 #endif /* ACE_HAS_THREADS */
354 server_dgram
.close ();
360 int run_main (int, ACE_TCHAR
*[])
362 ACE_START_TEST (ACE_TEXT ("SOCK_Dgram_Test"));
364 int retval
= spawn (AF_INET
);
366 #if defined (ACE_HAS_IPV6)
370 retval
= spawn (AF_INET6
);
373 #endif /* ACE_HAS_IPV6 */