00001 #include "ace_pch.h"
00002
00003
00004 #include "ace/OS.h"
00005 #include "ace/Process.h"
00006 #include "ace/ARGV.h"
00007 #include "ace/Signal.h"
00008 #include "ace/SString.h"
00009 #include "ace/Log_Msg.h"
00010
00011 #if !defined (__ACE_INLINE__)
00012 #include "ace/Process.i"
00013 #endif
00014
00015 ACE_RCSID (ace, Process, "$Id: Process.cpp,v 1.1.1.4.2.1 2003/03/13 19:44:22 chad Exp $")
00016
00017
00018
00019
00020
00021 #if !defined (ACE_WIN32)
00022 static void
00023 sigchld_nop (int, siginfo_t *, ucontext_t *)
00024 {
00025 return;
00026 }
00027 #endif
00028
00029
00030
00031 ACE_Process::ACE_Process (void)
00032 :
00033 #if !defined (ACE_WIN32)
00034 child_id_ (ACE_INVALID_PID),
00035 #endif
00036 exit_code_ (0)
00037 {
00038 #if defined (ACE_WIN32)
00039 ACE_OS::memset ((void *) &this->process_info_,
00040 0,
00041 sizeof this->process_info_);
00042 #endif
00043 }
00044
00045 ACE_Process::~ACE_Process (void)
00046 {
00047 #if defined (ACE_WIN32)
00048
00049 ACE_OS::close (this->process_info_.hThread);
00050 ACE_OS::close (this->process_info_.hProcess);
00051 #endif
00052
00053
00054 this->close_dup_handles ();
00055 }
00056
00057 int
00058 ACE_Process::prepare (ACE_Process_Options &)
00059 {
00060 return 0;
00061 }
00062
00063 pid_t
00064 ACE_Process::spawn (ACE_Process_Options &options)
00065 {
00066 if (prepare (options) < 0)
00067 return ACE_INVALID_PID;
00068
00069
00070
00071
00072 ACE_Handle_Set *set_p = 0;
00073 if (options.dup_handles (this->dup_handles_))
00074 set_p = &this->dup_handles_;
00075 else if (options.passed_handles (this->handles_passed_))
00076 set_p = &this->handles_passed_;
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087 if (set_p && !ACE_BIT_ENABLED (options.creation_flags (),
00088 ACE_Process_Options::NO_EXEC))
00089 {
00090 int maxlen = 0;
00091 ACE_TCHAR *cmd_line_buf = options.command_line_buf (&maxlen);
00092 size_t max_len = ACE_static_cast (size_t, maxlen);
00093 size_t curr_len = ACE_OS::strlen (cmd_line_buf);
00094 ACE_Handle_Set_Iterator h_iter (*set_p);
00095
00096
00097
00098 for (ACE_HANDLE h = h_iter ();
00099 h != ACE_INVALID_HANDLE && curr_len + 20 < max_len;
00100 h = h_iter ())
00101 {
00102 curr_len += ACE_OS::sprintf (&cmd_line_buf[curr_len],
00103 ACE_LIB_TEXT (" +H %d"),
00104 h);
00105 }
00106 }
00107
00108 #if defined (ACE_HAS_WINCE)
00109
00110
00111
00112
00113
00114 BOOL fork_result =
00115 ACE_TEXT_CreateProcess (options.process_name(),
00116 options.command_line_buf(),
00117 options.get_process_attributes(),
00118 options.get_thread_attributes(),
00119 options.handle_inheritence(),
00120 options.creation_flags(),
00121 options.env_buf(),
00122 options.working_directory(),
00123 options.startup_info(),
00124 &this->process_info_);
00125
00126 if (fork_result)
00127 {
00128 parent (this->getpid ());
00129 return this->getpid ();
00130 }
00131 return ACE_INVALID_PID;
00132
00133 #elif defined (ACE_WIN32)
00134 BOOL fork_result =
00135 ACE_TEXT_CreateProcess (0,
00136 options.command_line_buf (),
00137 options.get_process_attributes (),
00138 options.get_thread_attributes (),
00139 options.handle_inheritence (),
00140 options.creation_flags (),
00141 options.env_buf (),
00142 options.working_directory (),
00143 options.startup_info (),
00144 &this->process_info_);
00145
00146 if (fork_result)
00147 {
00148 parent (this->getpid ());
00149 return this->getpid ();
00150 }
00151 return ACE_INVALID_PID;
00152
00153 #elif defined (CHORUS)
00154
00155
00156 if (ACE_BIT_ENABLED (options.creation_flags (),
00157 ACE_Process_Options::NO_EXEC))
00158 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00159
00160
00161 if (options.get_stdin () != ACE_INVALID_HANDLE)
00162 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00163 if (options.get_stdout () != ACE_INVALID_HANDLE)
00164 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00165 if (options.get_stderr () != ACE_INVALID_HANDLE)
00166 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00167 if (options.working_directory () != 0)
00168 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00169
00170 if (options.env_argv ()[0] == 0)
00171
00172 this->child_id_ = ACE_OS::execvp (options.process_name (),
00173 options.command_line_argv ());
00174 else
00175 {
00176
00177
00178 for (char *const *user_env = options.env_argv ();
00179 *user_env != 0;
00180 user_env++)
00181 if (ACE_OS::putenv (*user_env) != 0)
00182 return ACE_INVALID_PID;
00183
00184
00185
00186 this->child_id_ = ACE_OS::execvp (options.process_name (),
00187 options.command_line_argv ());
00188 }
00189
00190 return this->child_id_;
00191 #else
00192
00193 this->child_id_ = ACE::fork (options.process_name (),
00194 options.avoid_zombies ());
00195
00196 if (this->child_id_ == 0)
00197 {
00198 # if !defined (ACE_LACKS_SETPGID)
00199
00200
00201
00202
00203 if (options.getgroup () != ACE_INVALID_PID
00204 && ACE_OS::setpgid (0,
00205 options.getgroup ()) < 0)
00206 ACE_ERROR ((LM_ERROR,
00207 ACE_LIB_TEXT ("%p.\n"),
00208 ACE_LIB_TEXT ("ACE_Process::spawn: setpgid failed.")));
00209 # endif
00210
00211 # if !defined (ACE_LACKS_SETREGID)
00212 if (options.getrgid () != (uid_t) -1
00213 || options.getegid () != (uid_t) -1)
00214 if (ACE_OS::setregid (options.getrgid (),
00215 options.getegid ()) == -1)
00216 ACE_ERROR ((LM_ERROR,
00217 ACE_LIB_TEXT ("%p.\n"),
00218 ACE_LIB_TEXT ("ACE_Process::spawn: setregid failed.")));
00219 # endif
00220
00221 # if !defined (ACE_LACKS_SETREUID)
00222
00223 if (options.getruid () != (uid_t) -1
00224 || options.geteuid () != (uid_t) -1)
00225 if (ACE_OS::setreuid (options.getruid (),
00226 options.geteuid ()) == -1)
00227 ACE_ERROR ((LM_ERROR,
00228 ACE_LIB_TEXT ("%p.\n"),
00229 ACE_LIB_TEXT ("ACE_Process::spawn: setreuid failed.")));
00230 # endif
00231
00232 this->child (ACE_OS::getppid ());
00233 }
00234 else if (this->child_id_ != -1)
00235 this->parent (this->child_id_);
00236
00237
00238 if (ACE_BIT_ENABLED (options.creation_flags (),
00239 ACE_Process_Options::NO_EXEC))
00240 return this->child_id_;
00241
00242 switch (this->child_id_)
00243 {
00244 case -1:
00245
00246 return ACE_INVALID_PID;
00247 case 0:
00248
00249 {
00250 if (options.get_stdin () != ACE_INVALID_HANDLE
00251 && ACE_OS::dup2 (options.get_stdin (),
00252 ACE_STDIN) == -1)
00253 ACE_OS::exit (errno);
00254 else if (options.get_stdout () != ACE_INVALID_HANDLE
00255 && ACE_OS::dup2 (options.get_stdout (),
00256 ACE_STDOUT) == -1)
00257 ACE_OS::exit (errno);
00258 else if (options.get_stderr () != ACE_INVALID_HANDLE
00259 && ACE_OS::dup2 (options.get_stderr (),
00260 ACE_STDERR) == -1)
00261 ACE_OS::exit (errno);
00262
00263
00264 ACE_OS::close (options.get_stdin ());
00265 ACE_OS::close (options.get_stdout ());
00266 ACE_OS::close (options.get_stderr ());
00267
00268
00269
00270 if (options.working_directory () != 0)
00271 ACE_OS::chdir (options.working_directory ());
00272
00273
00274
00275 int result = 0;
00276
00277 if (options.inherit_environment ())
00278 {
00279
00280
00281 for (char *const *user_env = options.env_argv ();
00282 *user_env != 0;
00283 user_env++)
00284 if (ACE_OS::putenv (*user_env) != 0)
00285 return ACE_INVALID_PID;
00286
00287
00288
00289 result = ACE_OS::execvp (options.process_name (),
00290 options.command_line_argv ());
00291 }
00292 else
00293 {
00294 #if defined (ghs)
00295
00296
00297 ACE_NOTSUP_RETURN (ACE_INVALID_PID);
00298 #else
00299 result = ACE_OS::execve (options.process_name (),
00300 options.command_line_argv (),
00301 options.env_argv ());
00302 # endif
00303 }
00304 if (result == -1)
00305 {
00306
00307
00308
00309
00310 ACE_OS::_exit (errno);
00311 }
00312
00313 return 0;
00314 }
00315 default:
00316
00317 return this->child_id_;
00318 }
00319 #endif
00320 }
00321
00322 void
00323 ACE_Process::parent (pid_t)
00324 {
00325
00326 }
00327
00328 void
00329 ACE_Process::child (pid_t)
00330 {
00331
00332 }
00333
00334 void
00335 ACE_Process::unmanage (void)
00336 {
00337
00338 }
00339
00340 int
00341 ACE_Process::running (void) const
00342 {
00343 #if defined (ACE_WIN32)
00344 DWORD code;
00345
00346 BOOL result = ::GetExitCodeProcess (this->gethandle (),
00347 &code);
00348 return result && code == STILL_ACTIVE;
00349 #else
00350 return ACE_OS::kill (this->getpid (),
00351 0) == 0
00352 || errno != ESRCH;
00353 #endif
00354 }
00355
00356 pid_t
00357 ACE_Process::wait (const ACE_Time_Value &tv,
00358 ACE_exitcode *status)
00359 {
00360 #if defined (ACE_WIN32)
00361
00362
00363 switch (::WaitForSingleObject (process_info_.hProcess,
00364 tv.msec ()))
00365 {
00366 case WAIT_OBJECT_0:
00367
00368
00369 ::GetExitCodeProcess (process_info_.hProcess,
00370 &this->exit_code_);
00371 if (status != 0)
00372 *status = this->exit_code_;
00373 return this->getpid ();
00374 case WAIT_TIMEOUT:
00375 errno = ETIME;
00376 return 0;
00377 default:
00378 ACE_OS::set_errno_to_last_error ();
00379 return -1;
00380 }
00381 #else
00382 if (tv == ACE_Time_Value::zero)
00383 {
00384 pid_t retv =
00385 ACE_OS::waitpid (this->child_id_,
00386 &this->exit_code_,
00387 WNOHANG);
00388 if (status != 0)
00389 *status = this->exit_code_;
00390
00391 return retv;
00392 }
00393
00394 if (tv == ACE_Time_Value::max_time)
00395 return this->wait (status);
00396
00397
00398
00399
00400
00401
00402
00403 ACE_Sig_Action old_action;
00404 ACE_Sig_Action do_sigchld ((ACE_SignalHandler)sigchld_nop);
00405 do_sigchld.register_action (SIGCHLD, &old_action);
00406
00407 pid_t pid;
00408 ACE_Time_Value tmo (tv);
00409 for (ACE_Countdown_Time time_left (&tmo); ; time_left.update ())
00410 {
00411 pid = ACE_OS::waitpid (this->getpid (),
00412 &this->exit_code_,
00413 WNOHANG);
00414 if (status != 0)
00415 *status = this->exit_code_;
00416
00417 if (pid > 0 || pid == ACE_INVALID_PID)
00418 break;
00419
00420
00421
00422
00423
00424
00425 if (-1 == ACE_OS::sleep (tmo) && errno == EINTR)
00426 continue;
00427
00428 pid = 0;
00429 break;
00430 }
00431
00432
00433 old_action.register_action (SIGCHLD);
00434
00435 return pid;
00436 #endif
00437 }
00438
00439 void
00440 ACE_Process::close_dup_handles (void)
00441 {
00442 if (this->dup_handles_.num_set () > 0)
00443 {
00444 ACE_Handle_Set_Iterator h_iter (this->dup_handles_);
00445 for (ACE_HANDLE h = h_iter ();
00446 h != ACE_INVALID_HANDLE;
00447 h = h_iter ())
00448 ACE_OS::closesocket (h);
00449 this->dup_handles_.reset ();
00450 }
00451 return;
00452 }
00453
00454 void
00455 ACE_Process::close_passed_handles (void)
00456 {
00457 if (this->handles_passed_.num_set () > 0)
00458 {
00459 ACE_Handle_Set_Iterator h_iter (this->handles_passed_);
00460 for (ACE_HANDLE h = h_iter ();
00461 h != ACE_INVALID_HANDLE;
00462 h = h_iter ())
00463 ACE_OS::closesocket (h);
00464 this->handles_passed_.reset ();
00465 }
00466 return;
00467 }
00468
00469
00470 ACE_Process_Options::ACE_Process_Options (int ie,
00471 int cobl,
00472 int ebl,
00473 int mea)
00474 :
00475 #if !defined (ACE_HAS_WINCE)
00476 inherit_environment_ (ie),
00477 #endif
00478 creation_flags_ (0),
00479 avoid_zombies_ (0),
00480 #if !defined (ACE_HAS_WINCE)
00481 #if defined (ACE_WIN32)
00482 environment_inherited_ (0),
00483 handle_inheritence_ (TRUE),
00484 process_attributes_ (0),
00485 thread_attributes_ (0),
00486 #else
00487 stdin_ (ACE_INVALID_HANDLE),
00488 stdout_ (ACE_INVALID_HANDLE),
00489 stderr_ (ACE_INVALID_HANDLE),
00490 ruid_ ((uid_t) -1),
00491 euid_ ((uid_t) -1),
00492 rgid_ ((uid_t) -1),
00493 egid_ ((uid_t) -1),
00494 #endif
00495 set_handles_called_ (0),
00496 environment_buf_index_ (0),
00497 environment_argv_index_ (0),
00498 environment_buf_ (0),
00499 environment_buf_len_ (ebl),
00500 max_environment_args_ (mea),
00501 max_environ_argv_index_ (mea - 1),
00502 #endif
00503 command_line_argv_calculated_ (0),
00504 command_line_buf_ (0),
00505 command_line_buf_len_ (cobl),
00506 process_group_ (ACE_INVALID_PID)
00507 {
00508 ACE_NEW (command_line_buf_,
00509 ACE_TCHAR[cobl]);
00510 command_line_buf_[0] = '\0';
00511
00512 #if !defined (ACE_HAS_WINCE)
00513 working_directory_[0] = '\0';
00514 ACE_NEW (environment_buf_,
00515 ACE_TCHAR[ebl]);
00516 ACE_NEW (environment_argv_,
00517 ACE_TCHAR *[mea]);
00518 environment_buf_[0] = '\0';
00519 environment_argv_[0] = 0;
00520 process_name_[0] = '\0';
00521 #if defined (ACE_WIN32)
00522 ACE_OS::memset ((void *) &this->startup_info_,
00523 0,
00524 sizeof this->startup_info_);
00525 this->startup_info_.cb = sizeof this->startup_info_;
00526 #endif
00527 #endif
00528 }
00529
00530 #if !defined (ACE_HAS_WINCE)
00531 #if defined (ACE_WIN32)
00532 void
00533 ACE_Process_Options::inherit_environment (void)
00534 {
00535
00536 if (environment_inherited_)
00537 return;
00538 environment_inherited_ = 1;
00539
00540
00541 ACE_TCHAR *existing_environment = ACE_OS::getenvstrings ();
00542
00543 size_t slot = 0;
00544
00545 while (existing_environment[slot] != '\0')
00546 {
00547 size_t len = ACE_OS::strlen (existing_environment + slot);
00548
00549
00550 if (this->setenv_i (existing_environment + slot, len) == -1)
00551 {
00552 ACE_ERROR ((LM_ERROR,
00553 ACE_LIB_TEXT ("%p.\n"),
00554 ACE_LIB_TEXT ("ACE_Process_Options::ACE_Process_Options")));
00555 break;
00556 }
00557
00558
00559 slot += len + 1;
00560 }
00561
00562 ACE_TEXT_FreeEnvironmentStrings (existing_environment);
00563 }
00564
00565 #else
00566
00567 ACE_TCHAR * const *
00568 ACE_Process_Options::env_argv (void)
00569 {
00570 return environment_argv_;
00571 }
00572
00573 #endif
00574
00575 int
00576 ACE_Process_Options::setenv (ACE_TCHAR *envp[])
00577 {
00578 int i = 0;
00579 while (envp[i])
00580 {
00581 if (this->setenv_i (envp[i],
00582 ACE_OS_String::strlen (envp[i])) == -1)
00583 return -1;
00584 i++;
00585 }
00586
00587 #if defined (ACE_WIN32)
00588 if (inherit_environment_)
00589 this->inherit_environment ();
00590 #endif
00591
00592 return 0;
00593 }
00594
00595 int
00596 ACE_Process_Options::setenv (const ACE_TCHAR *format, ...)
00597 {
00598 ACE_TCHAR stack_buf[DEFAULT_COMMAND_LINE_BUF_LEN];
00599
00600
00601 va_list argp;
00602 va_start (argp, format);
00603
00604
00605 ACE_OS::vsprintf (stack_buf,
00606 format,
00607 argp);
00608
00609 va_end (argp);
00610
00611
00612 if (this->setenv_i (stack_buf,
00613 ACE_OS_String::strlen (stack_buf)) == -1)
00614 return -1;
00615
00616 #if defined (ACE_WIN32)
00617 if (inherit_environment_)
00618 this->inherit_environment ();
00619 #endif
00620
00621 return 0;
00622 }
00623
00624 int
00625 ACE_Process_Options::setenv (const ACE_TCHAR *variable_name,
00626 const ACE_TCHAR *format, ...)
00627 {
00628 ACE_TCHAR newformat[DEFAULT_COMMAND_LINE_BUF_LEN];
00629
00630
00631 ACE_OS::sprintf (newformat,
00632 ACE_LIB_TEXT ("%s=%s"),
00633 variable_name,
00634 format);
00635
00636 ACE_TCHAR stack_buf[DEFAULT_COMMAND_LINE_BUF_LEN];
00637
00638
00639 va_list argp;
00640 va_start (argp, format);
00641
00642
00643 ACE_OS::vsprintf (stack_buf, newformat, argp);
00644
00645
00646 va_end (argp);
00647
00648
00649 if (this->setenv_i (stack_buf,
00650 ACE_OS_String::strlen (stack_buf)) == -1)
00651 return -1;
00652
00653 #if defined (ACE_WIN32)
00654 if (inherit_environment_)
00655 this->inherit_environment ();
00656 #endif
00657
00658 return 0;
00659 }
00660
00661 int
00662 ACE_Process_Options::setenv_i (ACE_TCHAR *assignment,
00663 size_t len)
00664 {
00665
00666 len++;
00667
00668
00669
00670 if (environment_argv_index_ == max_environ_argv_index_
00671 || (len + environment_buf_index_) >= environment_buf_len_)
00672 return -1;
00673
00674
00675 ACE_OS::memcpy (environment_buf_ + environment_buf_index_,
00676 assignment,
00677 len * sizeof (ACE_TCHAR));
00678
00679
00680 environment_argv_[environment_argv_index_++] =
00681 environment_buf_ + environment_buf_index_;
00682 environment_argv_[environment_argv_index_] = 0;
00683
00684
00685 environment_buf_index_ += len;
00686
00687
00688 environment_buf_[environment_buf_index_] = '\0';
00689 return 0;
00690 }
00691
00692 int
00693 ACE_Process_Options::set_handles (ACE_HANDLE std_in,
00694 ACE_HANDLE std_out,
00695 ACE_HANDLE std_err)
00696 {
00697 this->set_handles_called_ = 1;
00698 #if defined (ACE_WIN32)
00699
00700
00701 this->startup_info_.dwFlags = STARTF_USESTDHANDLES;
00702
00703 if (std_in == ACE_INVALID_HANDLE)
00704 std_in = ACE_STDIN;
00705 if (std_out == ACE_INVALID_HANDLE)
00706 std_out = ACE_STDOUT;
00707 if (std_err == ACE_INVALID_HANDLE)
00708 std_err = ACE_STDERR;
00709
00710 if (!::DuplicateHandle (::GetCurrentProcess (),
00711 std_in,
00712 ::GetCurrentProcess (),
00713 &this->startup_info_.hStdInput,
00714 0,
00715 TRUE,
00716 DUPLICATE_SAME_ACCESS))
00717 return -1;
00718
00719 if (!::DuplicateHandle (::GetCurrentProcess (),
00720 std_out,
00721 ::GetCurrentProcess (),
00722 &this->startup_info_.hStdOutput,
00723 0,
00724 TRUE,
00725 DUPLICATE_SAME_ACCESS))
00726 return -1;
00727
00728 if (!::DuplicateHandle (::GetCurrentProcess (),
00729 std_err,
00730 ::GetCurrentProcess (),
00731 &this->startup_info_.hStdError,
00732 0,
00733 TRUE,
00734 DUPLICATE_SAME_ACCESS))
00735 return -1;
00736 #else
00737 this->stdin_ = ACE_OS::dup (std_in);
00738 this->stdout_ = ACE_OS::dup (std_out);
00739 this->stderr_ = ACE_OS::dup (std_err);
00740 #endif
00741
00742 return 0;
00743 }
00744
00745
00746 void
00747 ACE_Process_Options::release_handles ()
00748 {
00749 if (set_handles_called_)
00750 {
00751 #if defined (ACE_WIN32)
00752 ACE_OS::close (startup_info_.hStdInput);
00753 ACE_OS::close (startup_info_.hStdOutput);
00754 ACE_OS::close (startup_info_.hStdError);
00755 #else
00756 ACE_OS::close (stdin_);
00757 ACE_OS::close (stdout_);
00758 ACE_OS::close (stderr_);
00759 #endif
00760 set_handles_called_ = 0;
00761 }
00762 }
00763 #endif
00764
00765
00766 ACE_Process_Options::~ACE_Process_Options (void)
00767 {
00768 #if !defined (ACE_HAS_WINCE)
00769 release_handles();
00770 delete [] environment_buf_;
00771 delete [] environment_argv_;
00772 #endif
00773 delete [] command_line_buf_;
00774 }
00775
00776 int
00777 ACE_Process_Options::command_line (const ACE_TCHAR *const argv[])
00778 {
00779
00780 int i = 0;
00781
00782 if (argv[i])
00783 {
00784 ACE_OS::strcat (command_line_buf_, argv[i]);
00785 while (argv[++i])
00786 {
00787 ACE_OS::strcat (command_line_buf_,
00788 ACE_LIB_TEXT (" "));
00789 ACE_OS::strcat (command_line_buf_,
00790 argv[i]);
00791 }
00792 }
00793
00794 command_line_argv_calculated_ = 0;
00795 return 0;
00796 }
00797
00798 int
00799 ACE_Process_Options::command_line (const ACE_TCHAR *format, ...)
00800 {
00801
00802 va_list argp;
00803 va_start (argp, format);
00804
00805
00806 ACE_OS::vsprintf (command_line_buf_,
00807 format,
00808 argp);
00809
00810
00811 va_end (argp);
00812
00813 command_line_argv_calculated_ = 0;
00814 return 0;
00815 }
00816
00817 #if defined (ACE_HAS_WCHAR) && !defined (ACE_HAS_WINCE)
00818
00819
00820
00821
00822 int
00823 ACE_Process_Options::command_line (const ACE_ANTI_TCHAR *format, ...)
00824 {
00825 ACE_ANTI_TCHAR *anti_clb;
00826 ACE_NEW_RETURN (anti_clb,
00827 ACE_ANTI_TCHAR[this->command_line_buf_len_],
00828 -1);
00829
00830
00831 va_list argp;
00832 va_start (argp, format);
00833
00834
00835 ACE_OS::vsprintf (anti_clb,
00836 format,
00837 argp);
00838
00839
00840 va_end (argp);
00841
00842 ACE_OS::strcpy (this->command_line_buf_,
00843 ACE_TEXT_ANTI_TO_TCHAR (anti_clb));
00844
00845 delete [] anti_clb;
00846
00847 command_line_argv_calculated_ = 0;
00848 return 0;
00849 }
00850 #endif
00851
00852 ACE_TCHAR *
00853 ACE_Process_Options::env_buf (void)
00854 {
00855 #if !defined (ACE_HAS_WINCE)
00856 if (environment_buf_[0] == '\0')
00857 return 0;
00858 else
00859 return environment_buf_;
00860 #else
00861 return 0;
00862 #endif
00863 }
00864
00865 ACE_TCHAR * const *
00866 ACE_Process_Options::command_line_argv (void)
00867 {
00868 if (command_line_argv_calculated_ == 0)
00869 {
00870 command_line_argv_calculated_ = 1;
00871
00872
00873
00874 ACE_Tokenizer parser (command_line_buf_);
00875 parser.delimiter_replace (' ', '\0');
00876 parser.preserve_designators ('\"', '\"');
00877 parser.preserve_designators ('\'', '\'');
00878
00879 int x = 0;
00880 do
00881 command_line_argv_[x] = parser.next ();
00882 while (command_line_argv_[x] != 0
00883
00884 && ++x < MAX_COMMAND_LINE_OPTIONS - 1);
00885
00886 command_line_argv_[x] = 0;
00887 }
00888
00889 return command_line_argv_;
00890 }
00891
00892
00893
00894
00895 int
00896 ACE_Process_Options::pass_handle (ACE_HANDLE h)
00897 {
00898 # if defined (ACE_WIN32)
00899 # if defined (ACE_HAS_WINCE)
00900 ACE_NOTSUP_RETURN (-1);
00901 # else
00902
00903
00904
00905
00906
00907
00908
00909
00910
00911 OSVERSIONINFO osvi;
00912 ZeroMemory (&osvi, sizeof (osvi));
00913 osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
00914
00915 if (!GetVersionEx (&osvi) || osvi.dwPlatformId != VER_PLATFORM_WIN32_NT)
00916 {
00917 HANDLE dup_handle;
00918 if (!DuplicateHandle (GetCurrentProcess (),
00919 ACE_static_cast (HANDLE, h),
00920 GetCurrentProcess (),
00921 &dup_handle,
00922 0,
00923 TRUE,
00924 DUPLICATE_SAME_ACCESS))
00925 return -1;
00926 dup_handles_.set_bit (ACE_static_cast (ACE_HANDLE, dup_handle));
00927 }
00928 # endif
00929 #endif
00930
00931 this->handles_passed_.set_bit (h);
00932
00933 return 0;
00934 }
00935
00936
00937
00938 int
00939 ACE_Process_Options::dup_handles (ACE_Handle_Set &set) const
00940 {
00941 if (this->dup_handles_.num_set () == 0)
00942 return 0;
00943 set.reset ();
00944 set = this->dup_handles_;
00945 return 1;
00946 }
00947
00948
00949
00950 int
00951 ACE_Process_Options::passed_handles (ACE_Handle_Set &set) const
00952 {
00953 if (this->handles_passed_.num_set () == 0)
00954 return 0;
00955 set.reset ();
00956 set = this->handles_passed_;
00957 return 1;
00958 }
00959
00960 ACE_Managed_Process::ACE_Managed_Process (void)
00961 {
00962 }
00963
00964 ACE_Managed_Process::~ACE_Managed_Process (void)
00965 {
00966 }