hare

[hare] The Hare programming language
git clone https://git.torresjrjr.com/hare.git
Log | Files | Refs | README | LICENSE

creds.ha (4796B)


      1 // SPDX-License-Identifier: MPL-2.0
      2 // (c) Hare authors <https://harelang.org>
      3 // Unix credentials types & functions; ref credentials(7)
      4 
      5 use errors;
      6 use rt;
      7 
      8 // Process ID.
      9 export type pid = rt::pid_t;
     10 
     11 // User ID.
     12 export type uid = rt::uid_t;
     13 
     14 // Group ID.
     15 export type gid = rt::gid_t;
     16 
     17 // Returns the current process user ID.
     18 export fn getuid() uid = {
     19 	let uid = 0u, euid = 0u, suid = 0u;
     20 	rt::getresuid(&uid, &euid, &suid) as void;
     21 	return uid;
     22 };
     23 
     24 // Returns the current process effective user ID.
     25 export fn geteuid() uid = {
     26 	let uid = 0u, euid = 0u, suid = 0u;
     27 	rt::getresuid(&uid, &euid, &suid) as void;
     28 	return euid;
     29 };
     30 
     31 // Returns the current process group ID.
     32 export fn getgid() gid = {
     33 	let gid = 0u, egid = 0u, sgid = 0u;
     34 	rt::getresgid(&gid, &egid, &sgid) as void;
     35 	return gid;
     36 };
     37 
     38 // Returns the current process effective group ID.
     39 export fn getegid() gid = {
     40 	let gid = 0u, egid = 0u, sgid = 0u;
     41 	rt::getresgid(&gid, &egid, &sgid) as void;
     42 	return egid;
     43 };
     44 
     45 // Sets the caller's user ID to the specified value. This generally requires
     46 // elevated permissions from the calling process.
     47 //
     48 // If the system returns an error, this function will abort the program. Failing
     49 // to handle errors from setuid is a grave security issue in your program, and
     50 // therefore we require this function to succeed. If you need to handle the
     51 // error case gracefully, call the appropriate syscall wrapper in [[rt::]]
     52 // yourself, and take extreme care to handle errors correctly.
     53 export fn setuid(uid: uid) void = rt::setresuid(uid, -1i: uint, -1i: uint)!;
     54 
     55 // Sets the caller's effective user ID to the specified value. This generally
     56 // requires elevated permissions from the calling process.
     57 //
     58 // If the system returns an error, this function will abort the program. Failing
     59 // to handle errors from seteuid is a grave security issue in your program, and
     60 // therefore we require this function to succeed. If you need to handle the
     61 // error case gracefully, call the appropriate syscall wrapper in [[rt::]]
     62 // yourself, and take extreme care to handle errors correctly.
     63 export fn seteuid(uid: uid) void = rt::setresuid(-1i: uint, uid, -1i: uint)!;
     64 
     65 // Sets the caller's group ID to the specified value. This generally requires
     66 // elevated permissions from the calling process.
     67 //
     68 // If the system returns an error, this function will abort the program. Failing
     69 // to handle errors from setuid is a grave security issue in your program, and
     70 // therefore we require this function to succeed. If you need to handle the
     71 // error case gracefully, call the appropriate syscall wrapper in [[rt::]]
     72 // yourself, and take extreme care to handle errors correctly.
     73 export fn setgid(gid: gid) void = rt::setresgid(gid, -1i: uint, -1i: uint)!;
     74 
     75 // Sets the caller's effective group ID to the specified value. This generally
     76 // requires elevated permissions from the calling process.
     77 //
     78 // If the system returns an error, this function will abort the program. Failing
     79 // to handle errors from setegid is a grave security issue in your program, and
     80 // therefore we require this function to succeed. If you need to handle the
     81 // error case gracefully, call the appropriate syscall wrapper in [[rt::]]
     82 // yourself, and take extreme care to handle errors correctly.
     83 export fn setegid(gid: gid) void = rt::setresgid(-1i: uint, gid, -1i: uint)!;
     84 
     85 // Returns a list of supplementary group IDs for the current process. The
     86 // returned slice is statically allocated.
     87 export fn getgroups() []gid = {
     88 	static let gids: [rt::NGROUPS_MAX]rt::gid_t = [0...];
     89 	const n = rt::getgroups(gids)!;
     90 	return gids[..n]: []gid;
     91 };
     92 
     93 // Sets the list of supplementary group IDs which apply to the current process.
     94 // This generally requires elevated permissions.
     95 //
     96 // If the system returns an error, this function will abort the program. Failing
     97 // to handle errors from setgroups is a grave security issue in your program,
     98 // and therefore we require this function to succeed. If you need to handle the
     99 // error case gracefully, call the appropriate syscall wrapper in [[rt::]]
    100 // yourself, and take extreme care to handle errors correctly.
    101 export fn setgroups(gids: []gid) void = rt::setgroups(gids: []rt::gid_t)!;
    102 
    103 // Returns the current process ID.
    104 export fn getpid() pid = rt::getpid();
    105 
    106 // Returns the parent process ID.
    107 export fn getppid() pid = rt::getppid();
    108 
    109 // Returns the current process group ID.
    110 export fn getpgrp() pid = rt::getpgrp();
    111 
    112 // Returns the current process's session ID.
    113 export fn getsid() pid = rt::getsid(0)!;
    114 
    115 // Returns the session ID associated with the given process.
    116 export fn getpsid(pid: pid) (pid | errors::noentry | errors::noaccess) = {
    117 	match (rt::getsid(pid)) {
    118 	case let pid: rt::pid_t =>
    119 		return pid;
    120 	case let err: rt::errno =>
    121 		assert(err == rt::ESRCH);
    122 		return errors::noentry;
    123 	};
    124 };