1
1
mirror of https://github.com/systemd/systemd-stable.git synced 2025-03-10 00:58:20 +03:00

[PATCH] add $local user spport for permissions

This commit is contained in:
kay.sievers@vrfy.org 2004-03-01 22:42:30 -08:00 committed by Greg KH
parent 311e9ae681
commit 534c853df5
3 changed files with 119 additions and 2 deletions

View File

@ -25,6 +25,7 @@
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <fcntl.h>
#include <sys/types.h>
#include "klibc_fixups.h"
@ -32,6 +33,8 @@
#define PW_FILE "/etc/passwd"
#define GR_FILE "/etc/group"
#define UTMP_FILE "/var/run/utmp"
/* return the id of a passwd style line, selected by the users name */
static unsigned long get_id_by_name(const char *uname, const char *dbfile)
@ -107,4 +110,38 @@ struct group *getgrnam(const char *name)
return &gr;
}
int ufd = -1;
void setutent()
{
if (ufd < 0)
ufd = open(UTMP_FILE, O_RDONLY);
fcntl(ufd, F_SETFD, FD_CLOEXEC);
lseek(ufd, 0, SEEK_SET);
}
void endutent() {
if (ufd < 0)
return;
close(ufd);
ufd = -1;
}
struct utmp *getutent(void)
{
static struct utmp utmp;
int retval;
if (ufd < 0) {
setutent();
if (ufd < 0)
return NULL;
}
retval = read(ufd, &utmp, sizeof(struct utmp));
if (retval < 1)
return NULL;
return &utmp;
}
#endif

View File

@ -1,7 +1,7 @@
#ifdef __KLIBC__
#ifndef KLIBC_FIXUPS_H
#define KLIBC_FIXUPS_H
#define KLIBC_FIXUPS_H
struct passwd {
char *pw_name; /* user name */
@ -23,6 +23,49 @@ struct group {
struct passwd *getpwnam(const char *name);
struct group *getgrnam(const char *name);
#endif
#define UT_LINESIZE 32
#define UT_NAMESIZE 32
#define UT_HOSTSIZE 256
#define USER_PROCESS 7 /* normal process */
#define ut_time ut_tv.tv_sec
extern int ufd;
struct exit_status {
short int e_termination; /* process termination status */
short int e_exit; /* process exit status */
};
struct utmp
{
short int ut_type; /* type of login */
pid_t ut_pid; /* pid of login process */
char ut_line[UT_LINESIZE]; /* devicename */
char ut_id[4]; /* Inittab id */
char ut_user[UT_NAMESIZE]; /* username */
char ut_host[UT_HOSTSIZE]; /* hostname for remote login */
struct exit_status ut_exit; /* exit status of a process marked as DEAD_PROCESS */
/* The ut_session and ut_tv fields must be the same size for 32 and 64-bit */
#if __WORDSIZE == 64 && defined __WORDSIZE_COMPAT32
int32_t ut_session; /* sid used for windowing */
struct {
int32_t tv_sec; /* seconds */
int32_t tv_usec; /* microseconds */
} ut_tv;
#else
long int ut_session;
struct timeval ut_tv;
#endif
int32_t ut_addr_v6[4]; /* internet address of remote host */
char __unused[20]; /* reserved for future use */
};
struct utmp *getutent(void);
void setutent(void);
void endutent(void);
#endif /* KLIBC_FIXUPS_H */
#endif /* __KLIBC__ */

View File

@ -32,6 +32,7 @@
#include <grp.h>
#ifndef __KLIBC__
#include <pwd.h>
#include <utmp.h>
#endif
#include "libsysfs/sysfs/libsysfs.h"
@ -44,6 +45,8 @@
#include "udevdb.h"
#include "klibc_fixups.h"
#define LOCAL_USER "$local"
/*
* Right now the major/minor of a device is stored in a file called
* "dev" in sysfs.
@ -132,6 +135,37 @@ static int make_node(char *filename, int major, int minor, unsigned int mode, ui
return 0;
}
/* get the local logged in user */
static void set_to_local_user(char *user)
{
struct utmp *u;
time_t recent = 0;
strnfieldcpy(user, default_owner_str, OWNER_SIZE);
setutent();
while (1) {
u = getutent();
if (u == NULL)
break;
/* is this a user login ? */
if (u->ut_type != USER_PROCESS)
continue;
/* is this a local login ? */
if (strcmp(u->ut_host, ""))
continue;
if (u->ut_time > recent) {
recent = u->ut_time;
strfieldcpy(user, u->ut_user);
dbg("local user is '%s'", user);
break;
}
}
endutent();
}
static int create_node(struct udevice *dev, int fake)
{
struct stat stats;
@ -175,6 +209,9 @@ static int create_node(struct udevice *dev, int fake)
if (endptr[0] == '\0')
uid = (uid_t) id;
else {
if (strncmp(dev->owner, LOCAL_USER, sizeof(LOCAL_USER)) == 0)
set_to_local_user(dev->owner);
struct passwd *pw = getpwnam(dev->owner);
if (pw == NULL)
dbg("specified user unknown '%s'", dev->owner);