unicorn Ruby/Rack server user+dev discussion/patches/pulls/bugs/help
 help / color / mirror / code / Atom feed
From: Jeremy Evans <code@jeremyevans.net>
To: unicorn-public@bogomips.org
Subject: Patch: Add support for chroot to Worker#user
Date: Tue, 21 Feb 2017 11:24:21 -0800	[thread overview]
Message-ID: <20170221192421.GI93742@jeremyevans.local> (raw)

Any chrooting would need to happen inside Worker#user, because
you can't chroot until after you have parsed the list of groups,
and you must chroot before dropping root privileges.

chroot is an important security feature, so that if the unicorn
process is exploited, file system access is limited to the chroot
directory instead of the entire system.

This is not a complete patch as it does not include tests. I can
add tests if you would consider accepting this feature.
---
 lib/unicorn/worker.rb | 11 ++++++++---
 1 file changed, 8 insertions(+), 3 deletions(-)

diff --git a/lib/unicorn/worker.rb b/lib/unicorn/worker.rb
index 6748a2f..db418ea 100644
--- a/lib/unicorn/worker.rb
+++ b/lib/unicorn/worker.rb
@@ -111,9 +111,10 @@ def close # :nodoc:
   # In most cases, you should be using the Unicorn::Configurator#user
   # directive instead.  This method should only be used if you need
   # fine-grained control of exactly when you want to change permissions
-  # in your after_fork hooks.
+  # in your after_fork hooks, or if you want to use the chroot support.
   #
-  # Changes the worker process to the specified +user+ and +group+
+  # Changes the worker process to the specified +user+ and +group+,
+  # and chroots to the current working directory if +chroot+ is set.
   # This is only intended to be called from within the worker
   # process from the +after_fork+ hook.  This should be called in
   # the +after_fork+ hook after any privileged functions need to be
@@ -123,7 +124,7 @@ def close # :nodoc:
   # directly back to the caller (usually the +after_fork+ hook.
   # These errors commonly include ArgumentError for specifying an
   # invalid user/group and Errno::EPERM for insufficient privileges
-  def user(user, group = nil)
+  def user(user, group = nil, chroot = false)
     # we do not protect the caller, checking Process.euid == 0 is
     # insufficient because modern systems have fine-grained
     # capabilities.  Let the caller handle any and all errors.
@@ -134,6 +135,10 @@ def user(user, group = nil)
       Process.initgroups(user, gid)
       Process::GID.change_privilege(gid)
     end
+    if chroot
+      Dir.chroot(Dir.pwd)
+      Dir.chdir('/')
+    end
     Process.euid != uid and Process::UID.change_privilege(uid)
     @switched = true
   end
-- 
2.11.0


             reply	other threads:[~2017-02-21 19:24 UTC|newest]

Thread overview: 3+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-02-21 19:24 Jeremy Evans [this message]
2017-02-21 19:53 ` Patch: Add support for chroot to Worker#user Eric Wong
2017-02-21 20:15   ` Jeremy Evans

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://yhbt.net/unicorn/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20170221192421.GI93742@jeremyevans.local \
    --to=code@jeremyevans.net \
    --cc=unicorn-public@bogomips.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://yhbt.net/unicorn.git/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).