[cs631apue] question about chroot(2)

Jan Schaumann jschauma at stevens.edu
Tue Nov 19 23:27:07 EST 2013


yluo4 <yluo4 at stevens.edu> wrote:

>   chroot(2) can change the root directory of a process to specified  
> directory and then we can use realpath(3) or use  dirname() and  
> basename() to solve the path problem easily.  But we don't have  
> privilege to use chroot(2) in linux lab.  Does anyone have an easy way  
> to solve the path problem?

You're right, without using chroot(2), which you can't do, this will get
tricky.

Off the top of my head, I think I'd probably try to do this something
along these lines:

read request
if request begins with "/~foo"
	strip /~foo
	get homedir for user "foo"
	append "sws" to homedir for user "foo"
	store that path as prefix
	store remainder of request as shortpath

if request begins with "/cgi-bin"
	strip "/cgi-bin"
	take cgi-dir as specified at startup time
	store that path as prefix
	store remainder of request as shortpath

if request doesn't match either of those two cases:
	take root dir specified at startup time
	store that path as prefix
	store request as shortpath

Then, option (1):

canonicolize shortpath:
	dirs = an array of directories, initially empty
	while not end of shortpath:
		find the next '/',
		chars = chars up until that '/'
		if chars == ".."
			pop last entry off dirs
		else if chars == "."
			continue
		else
			push chars onto dirs
	join dirs with '/' slashes into new canonpath

use prefix+canonpath as the final path



Option(2):

canonicolize prefix+shortpath using realpath(3) as canonpath

if realpath(3) errors, return an error
if realpath(3) succeeds:
	if canonpath is not under prefix, return an error



Both options have their disadvantages:
In (1) you're not handling symlinks, which might exist under the
server's docroot, and which would have to be resolved within that
docroot.

In (2), you're not accounting for the possibility of a URI request that
may exist under the docroot but that canonicolizes to outside of the
prefix.


I'm fine with you choosing either option.  I'm also fine with you coming
up with another option that makes more sense (if so, please share it
here).  Maybe take a look at what other web servers like bozohttpd or
mini_httpd do, too.  Some web servers may take the lazy way out and
simply say that requests containing "../" are not allowed.  This,
however, is not very elegant, nor correct according to the RFC, I
believe.

Also, welcome to software development, where something as seemingly
simple as resolving a path becomes... this.

-Jan


More information about the cs631apue mailing list