From ef258354719127382087c58e5c0f83ee45c958f6 Mon Sep 17 00:00:00 2001 From: Bdale Garbee Date: Thu, 28 Jun 2012 12:01:05 -0600 Subject: [PATCH] Imported Upstream version 1.8.5p2 --- ChangeLog | 41 ++++++++++ NEWS | 14 ++++ configure | 18 ++--- configure.in | 2 +- plugins/sudoers/set_perms.c | 8 +- plugins/sudoers/sudoers.c | 18 ++++- plugins/sudoers/toke.c | 2 + plugins/sudoers/toke.l | 2 + src/env_hooks.c | 149 +++++++++++++++++++----------------- src/sudo.h | 3 + src/tgetpass.c | 4 +- 11 files changed, 170 insertions(+), 91 deletions(-) diff --git a/ChangeLog b/ChangeLog index ddfb389..ce73728 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,44 @@ +2012-05-29 Todd C. Miller + + * NEWS: + Update for sudo 1.8.5p2 + [d369d4d40a19] + +2012-05-27 Todd C. Miller + + * src/env_hooks.c, src/sudo.h, src/tgetpass.c: + Provide unhooked version of getenv() and use it when looking up + DISPLAY and SUDO_ASKPASS in the environment. + [04dbdccf4a14] + +2012-05-21 Todd C. Miller + + * plugins/sudoers/set_perms.c, plugins/sudoers/sudoers.c: + If sudoers_mode is group-readable but the actual sudoers file is + not, open the file as uid 0, not uid 1. This fixes a problem when + sudoers has a more restrictive mode than what sudo expects to find. + In older versions, sudo would silently chmod the file to add the + group-readable bit. + [c056b6003e6f] + +2012-05-17 Todd C. Miller + + * NEWS, configure, configure.in: + Update for 1.8.5p1 + [c33c49bf5b4b] + + * plugins/sudoers/toke.c, plugins/sudoers/toke.l: + Fix #includedir; from Mike Frysinger + [d4833d4e39a0] + + * plugins/sudoers/check.c: + Don't prompt for a password if the user is in the exempt group, is + root, or is running the command as themselves even if the -k option + was specified. This makes "sudo -k command" consistent with the + behavior one would get if the user ran "sudo -k" immediately before + running the command. + [632b3961df00] + 2012-05-15 Todd C. Miller * INSTALL: diff --git a/NEWS b/NEWS index 2e65329..34e7b9a 100644 --- a/NEWS +++ b/NEWS @@ -1,3 +1,17 @@ +What's new in Sudo 1.8.5p2? + + * Fixed use of the SUDO_ASKPASS environment variable which was + broken in Sudo 1.8.5. + + * Fixed a problem reading the sudoers file when the file mode is + more restrictive than the expected mode. For example, when the + expected sudoers file mode is 0440 but the actual mode is 0400. + +What's new in Sudo 1.8.5p1? + + * Fixed a bug that prevented files in an include directory from + being evaluated. + What's new in Sudo 1.8.5? * When "noexec" is enabled, sudo_noexec.so will now be prepended diff --git a/configure b/configure index 9c2fcba..4d12595 100755 --- a/configure +++ b/configure @@ -1,6 +1,6 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.68 for sudo 1.8.5. +# Generated by GNU Autoconf 2.68 for sudo 1.8.5p2. # # Report bugs to . # @@ -570,8 +570,8 @@ MAKEFLAGS= # Identity of this package. PACKAGE_NAME='sudo' PACKAGE_TARNAME='sudo' -PACKAGE_VERSION='1.8.5' -PACKAGE_STRING='sudo 1.8.5' +PACKAGE_VERSION='1.8.5p2' +PACKAGE_STRING='sudo 1.8.5p2' PACKAGE_BUGREPORT='http://www.sudo.ws/bugs/' PACKAGE_URL='' @@ -1447,7 +1447,7 @@ if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures sudo 1.8.5 to adapt to many kinds of systems. +\`configure' configures sudo 1.8.5p2 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... @@ -1512,7 +1512,7 @@ fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of sudo 1.8.5:";; + short | recursive ) echo "Configuration of sudo 1.8.5p2:";; esac cat <<\_ACEOF @@ -1730,7 +1730,7 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -sudo configure 1.8.5 +sudo configure 1.8.5p2 generated by GNU Autoconf 2.68 Copyright (C) 2010 Free Software Foundation, Inc. @@ -2434,7 +2434,7 @@ cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by sudo $as_me 1.8.5, which was +It was created by sudo $as_me 1.8.5p2, which was generated by GNU Autoconf 2.68. Invocation command line was $ $0 $@ @@ -20682,7 +20682,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by sudo $as_me 1.8.5, which was +This file was extended by sudo $as_me 1.8.5p2, which was generated by GNU Autoconf 2.68. Invocation command line was CONFIG_FILES = $CONFIG_FILES @@ -20748,7 +20748,7 @@ _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ -sudo config.status 1.8.5 +sudo config.status 1.8.5p2 configured by $0, generated by GNU Autoconf 2.68, with options \\"\$ac_cs_config\\" diff --git a/configure.in b/configure.in index 3ab4fa2..6ec6016 100644 --- a/configure.in +++ b/configure.in @@ -3,7 +3,7 @@ dnl Process this file with GNU autoconf to produce a configure script. dnl dnl Copyright (c) 1994-1996,1998-2012 Todd C. Miller dnl -AC_INIT([sudo], [1.8.5], [http://www.sudo.ws/bugs/], [sudo]) +AC_INIT([sudo], [1.8.5p2], [http://www.sudo.ws/bugs/], [sudo]) AC_CONFIG_HEADER([config.h pathnames.h]) dnl dnl Note: this must come after AC_INIT diff --git a/plugins/sudoers/set_perms.c b/plugins/sudoers/set_perms.c index 97d6ee9..e2ae512 100644 --- a/plugins/sudoers/set_perms.c +++ b/plugins/sudoers/set_perms.c @@ -307,7 +307,7 @@ set_perms(int perm) * we use a non-zero uid in order to avoid NFS lossage. * Using uid 1 is a bit bogus but should work on all OS's. */ - if (sudoers_uid == ROOT_UID && (sudoers_mode & 040)) + if (sudoers_uid == ROOT_UID && (sudoers_mode & S_IRGRP)) state->euid = 1; else state->euid = sudoers_uid; @@ -617,7 +617,7 @@ set_perms(int perm) * we use a non-zero uid in order to avoid NFS lossage. * Using uid 1 is a bit bogus but should work on all OS's. */ - if (sudoers_uid == ROOT_UID && (sudoers_mode & 040)) + if (sudoers_uid == ROOT_UID && (sudoers_mode & S_IRGRP)) state->euid = 1; else state->euid = sudoers_uid; @@ -990,7 +990,7 @@ set_perms(int perm) * we use a non-zero uid in order to avoid NFS lossage. * Using uid 1 is a bit bogus but should work on all OS's. */ - if (sudoers_uid == ROOT_UID && (sudoers_mode & 040)) + if (sudoers_uid == ROOT_UID && (sudoers_mode & S_IRGRP)) state->euid = 1; else state->euid = sudoers_uid; @@ -1276,7 +1276,7 @@ set_perms(int perm) * we use a non-zero uid in order to avoid NFS lossage. * Using uid 1 is a bit bogus but should work on all OS's. */ - if (sudoers_uid == ROOT_UID && (sudoers_mode & 040)) + if (sudoers_uid == ROOT_UID && (sudoers_mode & S_IRGRP)) state->euid = 1; else state->euid = sudoers_uid; diff --git a/plugins/sudoers/sudoers.c b/plugins/sudoers/sudoers.c index af72c37..9002712 100644 --- a/plugins/sudoers/sudoers.c +++ b/plugins/sudoers/sudoers.c @@ -975,13 +975,23 @@ open_sudoers(const char *sudoers, bool doedit, bool *keepopen) switch (sudo_secure_file(sudoers, sudoers_uid, sudoers_gid, &sb)) { case SUDO_PATH_SECURE: + /* + * If we are expecting sudoers to be group readable but + * it is not, we must open the file as root, not uid 1. + */ + if (sudoers_uid == ROOT_UID && (sudoers_mode & S_IRGRP)) { + if ((sb.st_mode & S_IRGRP) == 0) { + restore_perms(); + set_perms(PERM_ROOT); + } + } + /* + * Open sudoers and make sure we can read it so we can present + * the user with a reasonable error message (unlike the lexer). + */ if ((fp = fopen(sudoers, "r")) == NULL) { log_error(USE_ERRNO, _("unable to open %s"), sudoers); } else { - /* - * Make sure we can actually read sudoers so we can present the - * user with a reasonable error message (unlike the lexer). - */ if (sb.st_size != 0 && fgetc(fp) == EOF) { log_error(USE_ERRNO, _("unable to read %s"), sudoers); diff --git a/plugins/sudoers/toke.c b/plugins/sudoers/toke.c index 83125a3..40bc147 100644 --- a/plugins/sudoers/toke.c +++ b/plugins/sudoers/toke.c @@ -3525,6 +3525,8 @@ _push_include(char *path, bool isdir) if (isdir) { struct stat sb; switch (sudo_secure_dir(path, sudoers_uid, sudoers_gid, &sb)) { + case SUDO_PATH_SECURE: + break; case SUDO_PATH_MISSING: debug_return_bool(false); case SUDO_PATH_BAD_TYPE: diff --git a/plugins/sudoers/toke.l b/plugins/sudoers/toke.l index 40981cd..84e8de6 100644 --- a/plugins/sudoers/toke.l +++ b/plugins/sudoers/toke.l @@ -816,6 +816,8 @@ _push_include(char *path, bool isdir) if (isdir) { struct stat sb; switch (sudo_secure_dir(path, sudoers_uid, sudoers_gid, &sb)) { + case SUDO_PATH_SECURE: + break; case SUDO_PATH_MISSING: debug_return_bool(false); case SUDO_PATH_BAD_TYPE: diff --git a/src/env_hooks.c b/src/env_hooks.c index c518cb1..1e1db8c 100644 --- a/src/env_hooks.c +++ b/src/env_hooks.c @@ -69,6 +69,19 @@ rpl_getenv(const char *name) typedef char * (*sudo_fn_getenv_t)(const char *); +char * +getenv_unhooked(const char *name) +{ +#if defined(HAVE_DLOPEN) && defined(RTLD_NEXT) + sudo_fn_getenv_t fn; + + fn = (sudo_fn_getenv_t)dlsym(RTLD_NEXT, "getenv"); + if (fn != NULL) + return fn(name); +#endif /* HAVE_DLOPEN && RTLD_NEXT */ + return rpl_getenv(name); +} + char * getenv(const char *name) { @@ -79,16 +92,8 @@ getenv(const char *name) return val; case SUDO_HOOK_RET_ERROR: return NULL; - default: { -#if defined(HAVE_DLOPEN) && defined(RTLD_NEXT) - sudo_fn_getenv_t fn; - - fn = (sudo_fn_getenv_t)dlsym(RTLD_NEXT, "getenv"); - if (fn != NULL) - return fn(name); -#endif /* HAVE_DLOPEN && RTLD_NEXT */ - return rpl_getenv(name); - } + default: + return getenv_unhooked(name); } } @@ -136,6 +141,19 @@ rpl_putenv(PUTENV_CONST char *string) typedef int (*sudo_fn_putenv_t)(PUTENV_CONST char *); +static int +putenv_unhooked(PUTENV_CONST char *string) +{ +#if defined(HAVE_DLOPEN) && defined(RTLD_NEXT) + sudo_fn_putenv_t fn; + + fn = (sudo_fn_putenv_t)dlsym(RTLD_NEXT, "putenv"); + if (fn != NULL) + return fn(string); +#endif /* HAVE_DLOPEN && RTLD_NEXT */ + return rpl_putenv(string); +} + int putenv(PUTENV_CONST char *string) { @@ -144,16 +162,8 @@ putenv(PUTENV_CONST char *string) return 0; case SUDO_HOOK_RET_ERROR: return -1; - default: { -#if defined(HAVE_DLOPEN) && defined(RTLD_NEXT) - sudo_fn_putenv_t fn; - - fn = (sudo_fn_putenv_t)dlsym(RTLD_NEXT, "putenv"); - if (fn != NULL) - return fn(string); -#endif /* HAVE_DLOPEN && RTLD_NEXT */ - return rpl_putenv(string); - } + default: + return putenv_unhooked(string); } } @@ -201,6 +211,19 @@ rpl_setenv(const char *var, const char *val, int overwrite) typedef int (*sudo_fn_setenv_t)(const char *, const char *, int); +static int +setenv_unhooked(const char *var, const char *val, int overwrite) +{ +#if defined(HAVE_SETENV) && defined(HAVE_DLOPEN) && defined(RTLD_NEXT) + sudo_fn_setenv_t fn; + + fn = (sudo_fn_setenv_t)dlsym(RTLD_NEXT, "setenv"); + if (fn != NULL) + return fn(var, val, overwrite); +#endif /* HAVE_SETENV && HAVE_DLOPEN && RTLD_NEXT */ + return rpl_setenv(var, val, overwrite); +} + int setenv(const char *var, const char *val, int overwrite) { @@ -209,24 +232,12 @@ setenv(const char *var, const char *val, int overwrite) return 0; case SUDO_HOOK_RET_ERROR: return -1; - default: { -#if defined(HAVE_SETENV) && defined(HAVE_DLOPEN) && defined(RTLD_NEXT) - sudo_fn_setenv_t fn; - - fn = (sudo_fn_setenv_t)dlsym(RTLD_NEXT, "setenv"); - if (fn != NULL) - return fn(var, val, overwrite); -#endif /* HAVE_SETENV && HAVE_DLOPEN && RTLD_NEXT */ - return rpl_setenv(var, val, overwrite); - } + default: + return setenv_unhooked(var, val, overwrite); } } -#ifdef UNSETENV_VOID -static void -#else -int -#endif +static int rpl_unsetenv(const char *var) { char **ep = environ; @@ -234,11 +245,7 @@ rpl_unsetenv(const char *var) if (var == NULL || *var == '\0' || strchr(var, '=') != NULL) { errno = EINVAL; -#ifdef UNSETENV_VOID - return; -#else return -1; -#endif } len = strlen(var); @@ -253,9 +260,7 @@ rpl_unsetenv(const char *var) ep++; } } -#ifndef UNSETENV_VOID return 0; -#endif } #ifdef UNSETENV_VOID @@ -264,47 +269,49 @@ typedef void (*sudo_fn_unsetenv_t)(const char *); typedef int (*sudo_fn_unsetenv_t)(const char *); #endif -#ifdef UNSETENV_VOID -void -unsetenv(const char *var) +static int +unsetenv_unhooked(const char *var) { - switch (process_hooks_unsetenv(var)) { - case SUDO_HOOK_RET_STOP: - return 0; - case SUDO_HOOK_RET_ERROR: - return -1; - default: { + int rval = 0; #if defined(HAVE_UNSETENV) && defined(HAVE_DLOPEN) && defined(RTLD_NEXT) - sudo_fn_unsetenv_t fn; - - fn = (sudo_fn_unsetenv_t)dlsym(RTLD_NEXT, "unsetenv"); - if (fn != NULL) - fn(var); - else + sudo_fn_unsetenv_t fn; + + fn = (sudo_fn_unsetenv_t)dlsym(RTLD_NEXT, "unsetenv"); + if (fn != NULL) { +# ifdef UNSETENV_VOID + fn(var); +# else + rval = fn(var); +# endif + } else #endif /* HAVE_UNSETENV && HAVE_DLOPEN && RTLD_NEXT */ - rpl_unsetenv(var); - } + { + rval = rpl_unsetenv(var); } + return rval; } + +#ifdef UNSETENV_VOID +void #else int +#endif unsetenv(const char *var) { + int rval; + switch (process_hooks_unsetenv(var)) { case SUDO_HOOK_RET_STOP: - return 0; + rval = 0; + break; case SUDO_HOOK_RET_ERROR: - return -1; - default: { -#if defined(HAVE_UNSETENV) && defined(HAVE_DLOPEN) && defined(RTLD_NEXT) - sudo_fn_unsetenv_t fn; - - fn = (sudo_fn_unsetenv_t)dlsym(RTLD_NEXT, "unsetenv"); - if (fn != NULL) - return fn(var); -#endif /* HAVE_UNSETENV && HAVE_DLOPEN && RTLD_NEXT */ - return rpl_unsetenv(var); - } + rval = -1; + break; + default: + rval = unsetenv_unhooked(var); + break; } +#ifndef UNSETENV_VOID + return rval; +#endif } -#endif /* UNSETENV_VOID */ diff --git a/src/sudo.h b/src/sudo.h index 8843914..c50f1e1 100644 --- a/src/sudo.h +++ b/src/sudo.h @@ -237,6 +237,9 @@ int process_hooks_setenv(const char *name, const char *value, int overwrite); int process_hooks_putenv(char *string); int process_hooks_unsetenv(const char *name); +/* env_hooks.c */ +char *getenv_unhooked(const char *name); + /* interfaces.c */ int get_net_ifs(char **addrinfo); diff --git a/src/tgetpass.c b/src/tgetpass.c index e9915b2..b23db4c 100644 --- a/src/tgetpass.c +++ b/src/tgetpass.c @@ -78,7 +78,7 @@ tgetpass(const char *prompt, int timeout, int flags) (void) fflush(stdout); if (askpass == NULL) { - askpass = getenv("SUDO_ASKPASS"); + askpass = getenv_unhooked("SUDO_ASKPASS"); if (askpass == NULL || *askpass == '\0') askpass = sudo_conf_askpass_path(); } @@ -86,7 +86,7 @@ tgetpass(const char *prompt, int timeout, int flags) /* If no tty present and we need to disable echo, try askpass. */ if (!ISSET(flags, TGP_STDIN|TGP_ECHO|TGP_ASKPASS|TGP_NOECHO_TRY) && !tty_present()) { - if (askpass == NULL || getenv("DISPLAY") == NULL) { + if (askpass == NULL || getenv_unhooked("DISPLAY") == NULL) { warningx(_("no tty present and no askpass program specified")); debug_return_str(NULL); } -- 2.30.2