1218885Sdim//===- llvm/Support/Program.h ------------------------------------*- C++ -*-===//
2218885Sdim//
3218885Sdim//                     The LLVM Compiler Infrastructure
4218885Sdim//
5218885Sdim// This file is distributed under the University of Illinois Open Source
6218885Sdim// License. See LICENSE.TXT for details.
7218885Sdim//
8218885Sdim//===----------------------------------------------------------------------===//
9218885Sdim//
10218885Sdim// This file declares the llvm::sys::Program class.
11218885Sdim//
12218885Sdim//===----------------------------------------------------------------------===//
13218885Sdim
14249423Sdim#ifndef LLVM_SUPPORT_PROGRAM_H
15249423Sdim#define LLVM_SUPPORT_PROGRAM_H
16218885Sdim
17251662Sdim#include "llvm/ADT/ArrayRef.h"
18218885Sdim#include "llvm/Support/Path.h"
19263508Sdim#include "llvm/Support/system_error.h"
20218885Sdim
21218885Sdimnamespace llvm {
22234353Sdimclass error_code;
23218885Sdimnamespace sys {
24218885Sdim
25263508Sdim  /// This is the OS-specific separator for PATH like environment variables:
26263508Sdim  // a colon on Unix or a semicolon on Windows.
27263508Sdim#if defined(LLVM_ON_UNIX)
28263508Sdim  const char EnvPathSeparator = ':';
29263508Sdim#elif defined (LLVM_ON_WIN32)
30263508Sdim  const char EnvPathSeparator = ';';
31263508Sdim#endif
32218885Sdim
33263508Sdim/// @brief This struct encapsulates information about a process.
34263508Sdimstruct ProcessInfo {
35263508Sdim#if defined(LLVM_ON_UNIX)
36263508Sdim  typedef pid_t ProcessId;
37263508Sdim#elif defined(LLVM_ON_WIN32)
38263508Sdim  typedef unsigned long ProcessId; // Must match the type of DWORD on Windows.
39263508Sdim  typedef void * HANDLE; // Must match the type of HANDLE on Windows.
40263508Sdim  /// The handle to the process (available on Windows only).
41263508Sdim  HANDLE ProcessHandle;
42263508Sdim#else
43263508Sdim#error "ProcessInfo is not defined for this platform!"
44263508Sdim#endif
45218885Sdim
46263508Sdim  /// The process identifier.
47263508Sdim  ProcessId Pid;
48218885Sdim
49263508Sdim  /// The return code, set after execution.
50263508Sdim  int ReturnCode;
51218885Sdim
52263508Sdim  ProcessInfo();
53263508Sdim};
54218885Sdim
55263508Sdim  /// This static constructor (factory) will attempt to locate a program in
56263508Sdim  /// the operating system's file system using some pre-determined set of
57263508Sdim  /// locations to search (e.g. the PATH on Unix). Paths with slashes are
58263508Sdim  /// returned unmodified.
59263508Sdim  /// @returns A Path object initialized to the path of the program or a
60263508Sdim  /// Path object that is empty (invalid) if the program could not be found.
61263508Sdim  /// @brief Construct a Program by finding it by name.
62263508Sdim  std::string FindProgramByName(const std::string& name);
63263508Sdim
64263508Sdim  // These functions change the specified standard stream (stdin, stdout, or
65263508Sdim  // stderr) to binary mode. They return errc::success if the specified stream
66263508Sdim  // was changed. Otherwise a platform dependent error is returned.
67263508Sdim  error_code ChangeStdinToBinary();
68263508Sdim  error_code ChangeStdoutToBinary();
69263508Sdim  error_code ChangeStderrToBinary();
70263508Sdim
71263508Sdim  /// This function executes the program using the arguments provided.  The
72263508Sdim  /// invoked program will inherit the stdin, stdout, and stderr file
73263508Sdim  /// descriptors, the environment and other configuration settings of the
74263508Sdim  /// invoking program.
75263508Sdim  /// This function waits the program to finish.
76263508Sdim  /// @returns an integer result code indicating the status of the program.
77263508Sdim  /// A zero or positive value indicates the result code of the program.
78263508Sdim  /// -1 indicates failure to execute
79263508Sdim  /// -2 indicates a crash during execution or timeout
80263508Sdim  int ExecuteAndWait(
81263508Sdim      StringRef Program, ///< Path of the program to be executed. It is
82263508Sdim      /// presumed this is the result of the FindProgramByName method.
83263508Sdim      const char **args, ///< A vector of strings that are passed to the
84218885Sdim      ///< program.  The first element should be the name of the program.
85218885Sdim      ///< The list *must* be terminated by a null char* entry.
86263508Sdim      const char **env = 0, ///< An optional vector of strings to use for
87218885Sdim      ///< the program's environment. If not provided, the current program's
88218885Sdim      ///< environment will be used.
89263508Sdim      const StringRef **redirects = 0, ///< An optional array of pointers to
90263508Sdim      ///< paths. If the array is null, no redirection is done. The array
91263508Sdim      ///< should have a size of at least three. The inferior process's
92263508Sdim      ///< stdin(0), stdout(1), and stderr(2) will be redirected to the
93263508Sdim      ///< corresponding paths.
94263508Sdim      ///< When an empty path is passed in, the corresponding file
95218885Sdim      ///< descriptor will be disconnected (ie, /dev/null'd) in a portable
96218885Sdim      ///< way.
97263508Sdim      unsigned secondsToWait = 0, ///< If non-zero, this specifies the amount
98263508Sdim      ///< of time to wait for the child process to exit. If the time
99263508Sdim      ///< expires, the child is killed and this call returns. If zero,
100263508Sdim      ///< this function will wait until the child finishes or forever if
101263508Sdim      ///< it doesn't.
102218885Sdim      unsigned memoryLimit = 0, ///< If non-zero, this specifies max. amount
103218885Sdim      ///< of memory can be allocated by process. If memory usage will be
104218885Sdim      ///< higher limit, the child is killed and this call returns. If zero
105218885Sdim      ///< - no memory limit.
106263508Sdim      std::string *ErrMsg = 0, ///< If non-zero, provides a pointer to a string
107218885Sdim      ///< instance in which error messages will be returned. If the string
108218885Sdim      ///< is non-empty upon return an error occurred while invoking the
109218885Sdim      ///< program.
110263508Sdim      bool *ExecutionFailed = 0);
111218885Sdim
112263508Sdim  /// Similar to ExecuteAndWait, but returns immediately.
113263508Sdim  /// @returns The \see ProcessInfo of the newly launced process.
114263508Sdim  /// \note On Microsoft Windows systems, users will need to either call \see
115263508Sdim  /// Wait until the process finished execution or win32 CloseHandle() API on
116263508Sdim  /// ProcessInfo.ProcessHandle to avoid memory leaks.
117263508Sdim  ProcessInfo
118263508Sdim  ExecuteNoWait(StringRef Program, const char **args, const char **env = 0,
119263508Sdim                const StringRef **redirects = 0, unsigned memoryLimit = 0,
120263508Sdim                std::string *ErrMsg = 0, bool *ExecutionFailed = 0);
121263508Sdim
122263508Sdim  /// Return true if the given arguments fit within system-specific
123263508Sdim  /// argument length limits.
124263508Sdim  bool argumentsFitWithinSystemLimits(ArrayRef<const char*> Args);
125263508Sdim
126263508Sdim  /// This function waits for the process specified by \p PI to finish.
127263508Sdim  /// \returns A \see ProcessInfo struct with Pid set to:
128263508Sdim  /// \li The process id of the child process if the child process has changed
129263508Sdim  /// state.
130263508Sdim  /// \li 0 if the child process has not changed state.
131263508Sdim  /// \note Users of this function should always check the ReturnCode member of
132263508Sdim  /// the \see ProcessInfo returned from this function.
133263508Sdim  ProcessInfo Wait(
134263508Sdim      const ProcessInfo &PI, ///< The child process that should be waited on.
135263508Sdim      unsigned SecondsToWait, ///< If non-zero, this specifies the amount of
136263508Sdim      ///< time to wait for the child process to exit. If the time expires, the
137263508Sdim      ///< child is killed and this function returns. If zero, this function
138263508Sdim      ///< will perform a non-blocking wait on the child process.
139263508Sdim      bool WaitUntilTerminates, ///< If true, ignores \p SecondsToWait and waits
140263508Sdim      ///< until child has terminated.
141263508Sdim      std::string *ErrMsg = 0 ///< If non-zero, provides a pointer to a string
142218885Sdim      ///< instance in which error messages will be returned. If the string
143263508Sdim      ///< is non-empty upon return an error occurred while invoking the
144263508Sdim      ///< program.
145218885Sdim      );
146263508Sdim  }
147218885Sdim}
148218885Sdim
149218885Sdim#endif
150