Revert "Use a variable on the stack to not have a temporary in the call"
[ACE_TAO.git] / TAO / tests / RTCORBA / Banded_Connections / server.cpp
blob681bbad7e11cedce4f428fc8173e3d994a5d8575
1 #include "testS.h"
2 #include "ace/Get_Opt.h"
3 #include "ace/Read_Buffer.h"
4 #include "tao/RTCORBA/RTCORBA.h"
5 #include "tao/RTPortableServer/RTPortableServer.h"
6 #include "../check_supported_priorities.cpp"
8 class Test_i : public POA_Test
10 public:
11 Test_i (CORBA::ORB_ptr orb,
12 RTCORBA::PriorityBands &bands);
14 void test_method (CORBA::Boolean client_propagated,
15 CORBA::Short priority);
17 //FUZZ: disable check_for_lack_ACE_OS
18 void shutdown ();
19 //FUZZ: enable check_for_lack_ACE_OS
21 private:
22 CORBA::ORB_var orb_;
23 RTCORBA::PriorityBands &bands_;
24 RTCORBA::Current_var rt_current_;
27 Test_i::Test_i (CORBA::ORB_ptr orb,
28 RTCORBA::PriorityBands &bands)
29 : orb_ (CORBA::ORB::_duplicate (orb)),
30 bands_ (bands),
31 rt_current_ ()
33 // We resolve and store the RT Current for later use.
34 CORBA::Object_var obj =
35 this->orb_->resolve_initial_references ("RTCurrent");
37 this->rt_current_ =
38 RTCORBA::Current::_narrow (obj.in ());
41 void
42 Test_i::test_method (CORBA::Boolean client_propagated,
43 CORBA::Short client_priority)
45 // Get the upcall thread's priority.
46 CORBA::Short server_priority =
47 this->rt_current_->the_priority ();
49 // Check which policy we are dealing with.
50 if (!client_propagated)
52 // With the SERVER_DECLARED priority model, <client_priority> is
53 // simply the priority associated with the priority propagation
54 // policy in the IOR. This should match the priority we get run
55 // at.
56 ACE_ASSERT (server_priority == client_priority);
58 ACE_DEBUG ((LM_DEBUG,
59 "Using SERVER_DECLARED policy: request processed at priority %d\n",
60 server_priority));
62 else
64 // We are using the CLIENT_DECLARED policy, both the client
65 // priority and the server priority should fall within the
66 // bands. Note that it may be the case that the server priority
67 // is not exactly the same as the client priority since we are
68 // using thread pools with lanes.
70 // Print out the bands.
71 int index = -1;
72 ACE_DEBUG ((LM_DEBUG,
73 "\nPriority Bands:\n"));
74 for (CORBA::ULong i = 0; i < this->bands_.length (); ++i)
76 ACE_DEBUG ((LM_DEBUG,
77 "%d) %d %d\n",
78 (i + 1),
79 this->bands_[i].low,
80 this->bands_[i].high));
82 // Check which band we are using.
83 if (client_priority <= this->bands_[i].high &&
84 client_priority >= this->bands_[i].low &&
85 server_priority <= this->bands_[i].high &&
86 server_priority >= this->bands_[i].low)
87 index = i + 1;
90 ACE_DEBUG ((LM_DEBUG,
91 "Client priority: %d "
92 "Server processing request at priority: %d\n",
93 client_priority,
94 server_priority));
96 if (index == -1)
97 ACE_DEBUG ((LM_DEBUG,
98 "ERROR: object and thread priorities do not "
99 "match the same band.\n"));
100 else
101 ACE_DEBUG ((LM_DEBUG,
102 "Band %d was used for this invocation\n", index));
106 void
107 Test_i::shutdown ()
109 this->orb_->shutdown (false);
112 //*************************************************************************
114 const ACE_TCHAR *bands_file = ACE_TEXT("bands");
115 const ACE_TCHAR *ior_output_file1 = ACE_TEXT("test1.ior");
116 const ACE_TCHAR *ior_output_file2 = ACE_TEXT("test2.ior");
118 // Parse command-line arguments.
120 parse_args (int argc, ACE_TCHAR *argv[])
122 ACE_Get_Opt get_opts (argc, argv, ACE_TEXT("b:o:n:"));
123 int c;
125 while ((c = get_opts ()) != -1)
126 switch (c)
128 case 'n':
129 ior_output_file1 = get_opts.opt_arg ();
130 break;
132 case 'o':
133 ior_output_file2 = get_opts.opt_arg ();
134 break;
136 case 'b':
137 bands_file = get_opts.opt_arg ();
138 break;
140 case '?':
141 default:
142 ACE_ERROR_RETURN ((LM_ERROR,
143 "usage: %s "
144 "-n <iorfile1> "
145 "-o <iorfile2> "
146 "-b <bands_file> "
147 "\n",
148 argv [0]),
149 -1);
152 return 0;
156 get_priority_bands (RTCORBA::PriorityBands &bands)
159 // Read bands from a file.
161 FILE* file =
162 ACE_OS::fopen (bands_file, "r");
164 if (file == 0)
165 return -1;
167 ACE_Read_Buffer reader (file, 1);
169 char *string =
170 reader.read (EOF, ' ', '\0');
172 if (string == 0)
173 return -1;
175 CORBA::ULong bands_length =
176 (reader.replaced () + 1) / 2;
177 bands.length (bands_length);
179 int result = 1;
180 char* working_string = string;
181 for (CORBA::ULong i = 0; i < bands_length; ++i)
183 result = ::sscanf (working_string,
184 "%hd",
185 &bands[i].low);
186 if (result == 0 || result == EOF)
187 break;
189 working_string += ACE_OS::strlen (working_string);
190 working_string += 1;
192 result = ::sscanf (working_string,
193 "%hd",
194 &bands[i].high);
195 if (result == 0 || result == EOF)
196 break;
198 working_string += ACE_OS::strlen (working_string);
199 working_string += 1;
201 if (bands[i].low > bands[i].high)
203 result = 0;
204 break;
208 reader.alloc ()->free (string);
210 if (result == 0 || result == EOF)
211 return -1;
212 else
213 return 0;
217 create_object (PortableServer::POA_ptr poa,
218 CORBA::ORB_ptr orb,
219 Test_i *server_impl,
220 const ACE_TCHAR *filename)
222 // Register servant with the POA.
223 PortableServer::ObjectId_var id;
224 id = poa->activate_object (server_impl);
226 // Create object reference.
227 CORBA::Object_var server =
228 poa->id_to_reference (id.in ());
230 // Print out the IOR.
231 CORBA::String_var ior =
232 orb->object_to_string (server.in ());
234 // Print ior to the file.
235 if (filename != 0)
237 FILE *output_file =
238 ACE_OS::fopen (filename, "w");
239 if (output_file == 0)
240 ACE_ERROR_RETURN ((LM_ERROR,
241 "Cannot open output file for writing IOR: %s",
242 filename),
243 -1);
244 ACE_OS::fprintf (output_file,
245 "%s",
246 ior.in ());
247 ACE_OS::fclose (output_file);
250 return 0;
253 void
254 object_activation_exception_test (RTPortableServer::POA_ptr poa,
255 Test_i *server_impl,
256 CORBA::Short priority)
260 // Register servant with POA.
261 PortableServer::ObjectId_var id =
262 poa->activate_object_with_priority (server_impl,
263 priority);
265 // This next line of code should not run because an exception
266 // should have been raised.
267 ACE_DEBUG ((LM_DEBUG, "ERROR: no exception caught\n"));
269 catch (const CORBA::BAD_PARAM&)
271 // Expected exception.
272 ACE_DEBUG ((LM_DEBUG,
273 "BAD_PARAM exception is caught as expected.\n"));
275 catch (const CORBA::Exception&)
277 // Unexpected exception.
278 ACE_DEBUG ((LM_DEBUG, "ERROR: unexpected exception caught\n"));
279 throw;
283 void
284 poa_creation_exception_test (PortableServer::POA_ptr root_poa,
285 PortableServer::POAManager_ptr manager,
286 CORBA::PolicyList &policies)
290 // Create a POA with invalid policies.
291 PortableServer::POA_var child_poa =
292 root_poa->create_POA ("Child_POA",
293 manager,
294 policies);
296 // This next line of code should not run because an exception
297 // should have been raised.
298 ACE_DEBUG ((LM_DEBUG, "ERROR: no exception caught\n"));
300 catch (const PortableServer::POA::InvalidPolicy&)
302 // Expected exception.
303 ACE_DEBUG ((LM_DEBUG,
304 "InvalidPolicy exception is caught as expected.\n"));
306 catch (const CORBA::Exception&)
308 // Unexpected exception.
309 ACE_DEBUG ((LM_DEBUG, "ERROR: unexpected exception\n"));
310 throw;
315 ACE_TMAIN(int argc, ACE_TCHAR *argv[])
317 CORBA::ORB_var orb;
321 // Initialize ORB.
322 orb =
323 CORBA::ORB_init (argc,
324 argv);
326 // Parse arguments.
327 int result =
328 parse_args (argc,
329 argv);
330 if (result != 0)
331 return result;
333 // Make sure we can support multiple priorities that are required
334 // for this test.
335 if (!check_supported_priorities (orb.in ()))
336 return 2;
338 // Get the RTORB.
339 CORBA::Object_var object =
340 orb->resolve_initial_references ("RTORB");
342 RTCORBA::RTORB_var rt_orb =
343 RTCORBA::RTORB::_narrow (object.in ());
345 // Get the RootPOA.
346 object =
347 orb->resolve_initial_references ("RootPOA");
349 PortableServer::POA_var root_poa =
350 PortableServer::POA::_narrow (object.in ());
352 // Get the POA Manager.
353 PortableServer::POAManager_var poa_manager =
354 root_poa->the_POAManager ();
356 // Obtain priority bands to be used in this test from the file
357 // specified by the user.
358 RTCORBA::PriorityBands bands;
359 result = get_priority_bands (bands);
360 if (result != 0)
361 ACE_ERROR_RETURN ((LM_ERROR,
362 "Error reading priority bands from file\n"),
363 result);
365 // Create a thread-pool.
366 CORBA::ULong stacksize = 0;
367 CORBA::Boolean allow_request_buffering = 0;
368 CORBA::ULong max_buffered_requests = 0;
369 CORBA::ULong max_request_buffer_size = 0;
370 CORBA::Boolean allow_borrowing = 0;
371 CORBA::ULong static_threads = 1;
372 CORBA::ULong dynamic_threads = 0;
374 // The lanes in the pool should match the bands.
375 RTCORBA::ThreadpoolLanes lanes;
376 lanes.length (bands.length ());
378 // For each band, setup up a thread lane.
379 for (CORBA::ULong i = 0;
380 i < bands.length ();
381 ++i)
383 lanes[i].static_threads = static_threads;
384 lanes[i].dynamic_threads = dynamic_threads;
386 // Lane priority is in the middle of the band priorities.
387 lanes[i].lane_priority =
388 (bands[i].low + bands[i].high) / 2;
391 // Create the thread-pool.
392 RTCORBA::ThreadpoolId threadpool_id =
393 rt_orb->create_threadpool_with_lanes (stacksize,
394 lanes,
395 allow_borrowing,
396 allow_request_buffering,
397 max_buffered_requests,
398 max_request_buffer_size);
400 // Test: Attempt to create a POA with priority bands that do not
401 // match the lanes. Should get POA::InvalidPolicy exception.
402 ACE_DEBUG ((LM_DEBUG,
403 "\n<---Test--->: Bands do not match lanes\n\n"));
405 // False bands.
406 RTCORBA::PriorityBands false_bands (bands);
407 false_bands[0].low = 10000;
408 false_bands[0].high = 10005;
410 CORBA::PolicyList poa_policy_list;
411 poa_policy_list.length (2);
413 // Create a bands policy.
414 poa_policy_list[0] =
415 rt_orb->create_priority_banded_connection_policy (false_bands);
417 // Create a thread-pool policy.
418 poa_policy_list[1] =
419 rt_orb->create_threadpool_policy (threadpool_id);
421 // Try to create a POA with invalid policies. Should throw an
422 // exception.
423 poa_creation_exception_test (root_poa.in (),
424 poa_manager.in (),
425 poa_policy_list);
427 // Two policies for the next POA.
428 poa_policy_list.length (2);
430 // Create a priority model policy.
431 poa_policy_list[0] =
432 rt_orb->create_priority_model_policy (RTCORBA::CLIENT_PROPAGATED,
435 // Create a thread-pool policy.
436 poa_policy_list[1] =
437 rt_orb->create_threadpool_policy (threadpool_id);
439 // Create POA with CLIENT_PROPAGATED priority model, with lanes
440 // but no bands.
441 PortableServer::POA_var client_propagated_poa =
442 root_poa->create_POA ("client_propagated_poa",
443 poa_manager.in (),
444 poa_policy_list);
446 // Three policies for the next POA.
447 poa_policy_list.length (3);
449 // Default POA priority comes from the 'middle' lane's priority.
450 CORBA::Short poa_priority =
451 lanes[lanes.length () / 2].lane_priority;
453 // Create a priority model policy.
454 poa_policy_list[0] =
455 rt_orb->create_priority_model_policy (RTCORBA::SERVER_DECLARED,
456 poa_priority);
458 // Create a bands policy.
459 poa_policy_list[1] =
460 rt_orb->create_priority_banded_connection_policy (bands);
462 // Create a thread-pool policy.
463 poa_policy_list[2] =
464 rt_orb->create_threadpool_policy (threadpool_id);
466 // Create POA with SERVER_DECLARED priority model, with bands
467 // and lanes.
468 PortableServer::POA_var server_declared_poa =
469 root_poa->create_POA ("server_declared_poa",
470 poa_manager.in (),
471 poa_policy_list);
473 // Test: Attempt to register an object with priority that
474 // doesn't match lanes. Should get BAD_PARAM exception.
475 ACE_DEBUG ((LM_DEBUG,
476 "\n<---Test--->: Servant priority does not match lanes\n\n"));
478 RTPortableServer::POA_var rt_server_declared_poa =
479 RTPortableServer::POA::_narrow (server_declared_poa.in ());
481 // Activation with incorrect priority should fail.
482 CORBA::Short wrong_priority = 10000;
483 object_activation_exception_test (rt_server_declared_poa.in (),
485 wrong_priority);
487 // Create first servant and register with <client_propagated_poa>.
488 Test_i server_impl (orb.in (),
489 bands);
490 result = create_object (client_propagated_poa.in (),
491 orb.in (),
492 &server_impl,
493 ior_output_file1);
494 if (result != 0)
495 return result;
497 // Create second servant and register with <server_declared_poa>.
498 Test_i server_impl2 (orb.in (),
499 bands);
500 result = create_object (server_declared_poa.in (),
501 orb.in (),
502 &server_impl2,
503 ior_output_file2);
504 if (result != 0)
505 return result;
507 // Activate POA manager.
508 poa_manager->activate ();
510 // Run ORB.
511 orb->run ();
513 // Destroy ORB.
514 orb->destroy ();
516 catch (const CORBA::INTERNAL& exception)
518 int minor_code =
519 exception.minor ();
521 if (errno == EPERM)
523 if (ACE_BIT_ENABLED (minor_code, TAO_RTCORBA_THREAD_CREATION_LOCATION_CODE))
525 ACE_ERROR_RETURN ((LM_ERROR,
526 "Cannot create thread with scheduling policy %s\n"
527 "because the user does not have the appropriate privileges, terminating program....\n"
528 "Check svc.conf options and/or run as root\n",
529 sched_policy_name (orb->orb_core ()->orb_params ()->ace_sched_policy ())),
532 else
534 ACE_ERROR_RETURN ((LM_ERROR,
535 "ERROR: would expect that TAO_RTCORBA_THREAD_CREATION_LOCATION_CODE "
536 "minor code is set, minor code is %d",
537 TAO_RTCORBA_THREAD_CREATION_LOCATION_CODE), -1);
540 else
542 exception._tao_print_exception (
543 "Unexpected exception caught in Banded_Connections test server:");
544 return -1;
547 catch (const CORBA::Exception& ex)
549 ex._tao_print_exception (
550 "Unexpected exception caught in Banded_Connections test server:");
551 return -1;
554 return 0;