>From a0f12bec4f9cd2752acdce8f3f8d463789bda36d Mon Sep 17 00:00:00 2001
From: Simo Sorce <simo@redhat.com>
Date: Wed, 20 Nov 2013 11:58:22 -0500
Subject: [PATCH] Use secure_getenv in client and mechglue module

proxymehc.so may be used in setuid binaries so follow best security
practices and use secure_getenv() if available.
Fallback to poorman emulation when secure_getenv() is not available.

Resolves: https://fedorahosted.org/gss-proxy/ticket/110
---
 proxy/Makefile.am               |  7 ++++---
 proxy/configure.ac              |  2 ++
 proxy/src/client/gpm_common.c   |  2 +-
 proxy/src/gp_common.h           |  1 +
 proxy/src/gp_util.c             | 20 ++++++++++++++++++++
 proxy/src/mechglue/gss_plugin.c |  4 ++--
 6 files changed, 30 insertions(+), 6 deletions(-)

diff --git a/proxy/Makefile.am b/proxy/Makefile.am
index 065be6ebcee0b4762f6d3cb603207476240d3b51..c94642167198e92f6cefa5578a45dc922a88e10d 100644
--- a/proxy/Makefile.am
+++ b/proxy/Makefile.am
@@ -102,7 +102,9 @@ GP_RPCCLI_OBJ = \
     src/client/gpm_wrap.c \
     src/client/gpm_unwrap.c \
     src/client/gpm_wrap_size_limit.c \
-    src/client/gpm_common.c
+    src/client/gpm_common.c \
+    src/gp_util.c
+
 GP_MECHGLUE_OBJ = \
     src/mechglue/gpp_accept_sec_context.c \
     src/mechglue/gpp_acquire_cred.c \
@@ -114,8 +116,7 @@ GP_MECHGLUE_OBJ = \
     src/mechglue/gpp_indicate_mechs.c \
     src/mechglue/gpp_priv_integ.c \
     src/mechglue/gpp_misc.c \
-    src/mechglue/gss_plugin.c \
-    src/gp_util.c
+    src/mechglue/gss_plugin.c
 
 dist_noinst_HEADERS = \
     rpcgen/gp_rpc.h \
diff --git a/proxy/configure.ac b/proxy/configure.ac
index b75a1ef35fbcd0672e4b5f9e7e0ad886cc5a5099..a0cc4ef1ac458cfc4851f0543b685eea43cd115d 100644
--- a/proxy/configure.ac
+++ b/proxy/configure.ac
@@ -149,6 +149,8 @@ AC_CHECK_LIB(gssrpc, gssrpc_xdrmem_create,,
              [$GSSAPI_LIBS $GSSRPC_LIBS])
 AC_SUBST([GSSRPC_LIBS])
 
+AC_CHECK_FUNCS([__secure_getenv secure_getenv])
+
 WITH_INITSCRIPT
 if test x$initscript = xsystemd; then
     WITH_SYSTEMD_UNIT_DIR
diff --git a/proxy/src/client/gpm_common.c b/proxy/src/client/gpm_common.c
index df1f5a1191760b2c84d3b847204068da44dd5a5c..74296dafa4d83a5f014ac2dd1609327e8ecf41fc 100644
--- a/proxy/src/client/gpm_common.c
+++ b/proxy/src/client/gpm_common.c
@@ -68,7 +68,7 @@ static int get_pipe_name(struct gpm_ctx *gpmctx, char *name)
     const char *socket;
     int ret;
 
-    socket = getenv("GSSPROXY_SOCKET");
+    socket = gp_getenv("GSSPROXY_SOCKET");
     if (!socket) {
         socket = GP_SOCKET_NAME;
     }
diff --git a/proxy/src/gp_common.h b/proxy/src/gp_common.h
index 9e4ae81cb7d974aad3d7633681943f51a8f53449..b5c525f37cd55460cba1deee866f1b236b6bc8e1 100644
--- a/proxy/src/gp_common.h
+++ b/proxy/src/gp_common.h
@@ -67,6 +67,7 @@
 
 bool gp_same(const char *a, const char *b);
 bool gp_boolean_is_true(const char *s);
+char *gp_getenv(const char *name);
 
 #include "rpcgen/gss_proxy.h"
 
diff --git a/proxy/src/gp_util.c b/proxy/src/gp_util.c
index 8400da14d040c16ea901c9cfe2fc4f22a97c190d..a6c870ffd71564be81c4d05e9d1890b4e054812e 100644
--- a/proxy/src/gp_util.c
+++ b/proxy/src/gp_util.c
@@ -23,8 +23,10 @@
    DEALINGS IN THE SOFTWARE.
 */
 
+#include "config.h"
 #include <stdbool.h>
 #include <string.h>
+#include <stdlib.h>
 
 bool gp_same(const char *a, const char *b)
 {
@@ -46,3 +48,21 @@ bool gp_boolean_is_true(const char *s)
 
     return false;
 }
+
+char *gp_getenv(const char *name)
+{
+#if HAVE_SECURE_GETENV
+    return secure_getenv(name);
+#elif HAVE___SECURE_GETENV
+    return __secure_getenv(name);
+#else
+#include <unistd.h>
+#include <sys/types.h>
+#warning secure_getenv not available, falling back to poorman emulation
+    if ((getuid() == geteuid()) &&
+        (getgid() == getegid())) {
+        return getenv(name);
+    }
+    return NULL;
+#endif
+}
diff --git a/proxy/src/mechglue/gss_plugin.c b/proxy/src/mechglue/gss_plugin.c
index 5b40df935fbb569935df4a30903667e36ff1b31f..372ab2e7ce32d423f6e67f3976fe5812379e08c7 100644
--- a/proxy/src/mechglue/gss_plugin.c
+++ b/proxy/src/mechglue/gss_plugin.c
@@ -64,7 +64,7 @@ enum gpp_behavior gpp_get_behavior(void)
     char *envval;
 
     if (behavior == GPP_UNINITIALIZED) {
-        envval = getenv("GSSPROXY_BEHAVIOR");
+        envval = gp_getenv("GSSPROXY_BEHAVIOR");
         if (envval) {
             if (strcmp(envval, "LOCAL_ONLY") == 0) {
                 behavior = GPP_LOCAL_ONLY;
@@ -102,7 +102,7 @@ gss_OID_set gss_mech_interposer(gss_OID mech_type)
 
     /* avoid looping in the gssproxy daemon by avoiding to interpose
      * any mechanism */
-    envval = getenv("GSS_USE_PROXY");
+    envval = gp_getenv("GSS_USE_PROXY");
     if (!envval) {
         return NULL;
     }
-- 
1.8.4.2

