You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@trafficserver.apache.org by du...@apache.org on 2018/05/30 21:08:31 UTC

[trafficserver] branch master updated: traffic_crashlog can now terminate itself when using custom startup script

This is an automated email from the ASF dual-hosted git repository.

duke8253 pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/trafficserver.git


The following commit(s) were added to refs/heads/master by this push:
     new 922f080  traffic_crashlog can now terminate itself when using custom startup script
922f080 is described below

commit 922f080282253c31e59b4bd626d7afc79a6ca2a2
Author: Fei Deng <du...@gmail.com>
AuthorDate: Fri May 25 09:45:11 2018 -0500

    traffic_crashlog can now terminate itself when using custom startup script
---
 cmd/traffic_crashlog/traffic_crashlog.cc | 58 ++++++++++++++++++++++++++++----
 proxy/Crash.cc                           |  5 +--
 proxy/Main.cc                            | 14 ++++----
 proxy/Main.h                             |  2 +-
 4 files changed, 62 insertions(+), 17 deletions(-)

diff --git a/cmd/traffic_crashlog/traffic_crashlog.cc b/cmd/traffic_crashlog/traffic_crashlog.cc
index cca4113..3f04d17 100644
--- a/cmd/traffic_crashlog/traffic_crashlog.cc
+++ b/cmd/traffic_crashlog/traffic_crashlog.cc
@@ -37,6 +37,7 @@ static int debug_mode     = false;
 static int wait_mode      = false;
 static char *host_triplet = nullptr;
 static int target_pid     = getppid();
+static char *user         = nullptr;
 
 // If pid_t is not sizeof(int), we will have to jiggle argument parsing.
 extern char __pid_size_static_assert[sizeof(pid_t) == sizeof(int) ? 0 : -1];
@@ -48,6 +49,7 @@ static const ArgumentDescription argument_descriptions[] = {
   {"wait", '-', "Stop until signalled at startup", "F", &wait_mode, nullptr, nullptr},
   {"syslog", '-', "Syslog after writing a crash log", "F", &syslog_mode, nullptr, nullptr},
   {"debug", '-', "Enable debugging mode", "F", &debug_mode, nullptr, nullptr},
+  {"user", '-', "Username used to set privileges", "S*", &user, nullptr, nullptr},
   HELP_ARGUMENT_DESCRIPTION(),
   VERSION_ARGUMENT_DESCRIPTION(),
   RUNROOT_ARGUMENT_DESCRIPTION()};
@@ -85,6 +87,48 @@ crashlog_open(const char *path)
   return (fd == -1) ? nullptr : fdopen(fd, "w");
 }
 
+static unsigned
+max_passwd_size()
+{
+#if defined(_SC_GETPW_R_SIZE_MAX)
+  long val = sysconf(_SC_GETPW_R_SIZE_MAX);
+  if (val > 0) {
+    return (unsigned)val;
+  }
+#endif
+
+  return 4096;
+}
+
+static void
+change_privileges()
+{
+  struct passwd *pwd;
+  struct passwd pbuf;
+  char buf[max_passwd_size()];
+
+  if (getpwnam_r(user, &pbuf, buf, sizeof(buf), &pwd) != 0) {
+    Error("missing password database entry for username '%s': %s", user, strerror(errno));
+    return;
+  }
+
+  if (pwd == nullptr) {
+    // Password entry not found ...
+    Error("missing password database entry for '%s'", user);
+    return;
+  }
+
+  if (setegid(pwd->pw_gid) != 0) {
+    Error("setegid(%d) failed: %s", pwd->pw_gid, strerror(errno));
+    return;
+  }
+
+  if (setreuid(pwd->pw_uid, 0) != 0) {
+    Error("setreuid(%d, %d) failed: %s", pwd->pw_uid, 0, strerror(errno));
+    return;
+  }
+}
+
 int
 main(int /* argc ATS_UNUSED */, const char **argv)
 {
@@ -101,6 +145,13 @@ main(int /* argc ATS_UNUSED */, const char **argv)
   // Process command line arguments and dump into variables
   process_args(&appVersionInfo, argument_descriptions, countof(argument_descriptions), argv);
 
+  // XXX This is a hack. traffic_manager starts traffic_server with the euid of the admin user. We are still
+  // privileged, but won't be able to open files in /proc or ptrace the target. This really should be fixed
+  // in traffic_manager.
+  if (getuid() == 0) {
+    change_privileges();
+  }
+
   if (wait_mode) {
     EnableDeathSignal(SIGKILL);
     kill(getpid(), SIGSTOP);
@@ -112,13 +163,6 @@ main(int /* argc ATS_UNUSED */, const char **argv)
     return 0;
   }
 
-  // XXX This is a hack. traffic_manager starts traffic_server with the euid of the admin user. We are still
-  // privileged, but won't be able to open files in /proc or ptrace the target. This really should be fixed
-  // in traffic_manager.
-  if (getuid() == 0) {
-    ATS_UNUSED_RETURN(seteuid(0));
-  }
-
   runroot_handler(argv);
   Layout::create();
   RecProcessInit(RECM_STAND_ALONE, nullptr /* diags */);
diff --git a/proxy/Crash.cc b/proxy/Crash.cc
index 366d5fd..7f15395 100644
--- a/proxy/Crash.cc
+++ b/proxy/Crash.cc
@@ -79,7 +79,7 @@ check_logger_path(const char *path)
 }
 
 void
-crash_logger_init()
+crash_logger_init(const char *user)
 {
   ats_scoped_str logger(create_logger_path());
   const char *basename;
@@ -119,7 +119,8 @@ crash_logger_init()
       }
     }
 
-    ink_release_assert(execl(logger, basename, "--syslog", "--wait", "--host", TS_BUILD_CANONICAL_HOST, NULL) != -1);
+    ink_release_assert(execl(logger, basename, "--syslog", "--wait", "--host", TS_BUILD_CANONICAL_HOST, "--user", user, NULL) !=
+                       -1);
     return; // not reached.
   }
 
diff --git a/proxy/Main.cc b/proxy/Main.cc
index ee56f19..0e88da1 100644
--- a/proxy/Main.cc
+++ b/proxy/Main.cc
@@ -1655,20 +1655,20 @@ main(int /* argc ATS_UNUSED */, const char **argv)
     REC_ReadConfigInteger(num_task_threads, "proxy.config.task_threads");
   }
 
+  ats_scoped_str user(MAX_LOGIN + 1);
+
+  *user        = '\0';
+  admin_user_p = ((REC_ERR_OKAY == REC_ReadConfigString(user, "proxy.config.admin.user_id", MAX_LOGIN)) && (*user != '\0') &&
+                  (0 != strcmp(user, "#-1")));
+
   // Set up crash logging. We need to do this while we are still privileged so that the crash
   // logging helper runs as root. Don't bother setting up a crash logger if we are going into
   // command mode since that's not going to daemonize or run for a long time unattended.
   if (!command_flag) {
-    crash_logger_init();
+    crash_logger_init(user);
     signal_register_crash_handler(crash_logger_invoke);
   }
 
-  ats_scoped_str user(MAX_LOGIN + 1);
-
-  *user        = '\0';
-  admin_user_p = ((REC_ERR_OKAY == REC_ReadConfigString(user, "proxy.config.admin.user_id", MAX_LOGIN)) && (*user != '\0') &&
-                  (0 != strcmp(user, "#-1")));
-
 #if TS_USE_POSIX_CAP
   // Change the user of the process.
   // Do this before we start threads so we control the user id of the
diff --git a/proxy/Main.h b/proxy/Main.h
index 4df2e06..14e36e3 100644
--- a/proxy/Main.h
+++ b/proxy/Main.h
@@ -76,5 +76,5 @@ maintainance_mode()
 
 extern AppVersionInfo appVersionInfo;
 
-void crash_logger_init();
+void crash_logger_init(const char *user);
 void crash_logger_invoke(int signo, siginfo_t *info, void *ctx);

-- 
To stop receiving notification emails like this one, please contact
duke8253@apache.org.