GCC Code Coverage Report


Directory: src/gate/
File: src/gate/processes.c
Date: 2025-12-12 23:40:09
Exec Total Coverage
Lines: 28 29 96.6%
Functions: 3 3 100.0%
Branches: 16 28 57.1%

Line Branch Exec Source
1 /* GATE PROJECT LICENSE:
2 +----------------------------------------------------------------------------+
3 | Copyright(c) 2018-2025, Stefan Meislinger <sm@opengate.at> |
4 | All rights reserved. |
5 | |
6 | Redistribution and use in source and binary forms, with or without |
7 | modification, are permitted provided that the following conditions are met:|
8 | |
9 | 1. Redistributions of source code must retain the above copyright notice, |
10 | this list of conditions and the following disclaimer. |
11 | 2. Redistributions in binary form must reproduce the above copyright |
12 | notice, this list of conditions and the following disclaimer in the |
13 | documentation and/or other materials provided with the distribution. |
14 | |
15 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"|
16 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
17 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
18 | ARE DISCLAIMED.IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE |
19 | LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
20 | CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
21 | SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
22 | INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
23 | CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
24 | ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF |
25 | THE POSSIBILITY OF SUCH DAMAGE. |
26 +----------------------------------------------------------------------------+
27 */
28
29 #include "gate/processes.h"
30
31 #include "gate/platforms.h"
32 #include "gate/debugging.h"
33 #include "gate/results.h"
34
35 #if defined(GATE_SYS_WIN16)
36 # define GATE_PROCESSES_WINTASK_IMPL 1
37 #elif defined(GATE_SYS_WIN)
38 # define GATE_PROCESSES_WINAPI_IMPL 1
39 #elif defined(GATE_SYS_WASM)
40 # define GATE_PROCESSES_WASM_IMPL 1
41 #elif defined(GATE_SYS_BEOS)
42 # define GATE_PROCESSES_BEOS_IMPL 1
43 #elif defined(GATE_SYS_POSIX)
44 # define GATE_PROCESSES_POSIX_IMPL 1
45 #elif defined(GATE_SYS_EFI)
46 # define GATE_PROCESSES_EFI_IMPL 1
47 #elif defined(GATE_SYS_DOS)
48 # define GATE_PROCESSES_DOS_IMPL 1
49 #else
50 # define GATE_PROCESSES_NOIMPL 1
51 #endif
52
53
54 1 gate_size_t gate_process_print_pid(gate_process_id_t pid, char* text, gate_size_t textlen)
55 {
56 1 return gate_str_print_int64(text, textlen, pid);
57 }
58 1 gate_size_t gate_process_parse_pid(char const* text, gate_size_t textlen, gate_process_id_t* pid)
59 {
60 1 return gate_str_parse_int64(text, textlen, pid);
61 }
62
63 7 gate_result_t gate_process_run(
64 gate_string_t const* executablepath,
65 gate_string_t const* args, gate_size_t argcount,
66 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
67 gate_stream_t* output, int* exit_code
68 )
69 {
70 gate_result_t ret;
71 7 gate_process_handle_t handle = NULL;
72 7 gate_process_stream_t* proc_stream = NULL;
73
1/2
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
7 gate_process_stream_t** ptr_stream = (output == NULL) ? NULL : &proc_stream;
74 char buffer[GATE_MAX_COPYBUFFER_LENGTH];
75 gate_size_t used;
76 gate_size_t written;
77
78 do
79 {
80 7 ret = gate_process_start(executablepath, args, argcount, workdir, envvars, envvarcount, flags, &handle, NULL, ptr_stream);
81
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7 times.
7 GATE_BREAK_IF_FAILED(ret);
82
83
2/4
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 7 times.
✗ Branch 3 not taken.
7 if ((ptr_stream != NULL) && (*ptr_stream != NULL))
84 {
85
1/2
✓ Branch 0 taken 9 times.
✗ Branch 1 not taken.
9 while (GATE_SUCCEEDED(ret))
86 {
87 9 ret = gate_stream_read(*ptr_stream, buffer, sizeof(buffer), &used);
88
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 9 times.
9 GATE_BREAK_IF_FAILED(ret);
89
2/2
✓ Branch 0 taken 7 times.
✓ Branch 1 taken 2 times.
9 if (used == 0)
90 {
91 7 break;
92 }
93 2 ret = gate_stream_write_block(output, buffer, used, &written);
94 }
95
96
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7 times.
7 if (GATE_FAILED(ret))
97 {
98 ret = gate_process_kill(&handle);
99 }
100
101
2/4
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 7 times.
✗ Branch 3 not taken.
7 if (GATE_SUCCEEDED(ret) && (exit_code != NULL))
102 {
103 7 ret = gate_process_get_exitcode(&handle, exit_code);
104
2/2
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 6 times.
7 if (ret == GATE_RESULT_INVALIDSTATE)
105 {
106 1 ret = gate_process_wait(&handle, GATE_PROCESS_WAIT_INFINITE);
107 1 ret = gate_process_get_exitcode(&handle, exit_code);
108 }
109 }
110 }
111 } while (0);
112
113
2/4
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 7 times.
✗ Branch 3 not taken.
7 if (ptr_stream && (*ptr_stream))
114 {
115 7 gate_object_release(*ptr_stream);
116 }
117
118
1/2
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
7 if (handle != NULL)
119 {
120 7 gate_process_close(&handle);
121 }
122 7 return ret;
123 }
124
125
126
127
128
129
130
131
132 #if defined(GATE_PROCESSES_WASM_IMPL)
133
134 #include "gate/platform/wasm/wasm_gate.h"
135 #include <stdlib.h>
136
137 gate_result_t gate_process_get_id(gate_process_id_t* pid)
138 {
139 *pid = 1;
140 return GATE_RESULT_OK;
141 }
142 void gate_process_quit(int exitcode)
143 {
144 exit(exitcode);
145 }
146
147 gate_result_t gate_process_enum(gate_process_enum_callback_t callback, void* userparam, gate_enumint_t flags)
148 {
149 return GATE_RESULT_OK;
150 }
151 gate_result_t gate_process_getinfo(gate_process_infobuffer_t* dest_buffer, gate_process_id_t proc_id, gate_enumint_t flags)
152 {
153 return GATE_RESULT_NOTSUPPORTED;
154 }
155 gate_result_t gate_process_start(
156 gate_string_t const* executablepath,
157 gate_string_t const* args, gate_size_t argcount,
158 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
159 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
160 {
161 return GATE_RESULT_NOTSUPPORTED;
162 }
163 gate_result_t gate_process_start_ex(
164 gate_string_t const* executablepath,
165 gate_string_t const* args, gate_size_t argcount,
166 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
167 char const* sessionlocation,
168 char const* username, char const* password,
169 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
170 {
171 return GATE_RESULT_NOTSUPPORTED;
172 }
173 gate_result_t gate_process_close(gate_process_handle_t* handle)
174 {
175 return GATE_RESULT_NOTSUPPORTED;
176 }
177 gate_result_t gate_process_get_exitcode(gate_process_handle_t* handle, int* exitcode)
178 {
179 return GATE_RESULT_NOTSUPPORTED;
180 }
181
182 gate_result_t gate_process_wait(gate_process_handle_t* handle, gate_uint32_t timeoutms)
183 {
184 return GATE_RESULT_NOTSUPPORTED;
185 }
186 gate_result_t gate_process_wait_pid(gate_process_id_t pid, gate_uint32_t timeoutms)
187 {
188 return GATE_RESULT_NOTSUPPORTED;
189 }
190 gate_result_t gate_process_terminate(gate_process_handle_t* handle, gate_bool_t system_request)
191 {
192 return GATE_RESULT_NOTSUPPORTED;
193 }
194 gate_result_t gate_process_terminate_pid(gate_process_id_t pid, gate_bool_t system_request)
195 {
196 return GATE_RESULT_NOTSUPPORTED;
197 }
198 gate_result_t gate_process_kill(gate_process_handle_t* handle)
199 {
200 return GATE_RESULT_NOTSUPPORTED;
201 }
202 gate_result_t gate_process_kill_pid(gate_process_id_t pid)
203 {
204 return GATE_RESULT_NOTSUPPORTED;
205 }
206 gate_result_t gate_process_suspend(gate_process_handle_t* handle)
207 {
208 return GATE_RESULT_NOTSUPPORTED;
209 }
210 gate_result_t gate_process_suspend_pid(gate_process_id_t pid)
211 {
212 return GATE_RESULT_NOTSUPPORTED;
213 }
214 gate_result_t gate_process_resume(gate_process_handle_t* handle)
215 {
216 return GATE_RESULT_NOTSUPPORTED;
217 }
218 gate_result_t gate_process_resume_pid(gate_process_id_t pid)
219 {
220 return GATE_RESULT_NOTSUPPORTED;
221 }
222
223 #endif /* GATE_PROCESSES_WASM_IMPL */
224
225
226
227 #if defined(GATE_PROCESSES_BEOS_IMPL)
228
229 #include <kernel/OS.h>
230 #include <support/SupportDefs.h>
231
232 #include <stdlib.h>
233
234 gate_result_t gate_process_get_id(gate_process_id_t* pid)
235 {
236 thread_id tid = find_thread(NULL);
237 thread_info info;
238 status_t status = get_thread_info(tid, &info);
239 if (status != B_OK)
240 {
241 return GATE_RESULT_FAILED;
242 }
243 if (pid)
244 {
245 *pid = (gate_process_id_t)info.team;
246 }
247 return GATE_RESULT_OK;
248 }
249 void gate_process_quit(int exitcode)
250 {
251 exit(exitcode);
252 }
253
254 gate_result_t gate_process_enum(gate_process_enum_callback_t callback, void* userparam, gate_enumint_t flags)
255 {
256 return GATE_RESULT_OK;
257 }
258 gate_result_t gate_process_getinfo(gate_process_infobuffer_t* dest_buffer, gate_process_id_t proc_id, gate_enumint_t flags)
259 {
260 return GATE_RESULT_NOTSUPPORTED;
261 }
262 gate_result_t gate_process_start(
263 gate_string_t const* executablepath,
264 gate_string_t const* args, gate_size_t argcount,
265 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
266 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
267 {
268 return GATE_RESULT_NOTSUPPORTED;
269 }
270 gate_result_t gate_process_start_ex(
271 gate_string_t const* executablepath,
272 gate_string_t const* args, gate_size_t argcount,
273 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
274 char const* sessionlocation,
275 char const* username, char const* password,
276 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
277 {
278 return GATE_RESULT_NOTSUPPORTED;
279 }
280 gate_result_t gate_process_close(gate_process_handle_t* handle)
281 {
282 return GATE_RESULT_NOTSUPPORTED;
283 }
284 gate_result_t gate_process_get_exitcode(gate_process_handle_t* handle, int* exitcode)
285 {
286 return GATE_RESULT_NOTSUPPORTED;
287 }
288
289 gate_result_t gate_process_wait(gate_process_handle_t* handle, gate_uint32_t timeoutms)
290 {
291 return GATE_RESULT_NOTSUPPORTED;
292 }
293 gate_result_t gate_process_wait_pid(gate_process_id_t pid, gate_uint32_t timeoutms)
294 {
295 return GATE_RESULT_NOTSUPPORTED;
296 }
297 gate_result_t gate_process_terminate(gate_process_handle_t* handle, gate_bool_t system_request)
298 {
299 return GATE_RESULT_NOTSUPPORTED;
300 }
301 gate_result_t gate_process_terminate_pid(gate_process_id_t pid, gate_bool_t system_request)
302 {
303 return GATE_RESULT_NOTSUPPORTED;
304 }
305 gate_result_t gate_process_kill(gate_process_handle_t* handle)
306 {
307 return GATE_RESULT_NOTSUPPORTED;
308 }
309 gate_result_t gate_process_kill_pid(gate_process_id_t pid)
310 {
311 return GATE_RESULT_NOTSUPPORTED;
312 }
313 gate_result_t gate_process_suspend(gate_process_handle_t* handle)
314 {
315 return GATE_RESULT_NOTSUPPORTED;
316 }
317 gate_result_t gate_process_suspend_pid(gate_process_id_t pid)
318 {
319 return GATE_RESULT_NOTSUPPORTED;
320 }
321 gate_result_t gate_process_resume(gate_process_handle_t* handle)
322 {
323 return GATE_RESULT_NOTSUPPORTED;
324 }
325 gate_result_t gate_process_resume_pid(gate_process_id_t pid)
326 {
327 return GATE_RESULT_NOTSUPPORTED;
328 }
329
330 #endif /* GATE_PROCESSES_BEOS_IMPL */
331
332
333
334 #if defined(GATE_PROCESSES_NOIMPL)
335
336 #include <stdlib.h>
337
338 gate_result_t gate_process_get_id(gate_process_id_t* pid)
339 {
340 *pid = 1;
341 return GATE_RESULT_OK;
342 }
343 void gate_process_quit(int exitcode)
344 {
345 exit(exitcode);
346 }
347
348 gate_result_t gate_process_enum(gate_process_enum_callback_t callback, void* userparam, gate_enumint_t flags)
349 {
350 return GATE_RESULT_OK;
351 }
352 gate_result_t gate_process_getinfo(gate_process_infobuffer_t* dest_buffer, gate_process_id_t proc_id, gate_enumint_t flags)
353 {
354 return GATE_RESULT_NOTSUPPORTED;
355 }
356 gate_result_t gate_process_start(
357 gate_string_t const* executablepath,
358 gate_string_t const* args, gate_size_t argcount,
359 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
360 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
361 {
362 return GATE_RESULT_NOTSUPPORTED;
363 }
364 gate_result_t gate_process_start_ex(
365 gate_string_t const* executablepath,
366 gate_string_t const* args, gate_size_t argcount,
367 gate_string_t const* workdir, gate_string_t const* envvars, gate_size_t envvarcount, gate_enumint_t flags,
368 char const* sessionlocation,
369 char const* username, char const* password,
370 gate_process_handle_t* result_handle, gate_process_id_t* result_pid, gate_process_stream_t** result_stream)
371 {
372 return GATE_RESULT_NOTSUPPORTED;
373 }
374 gate_result_t gate_process_close(gate_process_handle_t* handle)
375 {
376 return GATE_RESULT_NOTSUPPORTED;
377 }
378 gate_result_t gate_process_get_exitcode(gate_process_handle_t* handle, int* exitcode)
379 {
380 return GATE_RESULT_NOTSUPPORTED;
381 }
382
383 gate_result_t gate_process_wait(gate_process_handle_t* handle, gate_uint32_t timeoutms)
384 {
385 return GATE_RESULT_NOTSUPPORTED;
386 }
387 gate_result_t gate_process_wait_pid(gate_process_id_t pid, gate_uint32_t timeoutms)
388 {
389 return GATE_RESULT_NOTSUPPORTED;
390 }
391 gate_result_t gate_process_terminate(gate_process_handle_t* handle, gate_bool_t system_request)
392 {
393 return GATE_RESULT_NOTSUPPORTED;
394 }
395 gate_result_t gate_process_terminate_pid(gate_process_id_t pid, gate_bool_t system_request)
396 {
397 return GATE_RESULT_NOTSUPPORTED;
398 }
399 gate_result_t gate_process_kill(gate_process_handle_t* handle)
400 {
401 return GATE_RESULT_NOTSUPPORTED;
402 }
403 gate_result_t gate_process_kill_pid(gate_process_id_t pid)
404 {
405 return GATE_RESULT_NOTSUPPORTED;
406 }
407 gate_result_t gate_process_suspend(gate_process_handle_t* handle)
408 {
409 return GATE_RESULT_NOTSUPPORTED;
410 }
411 gate_result_t gate_process_suspend_pid(gate_process_id_t pid)
412 {
413 return GATE_RESULT_NOTSUPPORTED;
414 }
415 gate_result_t gate_process_resume(gate_process_handle_t* handle)
416 {
417 return GATE_RESULT_NOTSUPPORTED;
418 }
419 gate_result_t gate_process_resume_pid(gate_process_id_t pid)
420 {
421 return GATE_RESULT_NOTSUPPORTED;
422 }
423
424 #endif /* GATE_PROCESSES_NOIMPL */
425
426