mirror of
https://github.com/deadw00d/AROS.git
synced 2025-12-06 13:11:35 +00:00
840 lines
21 KiB
C
840 lines
21 KiB
C
/*
|
|
* credential.c --- handle credentials
|
|
*
|
|
* Original Author: ppessi <Pekka.Pessi@hut.fi>
|
|
*
|
|
* Based upon usergroup.library from AmiTCP/IP.
|
|
*
|
|
* Copyright © 2025 The AROS Dev Team.
|
|
* Copyright © 1993 AmiTCP/IP Group, <AmiTCP-Group@hut.fi>
|
|
* Helsinki University of Technology, Finland.
|
|
*/
|
|
|
|
#include <aros/debug.h>
|
|
|
|
#include "base.h"
|
|
#include "credential.h"
|
|
#include <proto/usergroup.h>
|
|
|
|
#include <exec/memory.h>
|
|
#include <exec/alerts.h>
|
|
#include <string.h>
|
|
#include <assert.h>
|
|
|
|
struct CredentialResource *CredentialBase;
|
|
|
|
static struct UserGroupCredentials creds[1];
|
|
|
|
#ifdef notyet
|
|
typedef struct CredentialResource *(*resident_init_fp)(void);
|
|
|
|
/*
|
|
* Create credential resource
|
|
*/
|
|
struct CredentialResource *CredentialInit(const char *name)
|
|
{
|
|
BPTR resseg = LoadSeg(_PATH_CREDENTIAL);
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (resseg) {
|
|
resident_init_fp initf = (resident_init_fp)((LONG *)(resseg << 2) + 1);
|
|
struct CredentialResource *res = initf();
|
|
|
|
if (res)
|
|
return res;
|
|
|
|
UnLoadSeg(resseg);
|
|
}
|
|
|
|
return NULL;
|
|
}
|
|
#endif
|
|
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
AROS_LH0I(pid_t, setsid,
|
|
|
|
/* SYNOPSIS */
|
|
|
|
/* LOCATION */
|
|
struct Library *, UserGroupBase, 34, Usergroup)
|
|
|
|
/* FUNCTION
|
|
The setsid() function creates a new session when the calling
|
|
process is not a process group leader. The calling process
|
|
then becomes the session leader of this session and the only
|
|
process in the new session.
|
|
|
|
RESULTS
|
|
Upon successful completion, the value of the new session ID is
|
|
returned. Otherwise, a value of -1 is returned and an error
|
|
code is stored to global errno location.
|
|
|
|
ERRORS
|
|
[EPERM] The calling process is already a session leader.
|
|
|
|
SEE ALSO
|
|
getpgrp()
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
#ifdef notyet
|
|
pid_t pid = (pid_t)FindTask(NULL);
|
|
struct proc *p = procfind(pid);
|
|
int error;
|
|
|
|
if (p->p_session->s_leader == pid) {
|
|
error = EPERM;
|
|
} else {
|
|
struct session *session;
|
|
|
|
while (!(session = AllocMem(sizeof(*session), MEMF_CLEAR|MEMF_PUBLIC))) {
|
|
Alert(AG_NoMemory | UG_CredRes);
|
|
Wait(0L);
|
|
}
|
|
InitList((struct List *)session->s_pgrpl);
|
|
Forbid();
|
|
p = proccopy(p, pid);
|
|
p->p_ucred->cr_ref++;
|
|
p->p_ucred = crcopy(p->p_ucred);
|
|
|
|
/* Remove from old process group */
|
|
rempgrp(p);
|
|
p->p_session = session;
|
|
MinAddHead(session->s_pgrpl, p->p_pgrp);
|
|
session->s_consoletask = GetConsoleTask();
|
|
session->s_leader = pid;
|
|
Permit();
|
|
return pid;
|
|
}
|
|
|
|
ug_SetErrno((struct Library *)UserGroupBase, error);
|
|
return -1;
|
|
#endif
|
|
return 0;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
AROS_LH0I(pid_t, getpgrp,
|
|
|
|
/* SYNOPSIS */
|
|
|
|
/* LOCATION */
|
|
struct Library *, UserGroupBase, 35, Usergroup)
|
|
|
|
/* FUNCTION
|
|
The getpgrp() function returns the process group id for the current
|
|
process. Currently, the process group ID is the same as the session
|
|
ID. The 0 is valid process group ID for console session.
|
|
|
|
RESULTS
|
|
Upon successful completion, the value of the process group ID is
|
|
returned. Otherwise, a value of -1 is returned and an error code is
|
|
stored to global errno location.
|
|
|
|
ERRORS
|
|
[ESRCH] The calling process don't belong to any process group.
|
|
|
|
SEE ALSO
|
|
setsid(), exec.library/FindTask()
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct proc *p = procfind(0);
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return p->p_session->s_leader;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
#ifdef notyet
|
|
/*
|
|
* Remove a process from session's process group and
|
|
* free session if last process is removed
|
|
*/
|
|
void
|
|
rempgrp(struct proc *p)
|
|
{
|
|
Forbid();
|
|
/* Free the session structure if the last task in process group dies */
|
|
MinRemove((struct Node *)p->p_pgrp);
|
|
if (IsMinListEmpty(p->p_session->s_pgrpl)) {
|
|
FreeMem(p->p_session, sizeof(*p->p_session));
|
|
} else if (p->p_session->s_leader == (pid_t)p->p_task) {
|
|
|
|
}
|
|
Permit();
|
|
}
|
|
#endif
|
|
|
|
/*
|
|
* Check super-user
|
|
*/
|
|
int
|
|
suser(struct ucred *cred)
|
|
{
|
|
if (cred->cr_uid == 0)
|
|
return 0;
|
|
return EPERM;
|
|
}
|
|
|
|
/*
|
|
* Search credentials
|
|
*/
|
|
static struct pcred *crfind(pid_t pid)
|
|
{
|
|
return procfind(pid)->p_cred;
|
|
}
|
|
|
|
/****** usergroup.library/getuid *********************************************
|
|
|
|
NAME
|
|
getuid, geteuid - get user process identification
|
|
getgid, getegid - get group process identification
|
|
|
|
SYNOPSIS
|
|
ruid = getuid()
|
|
D0
|
|
|
|
uid_t getuid(void);
|
|
|
|
euid = geteuid()
|
|
D0
|
|
|
|
uid_t geteuid(void);
|
|
|
|
rgid = getgid()
|
|
D0
|
|
|
|
gid_t getgid(void);
|
|
|
|
egid = getegid()
|
|
D0
|
|
|
|
gid_t getegid(void);
|
|
|
|
FUNCTION
|
|
The getuid() function returns the real user ID of the calling
|
|
process, geteuid() returns the effective user ID of the calling
|
|
process.
|
|
|
|
The getgid() function returns the real group ID of the calling
|
|
process, getegid() returns the effective group ID of the calling
|
|
process.
|
|
|
|
The real user ID and real group ID is specified at login time.
|
|
|
|
The real ID is the ID of the user who invoked the program. As the
|
|
effective user and gourp ID gives the process additional permissions
|
|
during the execution of `set-user-ID' or `set-group-ID' mode
|
|
programs, functions getgid() and getuid () are used to determine the
|
|
real-ids of the calling process.
|
|
|
|
RESULT
|
|
The getuid(), geteuid(), getgid(), and getegid() functions are
|
|
always successful, and no return value is reserved to indicate an
|
|
error.
|
|
|
|
NOTES
|
|
Any task can call these functions
|
|
|
|
SEE ALSO
|
|
getgroups(), setuid(), setreuid(), setgid(), setregid(), setgroups()
|
|
|
|
******************************************************************************
|
|
*/
|
|
|
|
AROS_LH0I(uid_t, getuid,
|
|
struct Library *, UserGroupBase, 8, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return crfind((pid_t)NULL)->p_ruid;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH0I(uid_t, geteuid,
|
|
struct Library *, UserGroupBase, 9, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return crfind((pid_t)NULL)->p_euid;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH0I(gid_t, getgid,
|
|
struct Library *, UserGroupBase, 12, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return crfind((pid_t)NULL)->p_rgid;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH0I(gid_t, getegid,
|
|
struct Library *, UserGroupBase, 13, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return crfind((pid_t)NULL)->p_egid;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
|
|
AROS_LH2 (int, getgroups,
|
|
|
|
/* SYNOPSIS */
|
|
AROS_LHA(int, ngroups, D0),
|
|
AROS_LHA(gid_t *, groups, A1),
|
|
|
|
/* LOCATION */
|
|
struct UserGroupBase *, UserGroupBase, 16, Usergroup)
|
|
|
|
/* FUNCTION
|
|
Getgroups() gets the current group access list of the user process
|
|
and stores it in the array gidset. The parameter gidsetlen indicates
|
|
the number of entries that may be placed in gidset. The function
|
|
getgroups() returns the actual number of groups returned in gidset.
|
|
No more than NGROUPS, as defined in <libraries/usergroup.h>, will
|
|
ever be returned.
|
|
|
|
RESULT
|
|
A successful call returns the number of groups in the group set. A
|
|
value of -1 indicates that the argument gidsetlen is smaller than
|
|
the number of groups in the group set.
|
|
|
|
ERRORS
|
|
[EINVAL] The argument gidsetlen is smaller than the number of
|
|
groups in the group set.
|
|
[EFAULT] The argument gidset specifies an invalid address.
|
|
|
|
SEE ALSO
|
|
setgroups(), initgroups(), getgid(), getegid()
|
|
|
|
HISTORY
|
|
The getgroups function call appeared in 4.2BSD.
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct pcred *pc = crfind((pid_t)NULL);
|
|
gid_t *getgroups;
|
|
short error;
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (ngroups == 0) {
|
|
return pc->p_ngroups;
|
|
} else if (ngroups < pc->p_ngroups) {
|
|
error = EINVAL;
|
|
} else if (groups == NULL || ((SIPTR)groups & 1) != 0) {
|
|
error = EFAULT;
|
|
} else {
|
|
/* This does also UWORD -> gid_t conversion */
|
|
getgroups = pc->p_groups;
|
|
ngroups = pc->p_ngroups;
|
|
while (ngroups-- > 0) {
|
|
*groups++ = *getgroups++;
|
|
}
|
|
return pc->p_ngroups;
|
|
}
|
|
|
|
ug_SetErrno((struct Library *)UserGroupBase, error);
|
|
return -1;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH2 (int, setreuid,
|
|
AROS_LHA(uid_t, ruid, D0),
|
|
AROS_LHA(uid_t, euid, D1),
|
|
struct UserGroupBase *, UserGroupBase, 10, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct pcred *pc = crfind((pid_t)NULL);
|
|
short error;
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (ruid == NOID)
|
|
ruid = pc->p_ruid;
|
|
if (euid == NOID)
|
|
euid = pc->pc_ucred->cr_uid;
|
|
|
|
/*
|
|
* Allow setting real uid to previous effective, for swapping real and
|
|
* effective. This should be:
|
|
*
|
|
* if (ruid != pc->p_ruid &&
|
|
* (error = suser(pc->pc_ucred, &p->p_acflag)))
|
|
*/
|
|
#if 1
|
|
/* allow setreuid(-1, 0) to emulate SUID */
|
|
if ((ruid != pc->p_ruid && ruid != pc->pc_ucred->cr_uid /* XXX */ &&
|
|
(error = suser(pc->pc_ucred))) ||
|
|
(/* euid != pc->pc_ucred->cr_uid */ 0 && euid != pc->p_ruid &&
|
|
(error = suser(pc->pc_ucred))))
|
|
#else
|
|
if ((ruid != pc->p_ruid && ruid != pc->pc_ucred->cr_uid /* XXX */ &&
|
|
(error = suser(pc->pc_ucred))) ||
|
|
(euid != pc->pc_ucred->cr_uid && euid != pc->p_ruid &&
|
|
(error = suser(pc->pc_ucred))))
|
|
#endif
|
|
{
|
|
unlock(&credential_list);
|
|
ug_SetErrno((struct Library *)UserGroupBase, error);
|
|
return -1;
|
|
} else {
|
|
/*
|
|
* Everything's okay, do it. Copy credentials so other references do
|
|
* not see our changes.
|
|
*/
|
|
pc->pc_ucred = crcopy(pc->pc_ucred);
|
|
pc->pc_ucred->cr_uid = euid;
|
|
pc->p_ruid = ruid;
|
|
|
|
return 0;
|
|
}
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
/****** usergroup.library/setuid ***********************************************
|
|
|
|
NAME
|
|
setuid, setreuid - set real and effective user ID's
|
|
setgid, setregid - set real and effective group ID's
|
|
|
|
SYNOPSIS
|
|
success = setuid(uid)
|
|
D0 D0
|
|
|
|
int setuid(uid_t);
|
|
|
|
success = setreuid(ruid, euid);
|
|
D0 D0 D1
|
|
|
|
int setreuid(uid_t, uid_t);
|
|
|
|
success = setgid(gid)
|
|
D0 D0
|
|
|
|
int setgid(gid_t);
|
|
|
|
success = setregid(ruid, euid)
|
|
D0 D0 D1
|
|
|
|
int setregid(gid_t ruid, gid_t euid);
|
|
|
|
FUNCTION
|
|
The real and effective ID's of the current process are set according
|
|
to the arguments. If ruid or euid is -1, the current uid is filled
|
|
in by the system. Unprivileged users may change the real ID to the
|
|
effective ID and vice-versa; only the super-user may make other
|
|
changes.
|
|
|
|
RETURN VALUES
|
|
Upon successful completion, a value of 0 is returned. Otherwise, a
|
|
value of -1 is returned and errno is set to indicate the error.
|
|
|
|
ERRORS
|
|
[EPERM] The current process is not the super-user and a change
|
|
other than changing the effective id to the real id was
|
|
specified.
|
|
|
|
SEE ALSO
|
|
getuid(), getgid(), geteuid(), getegid()
|
|
|
|
NOTES
|
|
Any task can call these functions.
|
|
|
|
HISTORY
|
|
A setuid() and setgid() function calls appeared in Version 6 AT&T
|
|
UNIX. The setreuid() and setregid() function calls appeared in
|
|
4.2BSD.
|
|
|
|
****************************************************************************
|
|
*/
|
|
|
|
AROS_LH1 (int, setuid,
|
|
AROS_LHA(uid_t, uid, D0),
|
|
struct UserGroupBase *, UserGroupBase, 11, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return setreuid(uid, uid);
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH2 (int, setregid,
|
|
AROS_LHA(gid_t, rgid, D0),
|
|
AROS_LHA(gid_t, egid, D1),
|
|
struct UserGroupBase *, UserGroupBase, 14, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct pcred *pc = crfind((pid_t)NULL);
|
|
short error;
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (rgid == NOID)
|
|
rgid = pc->p_rgid;
|
|
if (egid == NOID)
|
|
egid = pc->pc_ucred->cr_gid;
|
|
|
|
/*
|
|
* Allow setting real gid to previous effective, for swapping real and
|
|
* effective. This should be:
|
|
*
|
|
* if (rgid != pc->p_rgid &&
|
|
* (error = suser(pc->pc_ucred, &p->p_acflag)))
|
|
*/
|
|
if ((rgid != pc->p_rgid && rgid != pc->pc_ucred->cr_gid /* XXX */ &&
|
|
(error = suser(pc->pc_ucred))) ||
|
|
(egid != pc->pc_ucred->cr_gid && egid != pc->p_rgid &&
|
|
(error = suser(pc->pc_ucred)))) {
|
|
ug_SetErrno((struct Library *)UserGroupBase, error);
|
|
return -1;
|
|
} else {
|
|
/*
|
|
* Everything's okay, do it. Copy credentials so other references do
|
|
* not see our changes.
|
|
*/
|
|
pc->pc_ucred = crcopy(pc->pc_ucred);
|
|
pc->pc_ucred->cr_gid = egid;
|
|
pc->p_rgid = rgid;
|
|
|
|
return 0;
|
|
}
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
AROS_LH1 (int, setgid,
|
|
AROS_LHA(gid_t, gid, D0),
|
|
struct UserGroupBase *, UserGroupBase, 15, Usergroup)
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return setregid(gid, gid);
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
|
|
AROS_LH2(int, setgroups,
|
|
|
|
/* SYNOPSIS */
|
|
AROS_LHA(int, ngrp, D0),
|
|
AROS_LHA(const gid_t *, groups, A1),
|
|
|
|
/* LOCATION */
|
|
struct UserGroupBase *, UserGroupBase, 17, Usergroup)
|
|
|
|
/* FUNCTION
|
|
Setgroups() sets the group access list of the current user process
|
|
according to the array gidset. The parameter ngroups indicates the
|
|
number of entries in the array and must be no more than NGROUPS, as
|
|
defined in <libraries/usergroup.h>.
|
|
|
|
Only the super-user may set new groups. The super-user can not
|
|
set illegal groups (-1).
|
|
|
|
RESULT
|
|
A 0 value is returned on success, -1 on error, with an error
|
|
code stored in errno and available with ug_GetErr() function.
|
|
|
|
ERRORS
|
|
[EINVAL] An illegal group id was specified.
|
|
[EPERM] The caller has got no necessary privileges.
|
|
[EFAULT] The address specified for gidset is illegal.
|
|
|
|
NOTES
|
|
Any task can call this function.
|
|
|
|
SEE ALSO
|
|
getgroups(), initgroups()
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
register struct pcred *pc = crfind((pid_t)NULL);
|
|
register gid_t *gp;
|
|
register const gid_t *lp;
|
|
short error;
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (error = suser(pc->pc_ucred /*, &p->p_acflag */)) {
|
|
|
|
} else if (ngrp > NGROUPS) {
|
|
error = EINVAL;
|
|
} else if (groups == NULL || ((SIPTR)groups & 1) != 0) {
|
|
error = EFAULT;
|
|
} else {
|
|
pc->pc_ucred = crcopy(pc->pc_ucred);
|
|
pc->pc_ucred->cr_ngroups = ngrp;
|
|
for (gp = pc->pc_ucred->cr_groups, lp = groups; ngrp--; )
|
|
*gp++ = *lp++;
|
|
return 0;
|
|
}
|
|
|
|
ug_SetErrno((struct Library *)UserGroupBase, error);
|
|
return -1;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
|
|
/****** usergroup.library/MU2UG **********************************************
|
|
|
|
NAME
|
|
MU2ID - macro converting MultiUser id to usergroup id
|
|
ID2MU - macro converting usergroup id to MultiUser id
|
|
|
|
SYNOPSIS
|
|
ug_id = MU2ID(mu_id)
|
|
|
|
mu_id = ID2MU(ug_id)
|
|
|
|
FUNCTION
|
|
These macros are used to convert between different user ID
|
|
formats. The mu_id is in the format used by MultiUser filesystem
|
|
and multiuser.library. The ug_id is the format used by Unix and
|
|
usergroup.library.
|
|
|
|
Most of the id values are identical in usergroup.library and
|
|
multiuser.library. However, these two exceptions have values as
|
|
follows:
|
|
|
|
usergroup.library multiuser.library
|
|
super-user 0 65535
|
|
nobody -2 0
|
|
|
|
INPUTS AND RESULTS
|
|
mu_id - user ID in MultiUser format.
|
|
ug_id - user ID in usergroup format.
|
|
|
|
BUGS
|
|
The usergroup id values that won't fit into UWORD are truncated.
|
|
|
|
SEE ALSO
|
|
******************************************************************************
|
|
*/
|
|
|
|
#if 0
|
|
ASM uid_t R_ug_mu2id(REG(d0) UWORD id)
|
|
{
|
|
if (id == 0) {
|
|
return -2;
|
|
} else if (id == 65535) {
|
|
return 0;
|
|
} else {
|
|
return id;
|
|
}
|
|
}
|
|
|
|
ASM UWORD R_ug_id2mu(REG(d0) uid_t id)
|
|
{
|
|
if (id == 0) {
|
|
return 65535;
|
|
} else if (id == -2) {
|
|
return 0;
|
|
} else {
|
|
return id;
|
|
}
|
|
}
|
|
#endif
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
AROS_LH1I(mode_t, umask,
|
|
|
|
/* SYNOPSIS */
|
|
AROS_LHA(mode_t, newmask, D0),
|
|
|
|
/* LOCATION */
|
|
struct Library *, UserGroupBase, 32, Usergroup)
|
|
|
|
/* FUNCTION
|
|
The umask() routine sets the process's file mode creation mask to
|
|
numask and returns the previous value of the mask. The 9 low-order
|
|
access permission bits of numask are used by Unix-compatible
|
|
filesystems, for examble by NFS, to turn off corresponding bits
|
|
requested in file mode. This clearing allows each user to restrict
|
|
the default access to his files.
|
|
|
|
The default mask value is 022 (write access for owner only). Child
|
|
processes should inherit the mask of the calling process.
|
|
|
|
RESULT
|
|
The previous value of the file mode mask is returned by the call.
|
|
|
|
ERRORS
|
|
The umask() function is always successful.
|
|
|
|
SEE ALSO
|
|
getumask()
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct proc *p = procfind((pid_t)NULL);
|
|
|
|
mode_t oldmask = p->p_umask;
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
p->p_umask = newmask;
|
|
|
|
return oldmask ;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
AROS_LH0I(mode_t, getumask,
|
|
|
|
/* SYNOPSIS */
|
|
|
|
/* LOCATION */
|
|
struct Library *, UserGroupBase, 33, Usergroup)
|
|
|
|
/* FUNCTION
|
|
The getumask() routine sets the process's file mode creation mask to
|
|
numask and returns the previous value of the mask. The 9 low-order
|
|
access permission bits of numask are used by Unix-compatible
|
|
filesystems, for examble by NFS, to turn off corresponding bits
|
|
requested in file mode.
|
|
|
|
RESULT
|
|
The value of the file mode mask is returned by the call.
|
|
|
|
ERRORS
|
|
The getumask() function is always successful.
|
|
|
|
SEE ALSO
|
|
umask()
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
struct proc *p = procfind((pid_t)NULL);
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
return p->p_umask;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|
|
|
|
/*****************************************************************************
|
|
|
|
NAME */
|
|
AROS_LH1I(struct UserGroupCredentials *, getcredentials,
|
|
|
|
/* SYNOPSIS */
|
|
AROS_LHA(struct Task *, task, A0),
|
|
|
|
/* LOCATION */
|
|
struct Library *, UserGroupBase, 43, Usergroup)
|
|
|
|
/* FUNCTION
|
|
The function getcredentials() returns all credentials of the given
|
|
task. The credentials include real and effective user and group IDs,
|
|
umask, login name and session ID. If the task pointer is NULL, the
|
|
credentials of current task are returned.
|
|
|
|
RESULT
|
|
A getcredentials() function returns a valid pointer to structure
|
|
UserGroupCredentials on success and a null pointer if an error
|
|
occurs.
|
|
|
|
ERRORS
|
|
[EINVAL] An illegal task pointer was specified.
|
|
|
|
BUGS
|
|
This function leave its result in an internal static object and
|
|
return a pointer to that object. Subsequent calls to this function
|
|
will modify the same object.
|
|
|
|
SEE ALSO
|
|
|
|
******************************************************************************/
|
|
{
|
|
AROS_LIBFUNC_INIT
|
|
|
|
register struct proc *p = procfind((pid_t)task);
|
|
|
|
D(bug("[UserGroup] %s()\n", __func__));
|
|
|
|
if (p != NULL) {
|
|
register struct UserGroupCredentials *c = creds;
|
|
|
|
c->cr_ruid = p->p_cred->p_ruid;
|
|
c->cr_rgid = p->p_cred->p_rgid;
|
|
c->cr_umask = p->p_umask;
|
|
c->cr_euid = p->p_cred->p_euid;
|
|
c->cr_ngroups = p->p_cred->p_ngroups;
|
|
c->cr_session = (struct Task *)p->p_session->s_leader;
|
|
memcpy(c->cr_groups, p->p_cred->p_groups, sizeof(c->cr_groups));
|
|
memcpy(c->cr_login, p->p_session->s_login, sizeof(c->cr_login));
|
|
|
|
return c;
|
|
}
|
|
|
|
return NULL;
|
|
|
|
AROS_LIBFUNC_EXIT
|
|
}
|