Add support for non-root timestamp dirs. This allows the timestamp
dir to be shared via NFS (though this is not recommended).
This commit is contained in:
27
check.c
27
check.c
@@ -145,6 +145,7 @@ update_timestamp(timestampdir, timestampfile)
|
||||
char *timestampfile;
|
||||
{
|
||||
|
||||
set_perms(PERM_TIMESTAMP, 0);
|
||||
if (touch(timestampfile ? timestampfile : timestampdir, time(NULL)) == -1) {
|
||||
if (timestampfile) {
|
||||
int fd = open(timestampfile, O_WRONLY|O_CREAT|O_TRUNC, 0600);
|
||||
@@ -158,6 +159,7 @@ update_timestamp(timestampdir, timestampfile)
|
||||
log_error(NO_EXIT|USE_ERRNO, "Can't mkdir %s", timestampdir);
|
||||
}
|
||||
}
|
||||
set_perms(PERM_ROOT, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -307,6 +309,8 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
char *dirparent = def_str(I_TIMESTAMPDIR);
|
||||
int status = TS_ERROR; /* assume the worst */
|
||||
|
||||
set_perms(PERM_TIMESTAMP, 0);
|
||||
|
||||
/*
|
||||
* Sanity check dirparent and make it if it doesn't already exist.
|
||||
* We start out assuming the worst (that the dir is not sane) and
|
||||
@@ -318,9 +322,9 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
if (!S_ISDIR(sb.st_mode))
|
||||
log_error(NO_EXIT, "%s exists but is not a directory (0%o)",
|
||||
dirparent, sb.st_mode);
|
||||
else if (sb.st_uid != 0)
|
||||
log_error(NO_EXIT, "%s owned by uid %ld, should be owned by root",
|
||||
dirparent, (long) sb.st_uid);
|
||||
else if (sb.st_uid != timestamp_uid)
|
||||
log_error(NO_EXIT, "%s owned by uid %ld, should be uid %ld",
|
||||
dirparent, (long) sb.st_uid, (long) timestamp_uid);
|
||||
else if ((sb.st_mode & 0000022))
|
||||
log_error(NO_EXIT,
|
||||
"%s writable by non-owner (0%o), should be mode 0700",
|
||||
@@ -342,8 +346,10 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
status = TS_MISSING;
|
||||
}
|
||||
}
|
||||
if (status == TS_ERROR)
|
||||
if (status == TS_ERROR) {
|
||||
set_perms(PERM_ROOT, 0);
|
||||
return(status);
|
||||
}
|
||||
|
||||
/*
|
||||
* Sanity check the user's ticket dir. We start by downgrading
|
||||
@@ -361,9 +367,9 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
} else
|
||||
log_error(NO_EXIT, "%s exists but is not a directory (0%o)",
|
||||
timestampdir, sb.st_mode);
|
||||
} else if (sb.st_uid != 0)
|
||||
log_error(NO_EXIT, "%s owned by uid %ld, should be owned by root",
|
||||
timestampdir, (long) sb.st_uid);
|
||||
} else if (sb.st_uid != timestamp_uid)
|
||||
log_error(NO_EXIT, "%s owned by uid %ld, should be uid %ld",
|
||||
timestampdir, (long) sb.st_uid, (long) timestamp_uid);
|
||||
else if ((sb.st_mode & 0000022))
|
||||
log_error(NO_EXIT,
|
||||
"%s writable by non-owner (0%o), should be mode 0700",
|
||||
@@ -402,10 +408,10 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
timestampfile, sb.st_mode);
|
||||
} else {
|
||||
/* If bad uid or file mode, complain and kill the bogus file. */
|
||||
if (sb.st_uid != 0) {
|
||||
if (sb.st_uid != timestamp_uid) {
|
||||
log_error(NO_EXIT,
|
||||
"%s owned by uid %ld, should be owned by root",
|
||||
timestampfile, (long) sb.st_uid);
|
||||
"%s owned by uid %ld, should be uid %ld",
|
||||
timestampfile, (long) sb.st_uid, (long) timestamp_uid);
|
||||
(void) unlink(timestampfile);
|
||||
} else if ((sb.st_mode & 0000022)) {
|
||||
log_error(NO_EXIT,
|
||||
@@ -456,6 +462,7 @@ timestamp_status(timestampdir, timestampfile, user, make_dirs)
|
||||
}
|
||||
}
|
||||
|
||||
set_perms(PERM_ROOT, 0);
|
||||
return(status);
|
||||
}
|
||||
|
||||
|
13
set_perms.c
13
set_perms.c
@@ -145,6 +145,11 @@ set_perms_posix(perm, sudo_mode)
|
||||
fatal("seteuid(SUDOERS_UID)", 1);
|
||||
}
|
||||
break;
|
||||
case PERM_TIMESTAMP:
|
||||
if (seteuid(timestamp_uid))
|
||||
fatal("seteuid(timestamp_uid)", 1);
|
||||
break;
|
||||
|
||||
}
|
||||
}
|
||||
#endif /* !NO_SAVED_IDS && _SC_SAVED_IDS && _SC_VERSION */
|
||||
@@ -213,6 +218,10 @@ set_perms_fallback(perm, sudo_mode)
|
||||
fatal("setreuid(0, SUDOERS_UID)", 1);
|
||||
}
|
||||
break;
|
||||
case PERM_TIMESTAMP:
|
||||
if (setreuid(0, timestamp_uid))
|
||||
fatal("setreuid(0, timestamp_uid)", 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -276,6 +285,10 @@ set_perms_fallback(perm, sudo_mode)
|
||||
fatal("seteuid(SUDOERS_UID)", 1);
|
||||
}
|
||||
break;
|
||||
case PERM_TIMESTAMP:
|
||||
if (seteuid(timestamp_uid))
|
||||
fatal("seteuid(timestamp_uid)", 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif /* HAVE_SETREUID */
|
||||
|
17
sudo.c
17
sudo.c
@@ -131,6 +131,7 @@ FILE *sudoers_fp = NULL;
|
||||
struct interface *interfaces;
|
||||
int num_interfaces;
|
||||
int tgetpass_flags;
|
||||
int timestamp_uid;
|
||||
extern int errorlineno;
|
||||
#if defined(RLIMIT_CORE) && !defined(SUDO_DEVEL)
|
||||
static struct rlimit corelimit;
|
||||
@@ -287,6 +288,22 @@ main(argc, argv, envp)
|
||||
log_error(NO_MAIL|MSG_ONLY, "no passwd entry for %s!", *user_runas);
|
||||
}
|
||||
|
||||
/*
|
||||
* Look up the timestamp dir owner if one is specified.
|
||||
*/
|
||||
if (def_str(I_TIMESTAMPOWNER)) {
|
||||
struct passwd *pw;
|
||||
|
||||
if (*def_str(I_TIMESTAMPOWNER) == '#')
|
||||
pw = getpwuid(atoi(def_str(I_TIMESTAMPOWNER) + 1));
|
||||
else
|
||||
pw = getpwnam(def_str(I_TIMESTAMPOWNER));
|
||||
if (!pw)
|
||||
log_error(0, "timestamp owner (%s): No such user",
|
||||
def_str(I_TIMESTAMPOWNER));
|
||||
timestamp_uid = pw->pw_uid;
|
||||
}
|
||||
|
||||
/* This goes after the sudoers parse since we honor sudoers options. */
|
||||
if (sudo_mode == MODE_KILL || sudo_mode == MODE_INVALIDATE) {
|
||||
remove_timestamp((sudo_mode == MODE_KILL));
|
||||
|
2
sudo.h
2
sudo.h
@@ -116,6 +116,7 @@ struct sudo_user {
|
||||
#define PERM_FULL_USER 0x03
|
||||
#define PERM_SUDOERS 0x04
|
||||
#define PERM_RUNAS 0x05
|
||||
#define PERM_TIMESTAMP 0x06
|
||||
|
||||
/*
|
||||
* Shortcuts for sudo_user contents.
|
||||
@@ -235,6 +236,7 @@ extern int Argc;
|
||||
extern char **Argv;
|
||||
extern FILE *sudoers_fp;
|
||||
extern int tgetpass_flags;
|
||||
extern int timestamp_uid;
|
||||
|
||||
extern void (*set_perms) __P((int, int));
|
||||
#endif
|
||||
|
Reference in New Issue
Block a user