From 7deb28c8101d2384b01fdd735bb8e649c553ebbc Mon Sep 17 00:00:00 2001 From: flysand7 Date: Sat, 28 Sep 2024 10:30:54 +1100 Subject: [PATCH] [os2/process]: Unindent doc comments --- core/os/os2/process.odin | 237 +++++++++++++++++++-------------------- misc/odin.res | Bin 0 -> 8592 bytes 2 files changed, 118 insertions(+), 119 deletions(-) create mode 100644 misc/odin.res diff --git a/core/os/os2/process.odin b/core/os/os2/process.odin index ce65987b0..7b8f22a99 100644 --- a/core/os/os2/process.odin +++ b/core/os/os2/process.odin @@ -4,13 +4,13 @@ import "base:runtime" import "core:time" /* - In procedures that explicitly state this as one of the allowed values, - specifies an infinite timeout. +In procedures that explicitly state this as one of the allowed values, +specifies an infinite timeout. */ TIMEOUT_INFINITE :: time.MIN_DURATION // Note(flysand): Any negative duration will be treated as infinity /* - Arguments to the current process. +Arguments to the current process. */ args := get_args() @@ -24,17 +24,17 @@ get_args :: proc() -> []string { } /* - Exit the current process. +Exit the current process. */ exit :: proc "contextless" (code: int) -> ! { _exit(code) } /* - Obtain the UID of the current process. +Obtain the UID of the current process. - **Note(windows)**: Windows doesn't follow the posix permissions model, so - the function simply returns -1. +**Note(windows)**: Windows doesn't follow the posix permissions model, so +the function simply returns -1. */ @(require_results) get_uid :: proc() -> int { @@ -42,15 +42,15 @@ get_uid :: proc() -> int { } /* - Obtain the effective UID of the current process. +Obtain the effective UID of the current process. - The effective UID is typically the same as the UID of the process. In case - the process was run by a user with elevated permissions, the process may - lower the privilege to perform some tasks without privilege. In these cases - the real UID of the process and the effective UID are different. - - **Note(windows)**: Windows doesn't follow the posix permissions model, so - the function simply returns -1. +The effective UID is typically the same as the UID of the process. In case +the process was run by a user with elevated permissions, the process may +lower the privilege to perform some tasks without privilege. In these cases +the real UID of the process and the effective UID are different. + +**Note(windows)**: Windows doesn't follow the posix permissions model, so +the function simply returns -1. */ @(require_results) get_euid :: proc() -> int { @@ -58,10 +58,10 @@ get_euid :: proc() -> int { } /* - Obtain the GID of the current process. - - **Note(windows)**: Windows doesn't follow the posix permissions model, so - the function simply returns -1. +Obtain the GID of the current process. + +**Note(windows)**: Windows doesn't follow the posix permissions model, so +the function simply returns -1. */ @(require_results) get_gid :: proc() -> int { @@ -69,15 +69,15 @@ get_gid :: proc() -> int { } /* - Obtain the effective GID of the current process. - - The effective GID is typically the same as the GID of the process. In case - the process was run by a user with elevated permissions, the process may - lower the privilege to perform some tasks without privilege. In these cases - the real GID of the process and the effective GID are different. +Obtain the effective GID of the current process. - **Note(windows)**: Windows doesn't follow the posix permissions model, so - the function simply returns -1. +The effective GID is typically the same as the GID of the process. In case +the process was run by a user with elevated permissions, the process may +lower the privilege to perform some tasks without privilege. In these cases +the real GID of the process and the effective GID are different. + +**Note(windows)**: Windows doesn't follow the posix permissions model, so +the function simply returns -1. */ @(require_results) get_egid :: proc() -> int { @@ -85,7 +85,7 @@ get_egid :: proc() -> int { } /* - Obtain the ID of the current process. +Obtain the ID of the current process. */ @(require_results) get_pid :: proc() -> int { @@ -93,13 +93,13 @@ get_pid :: proc() -> int { } /* - Obtain the ID of the parent process. +Obtain the ID of the parent process. - **Note(windows)**: Windows does not mantain strong relationships between - parent and child processes. This function returns the ID of the process - that has created the current process. In case the parent has died, the ID - returned by this function can identify a non-existent or a different - process. +**Note(windows)**: Windows does not mantain strong relationships between +parent and child processes. This function returns the ID of the process +that has created the current process. In case the parent has died, the ID +returned by this function can identify a non-existent or a different +process. */ @(require_results) get_ppid :: proc() -> int { @@ -107,7 +107,7 @@ get_ppid :: proc() -> int { } /* - Obtain ID's of all processes running in the system. +Obtain ID's of all processes running in the system. */ @(require_results) process_list :: proc(allocator: runtime.Allocator) -> ([]int, Error) { @@ -115,9 +115,9 @@ process_list :: proc(allocator: runtime.Allocator) -> ([]int, Error) { } /* - Bit set specifying which fields of the `Process_Info` struct need to be - obtained by the `process_info()` procedure. Each bit corresponds to a - field in the `Process_Info` struct. +Bit set specifying which fields of the `Process_Info` struct need to be +obtained by the `process_info()` procedure. Each bit corresponds to a +field in the `Process_Info` struct. */ Process_Info_Fields :: bit_set[Process_Info_Field] Process_Info_Field :: enum { @@ -134,8 +134,8 @@ Process_Info_Field :: enum { ALL_INFO :: Process_Info_Fields{.Executable_Path, .PPid, .Priority, .Command_Line, .Command_Args, .Environment, .Username, .Working_Dir} /* - Contains information about the process as obtained by the `process_info()` - procedure. +Contains information about the process as obtained by the `process_info()` +procedure. */ Process_Info :: struct { // The information about a process the struct contains. `pid` is always @@ -162,19 +162,19 @@ Process_Info :: struct { } /* - Obtain information about a process. +Obtain information about a process. - This procedure obtains an information, specified by `selection` parameter of - a process given by `pid`. +This procedure obtains an information, specified by `selection` parameter of +a process given by `pid`. - Use `free_process_info` to free the memory allocated by this procedure. The - `free_process_info` procedure needs to be called, even if this procedure - returned an error, as some of the fields may have been allocated. +Use `free_process_info` to free the memory allocated by this procedure. The +`free_process_info` procedure needs to be called, even if this procedure +returned an error, as some of the fields may have been allocated. - **Note**: The resulting information may or may contain the fields specified - by the `selection` parameter. Always check whether the returned - `Process_Info` struct has the required fields before checking the error code - returned by this procedure. +**Note**: The resulting information may or may contain the fields specified +by the `selection` parameter. Always check whether the returned +`Process_Info` struct has the required fields before checking the error code +returned by this procedure. */ @(require_results) process_info_by_pid :: proc(pid: int, selection: Process_Info_Fields, allocator: runtime.Allocator) -> (Process_Info, Error) { @@ -182,20 +182,20 @@ process_info_by_pid :: proc(pid: int, selection: Process_Info_Fields, allocator: } /* - Obtain information about a process. +Obtain information about a process. - This procedure obtains information, specified by `selection` parameter - about a process that has been opened by the application, specified in - the `process` parameter. +This procedure obtains information, specified by `selection` parameter +about a process that has been opened by the application, specified in +the `process` parameter. - Use `free_process_info` to free the memory allocated by this procedure. The - `free_process_info` procedure needs to be called, even if this procedure - returned an error, as some of the fields may have been allocated. +Use `free_process_info` to free the memory allocated by this procedure. The +`free_process_info` procedure needs to be called, even if this procedure +returned an error, as some of the fields may have been allocated. - **Note**: The resulting information may or may contain the fields specified - by the `selection` parameter. Always check whether the returned - `Process_Info` struct has the required fields before checking the error code - returned by this procedure. +**Note**: The resulting information may or may contain the fields specified +by the `selection` parameter. Always check whether the returned +`Process_Info` struct has the required fields before checking the error code +returned by this procedure. */ @(require_results) process_info_by_handle :: proc(process: Process, selection: Process_Info_Fields, allocator: runtime.Allocator) -> (Process_Info, Error) { @@ -203,19 +203,19 @@ process_info_by_handle :: proc(process: Process, selection: Process_Info_Fields, } /* - Obtain information about the current process. +Obtain information about the current process. - This procedure obtains the information, specified by `selection` parameter - about the currently running process. +This procedure obtains the information, specified by `selection` parameter +about the currently running process. - Use `free_process_info` to free the memory allocated by this procedure. The - `free_process_info` procedure needs to be called, even if this procedure - returned an error, as some of the fields may have been allocated. +Use `free_process_info` to free the memory allocated by this procedure. The +`free_process_info` procedure needs to be called, even if this procedure +returned an error, as some of the fields may have been allocated. - **Note**: The resulting information may or may contain the fields specified - by the `selection` parameter. Always check whether the returned - `Process_Info` struct has the required fields before checking the error code - returned by this procedure. +**Note**: The resulting information may or may contain the fields specified +by the `selection` parameter. Always check whether the returned +`Process_Info` struct has the required fields before checking the error code +returned by this procedure. */ @(require_results) current_process_info :: proc(selection: Process_Info_Fields, allocator: runtime.Allocator) -> (Process_Info, Error) { @@ -223,7 +223,7 @@ current_process_info :: proc(selection: Process_Info_Fields, allocator: runtime. } /* - Obtain information about the specified process. +Obtain information about the specified process. */ process_info :: proc { process_info_by_pid, @@ -232,11 +232,11 @@ process_info :: proc { } /* - Free the information about the process. +Free the information about the process. - This procedure frees the memory occupied by process info using the provided - allocator. The allocator needs to be the same allocator that was supplied - to the `process_info` function. +This procedure frees the memory occupied by process info using the provided +allocator. The allocator needs to be the same allocator that was supplied +to the `process_info` function. */ free_process_info :: proc(pi: Process_Info, allocator: runtime.Allocator) { delete(pi.executable_path, allocator) @@ -254,13 +254,13 @@ free_process_info :: proc(pi: Process_Info, allocator: runtime.Allocator) { } /* - Represents a process handle. +Represents a process handle. - When a process dies, the OS is free to re-use the pid of that process. The - `Process` struct represents a handle to the process that will refer to a - specific process, even after it has died. +When a process dies, the OS is free to re-use the pid of that process. The +`Process` struct represents a handle to the process that will refer to a +specific process, even after it has died. - **Note(linux)**: The `handle` will be referring to pidfd. +**Note(linux)**: The `handle` will be referring to pidfd. */ Process :: struct { pid: int, @@ -276,13 +276,13 @@ Process_Open_Flag :: enum { } /* - Open a process handle using it's pid. +Open a process handle using it's pid. - This procedure obtains a process handle of a process specified by `pid`. - This procedure can be subject to race conditions. See the description of - `Process`. +This procedure obtains a process handle of a process specified by `pid`. +This procedure can be subject to race conditions. See the description of +`Process`. - Use `process_close()` function to close the process handle. +Use `process_close()` function to close the process handle. */ @(require_results) process_open :: proc(pid: int, flags := Process_Open_Flags {}) -> (Process, Error) { @@ -322,28 +322,28 @@ Process_Desc :: struct { } /* - Create a new process and obtain its handle. +Create a new process and obtain its handle. - This procedure creates a new process, with a given command and environment - strings as parameters. Use `environ()` to inherit the environment of the - current process. +This procedure creates a new process, with a given command and environment +strings as parameters. Use `environ()` to inherit the environment of the +current process. - The `desc` parameter specifies the description of how the process should - be created. It contains information such as the command line, the - environment of the process, the starting directory and many other options. - Most of the fields in the struct can be set to `nil` or an empty value. - - Use `process_close` to close the handle to the process. Note, that this - is not the same as terminating the process. One can terminate the process - and not close the handle, in which case the handle would be leaked. In case - the function returns an error, an invalid handle is returned. +The `desc` parameter specifies the description of how the process should +be created. It contains information such as the command line, the +environment of the process, the starting directory and many other options. +Most of the fields in the struct can be set to `nil` or an empty value. - This procedure is not thread-safe. It may alter the inheritance properties - of file handles in an unpredictable manner. In case multiple threads change - handle inheritance properties, make sure to serialize all those calls. +Use `process_close` to close the handle to the process. Note, that this +is not the same as terminating the process. One can terminate the process +and not close the handle, in which case the handle would be leaked. In case +the function returns an error, an invalid handle is returned. + +This procedure is not thread-safe. It may alter the inheritance properties +of file handles in an unpredictable manner. In case multiple threads change +handle inheritance properties, make sure to serialize all those calls. */ @(require_results) -process_start :: proc(desc := Process_Desc {}) -> (Process, Error) { +process_start :: proc(desc: Process_Desc) -> (Process, Error) { return _process_start(desc) } @@ -371,17 +371,17 @@ Process_State :: struct { } /* - Wait for a process event. +Wait for a process event. - This procedure blocks the execution until the process has exited or the - timeout (if specified) has reached zero. If the timeout is `TIMEOUT_INFINITE`, - no timeout restriction is imposed and the procedure can block indefinately. +This procedure blocks the execution until the process has exited or the +timeout (if specified) has reached zero. If the timeout is `TIMEOUT_INFINITE`, +no timeout restriction is imposed and the procedure can block indefinately. - If the timeout has expired, the `General_Error.Timeout` is returned as - the error. +If the timeout has expired, the `General_Error.Timeout` is returned as +the error. - If an error is returned for any other reason, other than timeout, the - process state is considered undetermined. +If an error is returned for any other reason, other than timeout, the +process state is considered undetermined. */ @(require_results) process_wait :: proc(process: Process, timeout := TIMEOUT_INFINITE) -> (Process_State, Error) { @@ -389,12 +389,12 @@ process_wait :: proc(process: Process, timeout := TIMEOUT_INFINITE) -> (Process_ } /* - Close the handle to a process. +Close the handle to a process. - This procedure closes the handle associated with a process. It **does not** - terminate a process, in case it was running. In case a termination is - desired, kill the process first, wait for the process to finish, - then close the handle. +This procedure closes the handle associated with a process. It **does not** +terminate a process, in case it was running. In case a termination is +desired, kill the process first, wait for the process to finish, +then close the handle. */ @(require_results) process_close :: proc(process: Process) -> (Error) { @@ -402,10 +402,9 @@ process_close :: proc(process: Process) -> (Error) { } /* - Terminate a process. - - This procedure terminates a process, specified by it's handle, `process`. +Terminate a process. +This procedure terminates a process, specified by it's handle, `process`. */ @(require_results) process_kill :: proc(process: Process) -> (Error) { diff --git a/misc/odin.res b/misc/odin.res new file mode 100644 index 0000000000000000000000000000000000000000..f9cace9c5fafb49861f7af71e3f9f4b7eafb5576 GIT binary patch literal 8592 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 kH4qQj85l^y{0s~aD%;lQN_9NkNVT03?GO3jhEB literal 0 HcmV?d00001