Skip to main content

relibc/header/sys_resource/
mod.rs

1//! `sys/resource.h` implementation.
2//!
3//! See <https://pubs.opengroup.org/onlinepubs/9799919799/basedefs/sys_resource.h.html>.
4
5use crate::{
6    error::ResultExt,
7    header::sys_select::timeval,
8    out::Out,
9    platform::{
10        Pal, Sys,
11        types::{c_int, c_long, c_ulonglong, id_t},
12    },
13};
14
15/// Returns information about the current process.
16pub const RUSAGE_SELF: c_int = 0;
17/// Returns information about children of the current process.
18pub const RUSAGE_CHILDREN: c_int = -1;
19/// Non-POSIX.
20///
21/// Return resource consumption statistics for both the current process and
22/// all of its terminated child processes that have been waited for.
23pub const RUSAGE_BOTH: c_int = -2;
24// TODO should be guarded by `_GNU_SOURCE`
25/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
26///
27/// Return resource usage statistics for the calling thread.
28pub const RUSAGE_THREAD: c_int = 1;
29
30/// A value of `rlim_t` indicating no limit.
31pub const RLIM_INFINITY: u64 = 0xFFFF_FFFF_FFFF_FFFF;
32/// A value of type `rlim_t` indicating an unrepresentable saved soft limit.
33pub const RLIM_SAVED_CUR: u64 = RLIM_INFINITY;
34/// A value of type `rlim_t` indicating an unrepresentable saved hard limit.
35pub const RLIM_SAVED_MAX: u64 = RLIM_INFINITY;
36
37/// Limit on CPU time per process.
38pub const RLIMIT_CPU: c_int = 0;
39/// Limit on file size.
40pub const RLIMIT_FSIZE: c_int = 1;
41/// Limit on data segment size.
42pub const RLIMIT_DATA: c_int = 2;
43/// Limit on stack size.
44pub const RLIMIT_STACK: c_int = 3;
45/// Limit on size of core image.
46pub const RLIMIT_CORE: c_int = 4;
47/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
48///
49/// This is a limit (in bytes) on the process's resident set (the number of
50/// virtual pages resident in RAM).
51/// Only affects Linux 2.4.0 to 2.4.29.
52pub const RLIMIT_RSS: c_int = 5;
53/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
54///
55/// This is a limit on the number of extant processes (or, more preciselu on
56/// Linux, threads) for the real user ID of the calling process.
57pub const RLIMIT_NPROC: c_int = 6;
58/// Limit on number of open files.
59pub const RLIMIT_NOFILE: c_int = 7;
60/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
61///
62/// This is the maximum number of bytes of memory that may be locked into RAM.
63pub const RLIMIT_MEMLOCK: c_int = 8;
64/// Limit on address space size.
65pub const RLIMIT_AS: c_int = 9;
66/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
67///
68/// This is a limit on the combined number of `flock(2)` locks and `fcntl(2)`
69/// leases that this process may establish.
70/// Only affects Linux 2.4.0 to 2.4.24.
71pub const RLIMIT_LOCKS: c_int = 10;
72/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
73///
74/// This is a limit on the number of signals that may be queued for the real
75/// user ID of the calling process.
76pub const RLIMIT_SIGPENDING: c_int = 11;
77/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
78///
79/// This is a limit on the number of bytes that can be allocated for POSIX
80/// message queues for the real user ID of the calling process.
81pub const RLIMIT_MSGQUEUE: c_int = 12;
82/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
83///
84/// This specifies a ceiling to which the process's nice value can be raised
85/// using `setpriority(2)` or `nice(2)`.
86pub const RLIMIT_NICE: c_int = 13;
87/// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrlimit.2.html>.
88///
89/// This specifies a ceiling on the real-time priority that may be set for
90/// this process using `sched_setscheduler(2)` and `sched_setparam(2)`.
91pub const RLIMIT_RTPRIO: c_int = 14;
92/// Non-POSIX, found in glibc.
93///
94/// Number of limit flavors.
95pub const RLIMIT_NLIMITS: c_int = 15;
96
97/// Unsigned integer type used for limit values.
98pub type rlim_t = c_ulonglong;
99
100#[repr(C)]
101pub struct rlimit {
102    /// The current (soft) limit.
103    pub rlim_cur: rlim_t,
104    /// The hard limit.
105    pub rlim_max: rlim_t,
106}
107
108#[repr(C)]
109pub struct rusage {
110    /// User time used.
111    pub ru_utime: timeval,
112    /// System time used.
113    pub ru_stime: timeval,
114    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
115    ///
116    /// Maximum resident set size.
117    pub ru_maxrss: c_long,
118    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
119    ///
120    /// Integral shared memory size.
121    pub ru_ixrss: c_long,
122    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
123    ///
124    /// Integral unshared data size.
125    pub ru_idrss: c_long,
126    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
127    ///
128    /// Integral unshared stack size.
129    pub ru_isrss: c_long,
130    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
131    ///
132    /// Page reclaims (soft page faults).
133    pub ru_minflt: c_long,
134    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
135    ///
136    /// Page faults (hard page faults).
137    pub ru_majflt: c_long,
138    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
139    ///
140    /// Swaps.
141    pub ru_nswap: c_long,
142    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
143    ///
144    /// Block input operations.
145    pub ru_inblock: c_long,
146    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
147    ///
148    /// Block output operations.
149    pub ru_oublock: c_long,
150    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
151    ///
152    /// IPC messages sent.
153    pub ru_msgsnd: c_long,
154    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
155    ///
156    /// IPC messages received.
157    pub ru_msgrcv: c_long,
158    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
159    ///
160    /// Signals received.
161    pub ru_nsignals: c_long,
162    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
163    ///
164    /// Voluntary context switches.
165    pub ru_nvcsw: c_long,
166    /// Non-POSIX, see <https://www.man7.org/linux/man-pages/man2/getrusage.2.html>.
167    ///
168    /// Involuntary context switches.
169    pub ru_nivcsw: c_long,
170}
171
172/// Identifies the `who` argument as a process ID.
173pub const PRIO_PROCESS: c_int = 0;
174/// Identifies the `who` argument as a process group ID.
175pub const PRIO_PGRP: c_int = 1;
176/// Identifies the `who` argument as a user ID.
177pub const PRIO_USER: c_int = 2;
178
179/// See <https://pubs.opengroup.org/onlinepubs/9799919799/functions/getpriority.html>.
180///
181/// Obtains the nice value of a process, process group or user.
182///
183/// A value of `0` for `who` indicates the current process, process group or
184/// user.
185///
186/// A return value of `-1` can either be a valid nice value or indicate that
187/// an error occurred. To distinguish between them, first set `errno` to `0`
188/// before calling `getpriority()`, then check the value of `errno` after the
189/// call to `getpriority()`.
190#[unsafe(no_mangle)]
191pub extern "C" fn getpriority(which: c_int, who: id_t) -> c_int {
192    let r = Sys::getpriority(which, who).or_minus_one_errno();
193    if r < 0 {
194        return r;
195    }
196    20 - r
197}
198
199/// See <https://pubs.opengroup.org/onlinepubs/9799919799/functions/setpriority.html>.
200///
201/// Sets the nice value of a process, process group or user.
202///
203/// A value of `0` for `who` indicates the current process, process group or
204/// user.
205///
206/// A return value of `0` indicates success, `-1` indicates error.
207#[unsafe(no_mangle)]
208pub extern "C" fn setpriority(which: c_int, who: id_t, nice: c_int) -> c_int {
209    Sys::setpriority(which, who, nice)
210        .map(|()| 0)
211        .or_minus_one_errno()
212}
213
214/// See <https://pubs.opengroup.org/onlinepubs/9799919799/functions/getrlimit.html>.
215///
216/// Stores the value of the limit indicated by `resource` into the `rlimit`
217/// struct pointed to by `rlp`.
218///
219/// A return value of `0` indicates success, `-1` indicates error.
220#[unsafe(no_mangle)]
221pub unsafe extern "C" fn getrlimit(resource: c_int, rlp: *mut rlimit) -> c_int {
222    Sys::getrlimit(resource, unsafe { Out::nonnull(rlp) })
223        .map(|()| 0)
224        .or_minus_one_errno()
225}
226
227/// See <https://pubs.opengroup.org/onlinepubs/9799919799/functions/setrlimit.html>.
228///
229/// Sets the value of the limit indicated by `resource` to the value specified
230/// in the `rlimit` struct pointed to by `rlp`.
231///
232/// A return value of `0` indicates success, `-1` indicates error.
233#[unsafe(no_mangle)]
234pub unsafe extern "C" fn setrlimit(resource: c_int, rlp: *const rlimit) -> c_int {
235    unsafe { Sys::setrlimit(resource, rlp) }
236        .map(|()| 0)
237        .or_minus_one_errno()
238}
239
240/// See <https://pubs.opengroup.org/onlinepubs/9799919799/functions/getrusage.html>.
241///
242/// Stores the measures of the resources used by the current process or its
243/// terminated and waited-for child processes in the `rusage` struct pointed
244/// to by `r_usage`.
245///
246/// A return value of `0` indicates success, `-1` indicates error.
247#[unsafe(no_mangle)]
248pub unsafe extern "C" fn getrusage(who: c_int, r_usage: *mut rusage) -> c_int {
249    Sys::getrusage(who, unsafe { Out::nonnull(r_usage) })
250        .map(|()| 0)
251        .or_minus_one_errno()
252}