SDL_process.h 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384
  1. /*
  2. Simple DirectMedia Layer
  3. Copyright (C) 1997-2024 Sam Lantinga <[email protected]>
  4. This software is provided 'as-is', without any express or implied
  5. warranty. In no event will the authors be held liable for any damages
  6. arising from the use of this software.
  7. Permission is granted to anyone to use this software for any purpose,
  8. including commercial applications, and to alter it and redistribute it
  9. freely, subject to the following restrictions:
  10. 1. The origin of this software must not be misrepresented; you must not
  11. claim that you wrote the original software. If you use this software
  12. in a product, an acknowledgment in the product documentation would be
  13. appreciated but is not required.
  14. 2. Altered source versions must be plainly marked as such, and must not be
  15. misrepresented as being the original software.
  16. 3. This notice may not be removed or altered from any source distribution.
  17. */
  18. /**
  19. * # CategoryProcess
  20. *
  21. * Process control support.
  22. *
  23. * These functions provide a cross-platform way to spawn and manage OS-level
  24. * processes.
  25. *
  26. * You can create a new subprocess with SDL_CreateProcess() and optionally
  27. * read and write to it using SDL_ReadProcess() and SDL_WriteProcess(). If
  28. * more advanced functionality like chaining input between processes is
  29. * necessary, you can use SDL_CreateProcessWithProperties().
  30. *
  31. * You can get the status of a created process with SDL_WaitProcess(), or
  32. * terminate the process with SDL_KillProcess().
  33. *
  34. * Don't forget to call SDL_DestroyProcess() to clean up, whether the process
  35. * process was killed, terminated on its own, or is still running!
  36. */
  37. #ifndef SDL_process_h_
  38. #define SDL_process_h_
  39. #include <SDL3/SDL_error.h>
  40. #include <SDL3/SDL_begin_code.h>
  41. /* Set up for C function definitions, even when using C++ */
  42. #ifdef __cplusplus
  43. extern "C" {
  44. #endif
  45. typedef struct SDL_Process SDL_Process;
  46. /**
  47. * Create a new process.
  48. *
  49. * The path to the executable is supplied in args[0]. args[1..N] are
  50. * additional arguments passed on the command line of the new process, and the
  51. * argument list should be terminated with a NULL, e.g.:
  52. *
  53. * ```c
  54. * const char *args[] = { "myprogram", "argument", NULL };
  55. * ```
  56. *
  57. * Setting pipe_stdio to SDL_TRUE is equivalent to setting
  58. * `SDL_PROP_PROCESS_CREATE_STDIN_NUMBER` and
  59. * `SDL_PROP_PROCESS_CREATE_STDOUT_NUMBER` to `SDL_PROCESS_STDIO_APP`, and
  60. * will allow the use of SDL_ReadProcess() and SDL_WriteProcess().
  61. *
  62. * See SDL_CreateProcessWithProperties() for more details.
  63. *
  64. * \param args the path and arguments for the new process.
  65. * \param pipe_stdio SDL_TRUE to create pipes to the process's standard input
  66. * and from the process's standard output, SDL_FALSE for the
  67. * process to have no input and inherit the application's
  68. * standard output.
  69. * \returns the newly created and running process, or NULL if the process
  70. * couldn't be created.
  71. *
  72. * \threadsafety It is safe to call this function from any thread.
  73. *
  74. * \since This function is available since SDL 3.0.0.
  75. *
  76. * \sa SDL_CreateProcessWithProperties
  77. * \sa SDL_GetProcessProperties
  78. * \sa SDL_ReadProcess
  79. * \sa SDL_WriteProcess
  80. * \sa SDL_KillProcess
  81. * \sa SDL_WaitProcess
  82. * \sa SDL_DestroyProcess
  83. */
  84. extern SDL_DECLSPEC SDL_Process *SDLCALL SDL_CreateProcess(const char * const *args, SDL_bool pipe_stdio);
  85. /**
  86. * Description of where standard I/O should be directed when creating a
  87. * process.
  88. *
  89. * If a standard I/O stream is set to SDL_PROCESS_STDIO_INHERIT, it will go to
  90. * the same place as the application's I/O stream. This is the default for
  91. * standard output and standard error.
  92. *
  93. * If a standard I/O stream is set to SDL_PROCESS_STDIO_NULL, it is connected
  94. * to `NUL:` on Windows and `/dev/null` on POSIX systems. This is the default
  95. * for standard input.
  96. *
  97. * If a standard I/O stream is set to SDL_PROCESS_STDIO_APP, it is connected
  98. * to a new SDL_IOStream that is available to the application. Standard input
  99. * will be available as `SDL_PROP_PROCESS_STDIN_POINTER` and allows
  100. * SDL_WriteProcess(), standard output will be available as
  101. * `SDL_PROP_PROCESS_STDOUT_POINTER` and allows SDL_ReadProcess(), and
  102. * standard error will be available as `SDL_PROP_PROCESS_STDERR_POINTER` in
  103. * the properties for the created process.
  104. *
  105. * If a standard I/O stream is set to SDL_PROCESS_STDIO_REDIRECT, it is
  106. * connected to an existing SDL_IOStream provided by the application. Standard
  107. * input is provided using `SDL_PROP_PROCESS_CREATE_STDIN_POINTER`, standard
  108. * output is provided using `SDL_PROP_PROCESS_CREATE_STDOUT_POINTER`, and
  109. * standard error is provided using `SDL_PROP_PROCESS_CREATE_STDERR_POINTER`
  110. * in the creation properties. These existing streams should be closed by the
  111. * application once the new process is created.
  112. *
  113. * In order to use an SDL_IOStream with SDL_PROCESS_STDIO_REDIRECT, it must
  114. * have `SDL_PROP_IOSTREAM_WINDOWS_HANDLE_POINTER` or
  115. * `SDL_PROP_IOSTREAM_FILE_DESCRIPTOR_NUMBER` set. This is true for streams
  116. * representing files and process I/O.
  117. *
  118. * \since This enum is available since SDL 3.0.0.
  119. *
  120. * \sa SDL_CreateProcessWithProperties
  121. * \sa SDL_GetProcessProperties
  122. * \sa SDL_ReadProcess
  123. * \sa SDL_WriteProcess
  124. */
  125. typedef enum SDL_ProcessIO
  126. {
  127. SDL_PROCESS_STDIO_INHERITED, /**< The I/O stream is inherited from the application. */
  128. SDL_PROCESS_STDIO_NULL, /**< The I/O stream is ignored. */
  129. SDL_PROCESS_STDIO_APP, /**< The I/O stream is connected to a new SDL_IOStream that the application can read or write */
  130. SDL_PROCESS_STDIO_REDIRECT, /**< The I/O stream is redirected to an existing SDL_IOStream. */
  131. } SDL_ProcessIO;
  132. /**
  133. * Create a new process with the specified properties.
  134. *
  135. * These are the supported properties:
  136. *
  137. * - `SDL_PROP_PROCESS_CREATE_ARGS_POINTER`: an array of strings containing
  138. * the program to run, any arguments, and a NULL pointer, e.g. const char
  139. * *args[] = { "myprogram", "argument", NULL }. This is a required property.
  140. * - `SDL_PROP_PROCESS_CREATE_ENVIRONMENT_POINTER`: an array of strings
  141. * containing variable=value, and a NULL pointer, e.g. const char *env[] = {
  142. * "PATH=/bin:/usr/bin", NULL }. If this property is set, it will be the
  143. * entire environment for the process, otherwise the current environment is
  144. * used.
  145. * - `SDL_PROP_PROCESS_CREATE_STDIN_NUMBER`: an SDL_ProcessIO value describing
  146. * where standard input for the process comes from, defaults to
  147. * `SDL_PROCESS_STDIO_NULL`.
  148. * - `SDL_PROP_PROCESS_CREATE_STDIN_POINTER`: an SDL_IOStream pointer used for
  149. * standard input when `SDL_PROP_PROCESS_CREATE_STDIN_NUMBER` is set to
  150. * `SDL_PROCESS_STDIO_REDIRECT`.
  151. * - `SDL_PROP_PROCESS_CREATE_STDOUT_NUMBER`: an SDL_ProcessIO value
  152. * describing where standard output for the process goes go, defaults to
  153. * `SDL_PROCESS_STDIO_INHERITED`.
  154. * - `SDL_PROP_PROCESS_CREATE_STDOUT_POINTER`: an SDL_IOStream pointer used
  155. * for standard output when `SDL_PROP_PROCESS_CREATE_STDOUT_NUMBER` is set
  156. * to `SDL_PROCESS_STDIO_REDIRECT`.
  157. * - `SDL_PROP_PROCESS_CREATE_STDERR_NUMBER`: an SDL_ProcessIO value
  158. * describing where standard error for the process goes go, defaults to
  159. * `SDL_PROCESS_STDIO_INHERITED`.
  160. * - `SDL_PROP_PROCESS_CREATE_STDERR_POINTER`: an SDL_IOStream pointer used
  161. * for standard error when `SDL_PROP_PROCESS_CREATE_STDERR_NUMBER` is set to
  162. * `SDL_PROCESS_STDIO_REDIRECT`.
  163. * - `SDL_PROP_PROCESS_CREATE_STDERR_TO_STDOUT_BOOLEAN`: true if the error
  164. * output of the process should be redirected into the standard output of
  165. * the process. This property has no effect if
  166. * `SDL_PROP_PROCESS_CREATE_STDERR_NUMBER` is set.
  167. *
  168. * On POSIX platforms, wait() and waitpid(-1, ...) should not be called, and
  169. * SIGCHLD should not be ignored or handled because those would prevent SDL
  170. * from properly tracking the lifetime of the underlying process. You should
  171. * use SDL_WaitProcess() instead.
  172. *
  173. * \param props the properties to use.
  174. * \returns the newly created and running process, or NULL if the process
  175. * couldn't be created.
  176. *
  177. * \threadsafety It is safe to call this function from any thread.
  178. *
  179. * \since This function is available since SDL 3.0.0.
  180. *
  181. * \sa SDL_CreateProcess
  182. * \sa SDL_GetProcessProperties
  183. * \sa SDL_ReadProcess
  184. * \sa SDL_WriteProcess
  185. * \sa SDL_KillProcess
  186. * \sa SDL_WaitProcess
  187. * \sa SDL_DestroyProcess
  188. */
  189. extern SDL_DECLSPEC SDL_Process *SDLCALL SDL_CreateProcessWithProperties(SDL_PropertiesID props);
  190. #define SDL_PROP_PROCESS_CREATE_ARGS_POINTER "SDL.process.create.args"
  191. #define SDL_PROP_PROCESS_CREATE_ENVIRONMENT_POINTER "SDL.process.create.environment"
  192. #define SDL_PROP_PROCESS_CREATE_STDIN_NUMBER "SDL.process.create.stdin_option"
  193. #define SDL_PROP_PROCESS_CREATE_STDIN_POINTER "SDL.process.create.stdin_source"
  194. #define SDL_PROP_PROCESS_CREATE_STDOUT_NUMBER "SDL.process.create.stdout_option"
  195. #define SDL_PROP_PROCESS_CREATE_STDOUT_POINTER "SDL.process.create.stdout_source"
  196. #define SDL_PROP_PROCESS_CREATE_STDERR_NUMBER "SDL.process.create.stderr_option"
  197. #define SDL_PROP_PROCESS_CREATE_STDERR_POINTER "SDL.process.create.stderr_source"
  198. #define SDL_PROP_PROCESS_CREATE_STDERR_TO_STDOUT_BOOLEAN "SDL.process.create.stderr_to_stdout"
  199. /**
  200. * Get the properties associated with a process.
  201. *
  202. * The following read-only properties are provided by SDL:
  203. *
  204. * - `SDL_PROP_PROCESS_PID_NUMBER`: the process ID of the process.
  205. * - `SDL_PROP_PROCESS_STDIN_POINTER`: an SDL_IOStream that can be used to write input to the process, if it was created with `SDL_PROP_PROCESS_CREATE_STDIN_NUMBER` set to `SDL_PROCESS_STDIO_APP`.
  206. * - `SDL_PROP_PROCESS_STDOUT_POINTER`: a non-blocking SDL_IOStream that can be used to read output from the process, if it was created with `SDL_PROP_PROCESS_CREATE_STDOUT_NUMBER` set to `SDL_PROCESS_STDIO_APP`.
  207. * - `SDL_PROP_PROCESS_STDERR_POINTER`: a non-blocking SDL_IOStream that can be used to read error output from the process, if it was created with `SDL_PROP_PROCESS_CREATE_STDERR_NUMBER` set to `SDL_PROCESS_STDIO_APP`.
  208. *
  209. * \param process the process to query.
  210. * \returns a valid property ID on success or 0 on failure; call
  211. * SDL_GetError() for more information.
  212. *
  213. * \sa SDL_CreateProcess
  214. * \sa SDL_CreateProcessWithProperties
  215. *
  216. * \threadsafety It is safe to call this function from any thread.
  217. *
  218. * \since This function is available since SDL 3.0.0.
  219. */
  220. extern SDL_DECLSPEC SDL_PropertiesID SDL_GetProcessProperties(SDL_Process *process);
  221. #define SDL_PROP_PROCESS_PID_NUMBER "SDL.process.pid"
  222. #define SDL_PROP_PROCESS_STDIN_POINTER "SDL.process.stdin"
  223. #define SDL_PROP_PROCESS_STDOUT_POINTER "SDL.process.stdout"
  224. #define SDL_PROP_PROCESS_STDERR_POINTER "SDL.process.stderr"
  225. /**
  226. * Read all the output from a process.
  227. *
  228. * If a process was created with I/O enabled, you can use this function to
  229. * read the output. This function blocks until the process is complete,
  230. * capturing all output, and providing the process exit code.
  231. *
  232. * This is just a convenience function. If you need more control over the
  233. * process, you can get the output stream from the process properties and read
  234. * it directly.
  235. *
  236. * The data is allocated with a zero byte at the end (null terminated) for
  237. * convenience. This extra byte is not included in the value reported via
  238. * `datasize`.
  239. *
  240. * The data should be freed with SDL_free().
  241. *
  242. * \param process The process to read.
  243. * \param datasize a pointer filled in with the number of bytes read, may be
  244. * NULL.
  245. * \param exitcode a pointer filled in with the process exit code if the
  246. * process has exited, may be NULL.
  247. * \returns the data or NULL on failure; call SDL_GetError() for more
  248. * information.
  249. *
  250. * \threadsafety This function is not thread safe.
  251. *
  252. * \since This function is available since SDL 3.0.0.
  253. *
  254. * \sa SDL_CreateProcess
  255. * \sa SDL_CreateProcessWithProperties
  256. * \sa SDL_GetProcessProperties
  257. * \sa SDL_WriteProcess
  258. * \sa SDL_DestroyProcess
  259. */
  260. extern SDL_DECLSPEC void * SDLCALL SDL_ReadProcess(SDL_Process *process, size_t *datasize, int *exitcode);
  261. /**
  262. * Write to a process.
  263. *
  264. * If a process was created with I/O enabled, you can use this function to
  265. * send data as input to the process. This function blocks until the data is
  266. * written.
  267. *
  268. * This is just a convenience function. If the process is structured so it
  269. * takes large amounts of input and generates lots of output, you should get
  270. * the input and output streams from the process properties and handle them
  271. * simultaneously to prevent the process from being blocked waiting for I/O.
  272. *
  273. * \param process The process to write.
  274. * \param ptr a pointer to a buffer containing data to write.
  275. * \param size the number of bytes to write.
  276. * \param closeio if SDL_TRUE, closes the process input before returning, even
  277. * in the case of an error.
  278. * \returns SDL_TRUE on success or SDL_FALSE on failure; call SDL_GetError()
  279. * for more information.
  280. *
  281. * \threadsafety This function is not thread safe.
  282. *
  283. * \since This function is available since SDL 3.0.0.
  284. *
  285. * \sa SDL_CreateProcess
  286. * \sa SDL_CreateProcessWithProperties
  287. * \sa SDL_GetProcessProperties
  288. * \sa SDL_ReadProcess
  289. * \sa SDL_DestroyProcess
  290. */
  291. extern SDL_DECLSPEC SDL_bool SDLCALL SDL_WriteProcess(SDL_Process *process, const void *ptr, size_t size, SDL_bool closeio);
  292. /**
  293. * Stop a process.
  294. *
  295. * \param process The process to stop.
  296. * \param force SDL_TRUE to terminate the process immediately, SDL_FALSE to
  297. * try to stop the process gracefully. In general you should try
  298. * to stop the process gracefully first as terminating a process
  299. * may leave it with half-written data or in some other unstable
  300. * state.
  301. * \returns SDL_TRUE on success or SDL_FALSE on failure; call SDL_GetError()
  302. * for more information.
  303. *
  304. * \threadsafety This function is not thread safe.
  305. *
  306. * \since This function is available since SDL 3.0.0.
  307. *
  308. * \sa SDL_CreateProcess
  309. * \sa SDL_CreateProcessWithProperties
  310. * \sa SDL_WaitProcess
  311. * \sa SDL_DestroyProcess
  312. */
  313. extern SDL_DECLSPEC SDL_bool SDLCALL SDL_KillProcess(SDL_Process *process, SDL_bool force);
  314. /**
  315. * Wait for a process to finish.
  316. *
  317. * This can be called multiple times to get the status of a process.
  318. *
  319. * The exit code will be the exit code of the process if it terminates
  320. * normally, a negative signal if it terminated due to a signal, or -255
  321. * otherwise. It will not be changed if the process is still running.
  322. *
  323. * \param process The process to wait for.
  324. * \param block If true, block until the process finishes; otherwise, report
  325. * on the process' status.
  326. * \param exitcode a pointer filled in with the process exit code if the
  327. * process has exited, may be NULL.
  328. * \returns SDL_TRUE if the process exited, SDL_FALSE otherwise.
  329. *
  330. * \threadsafety This function is not thread safe.
  331. *
  332. * \since This function is available since SDL 3.0.0.
  333. *
  334. * \sa SDL_CreateProcess
  335. * \sa SDL_CreateProcessWithProperties
  336. * \sa SDL_KillProcess
  337. * \sa SDL_DestroyProcess
  338. */
  339. extern SDL_DECLSPEC SDL_bool SDLCALL SDL_WaitProcess(SDL_Process *process, SDL_bool block, int *exitcode);
  340. /**
  341. * Destroy a previously created process object.
  342. *
  343. * Note that this does not stop the process, just destroys the SDL object used
  344. * to track it. If you want to stop the process you should use
  345. * SDL_KillProcess().
  346. *
  347. * \param process The process object to destroy.
  348. *
  349. * \threadsafety This function is not thread safe.
  350. *
  351. * \since This function is available since SDL 3.0.0.
  352. *
  353. * \sa SDL_CreateProcess
  354. * \sa SDL_CreateProcessWithProperties
  355. * \sa SDL_KillProcess
  356. */
  357. extern SDL_DECLSPEC void SDLCALL SDL_DestroyProcess(SDL_Process *process);
  358. /* Ends C function definitions when using C++ */
  359. #ifdef __cplusplus
  360. }
  361. #endif
  362. #include <SDL3/SDL_close_code.h>
  363. #endif /* SDL_process_h_ */