http-faccess is an HTTP server that reports whether the server's process owner can read files relative to a base directory
Find a file
2020-04-22 17:42:27 +02:00
.gitignore Add gitignore. 2020-04-22 16:28:16 +02:00
COPYING Initial commit 2020-04-15 15:33:33 +02:00
doc.go Doc polish (less run-on in the first sentence). 2020-04-22 17:42:27 +02:00
Dockerfile Add Dockerfile. 2020-04-22 17:06:50 +02:00
go.mod Initial commit 2020-04-15 15:33:33 +02:00
go.sum Initial commit 2020-04-15 15:33:33 +02:00
LICENSE Initial commit 2020-04-15 15:33:33 +02:00
main.go Initial commit 2020-04-15 15:33:33 +02:00
Makefile Initial commit 2020-04-15 15:33:33 +02:00
README.md Doc polish (less run-on in the first sentence). 2020-04-22 17:42:27 +02:00

http-faccess

GoDoc

http-faccess -- HTTP server that reports whether the server's process owner can read files relative to a base directory.

SYNOPSIS

.

	http-faccess [-address addr] [-base dir] [-access log] [-error log]
                 [-gid gid] [-mode mode]

	http-faccess -version

	http-faccess -help

DESCRIPTION

http-faccess is an HTTP server that reports, through response status codes, whether the file or directory represented by the URL path is readable by the server's process owner. The URL path is interpreted as a path on the server's host relative to a given base directory. http-faccess is meant to be used as a tool within trusted networks, and should not be exposed to the public internet (see SECURITY).

base is a directory on the host on which http-faccess runs (by default, the current working directory when http-faccess was invoked). The process owner is the effective user running http-faccess. base MUST be a directory, and it MUST be readable by the process owner when http-faccess is invoked.

The URL path of a request, without the leading '/', is interpeted as a path relative to the base directory. The only permitted request methods are GET and HEAD. Response bodies are always empty; the information in the response is defined solely by its status code. Responses from http-faccess are not cacheable.

The response status codes are:

204 No Content:            the file or directory represented
                           by the URL path is readable

301 Moved Permanently:     redirect to a path without repeated
                           slashes (see below)

403 Forbidden:             the file or directory exists, but is
                           not readable

404 Not Found:             the file or directory does not exist

405 Method Not Allowed:    the request method was neither of GET
                           or HEAD

500 Internal Server Error: an error was encountered while
                           attempting to determine readability

If the URL path ends with '/', then it denotes a directory, otherwise a file. If the URL in a request denotes a file (there is no trailing '/'), but there is a directory at the corresponding path on the host, then the response is 404 Not Found. Similarly, the response is 404 if the request denotes a directory but there is a file at the corresponding path.

Requests for the root document -- in which the path consists only of '/', or when the request URI has no trailing slash, such as http://example.com -- always result in status 204. The rationale is that these requests designate the base directory, which had to be readable when http-faccess started.

If there is a symbolic link at the path corresponding to the URL path, the link is followed to its target, possibly over a chain of links, and results are reported for the target. Dangling links result in a 500 error response.

If the URL path contains sequences of slashes, such as '//foo/bar//baz', http-faccess returns a 301 redirect response, in which the Location contains the path without the duplicate slashes.

If any component of the URL path is a single dot ('/./'), then it is transparently removed from the path. '/../' has the usual meaning of designating the parent directory, except that it goes no higher than the document root, so it is not possible to explore the filesystem outside of the base directory. Paths containing '/./' or '/../' are modified transparently before the path is evaluated for readability; there is no redirect response in such cases, unless there are also repeated slashes.

For example:

URL path:             is evaluated as:
/./foo                /foo
/foo/./bar            /foo/bar
/..                   /
/../foo               /foo
/../dir/              /dir/
/dir/../foo           /foo
/dir1/dir2/../foo     /dir1/foo

EXAMPLES

Suppose that http-faccess is invoked as user smith with:

$ http-faccess -address :7357 -base /foo/

The server then listens at port 7357, and reports the readability of files and directories in /foo/ for user smith.

Suppose further that /foo/ has these contents, where jones is another user, and smith belongs to the group smithgrp, but not to the group jonesgrp:

$ ls -l /foo/
-rw-r--r-- smith smithgrp  bar.txt
-rw-r----- jones jonesgrp  baz.html
-rw-r----- jones smithgrp  quux.jpg
drwxr-xr-x smith smithgrp  subdir

Then http-faccess returns the following status codes for requests with these URL paths:

URL path: /
Status:   204
The root path is always readable.

URL path: /bar.txt
Status:   204
/foo/bar.txt is readable for smith.

URL path: /baz.html
Status:   403
/foo/baz.html exists, but is not readable for smith.

URL path: /quux.jpg
Status:   204
/foo/quux.jpg is readable for smith.

URL path: /subdir
Status:   404
/foo/subdir/ is a directory, but the URL path designates a file.

URL path: /subdir/
Status:   204
Directory /foo/subdir/ is readable for smith.

URL path: /../
Status:   204
Evaluated as the root path.

URL path: /subdir/../bar.txt
Status:   204
Interpreted as /bar.txt

URL path: /././quux.jpg
Status:   204
Interpreted as /quux.jpg

URL path: //bar/baz//quux
Status:   301
Location: /bar/baz/quux
Redirect to the path without repeated slashes.

OPTIONS

http-faccess may be invoked with these command-line flags:

-base dir

Evaluate URL paths in requests as paths relative to the directory dir. dir MUST be a directory, and it MUST be readable by the process owner at invocation. http-faccess always evaluates paths relative to dir as it was at invocation time, even if its name or permissions change after the server was started. By default, dir is the current working directory at invocation.

-address addr

Listen for requests at addr. addr can have one of the forms:

[ip-address]:port
unix@/path/to/unix.sock

The first form specifies an IP address. If only :port is specified, http-faccess listens at that port on all IP network interfaces. The second form specifies a Unix domain socket at the path after "unix@". The socket file is created when the server starts; if any file already exists at that path, then http-faccess fails to start. By default, http-faccess listens at port :7357.

-gid groupid

Set the numeric group id of the socket file created when the server starts, if a Unix domain socket was specified by the -address option. Ignored if the server is listening at an IP address. If groupid is -1, then the gid of the socket file is not changed -- this is the default.

-mode mode

Set the permissions of the socket file created when the server starts, if a Unix domain socket was specified by the -address option. Ignored if the server is listening at an IP address. If the value of mode has a leading 0, it is interpreted as an octal number, so that the customary notation for permissions can be used (such as 0660). If mode is -1, the permissions of the socket file are not changed -- this is the default.

-access logfile

Write the server access log (in Common Log Format) to logfile, or to standard output if logfile is "-". To suppress logging, set logfile to /dev/null. By default, http-faccess logs to stdout.

-error logfile

Write error logs, which detail the errors that cause 500 responses, to logfile, or to stdout if logfile is "-". Suppress error logs by setting logfile to /dev/null. By default, http-faccess writes error logs to stderr.

-version

Print the version and exit.

-help

Print a usage message and exit.

LIMITATIONS

http-faccess is platform-specific -- it only runs on Unix systems with a POSIX-compliant implementation of faccessat(2).

There is always a TOCTOU race between the server's reports about the readability of a file or directory and subsequent attempts by the process owner to read that file or directory. The file may be changed or deleted at any time after http-faccess reports a result.

Requests that lead to redirect responses (to paths without repeated slashes) are not logged in the access log.

SECURITY

Depending on the contents of the base directory, http-faccess can expose sensitive information about the host's file system, which could be exploited by an attacker. http-faccess does not reveal the contents of any file, does not allow directory listings, does not report the causes of 500 errors in the response (these are only reported in the server's error log), and does not permit the use of '/../' to navigate outside the base directory. But an attacker may draw inferences by testing hypotheses about paths on the host, by discovering what is readable or not readable and what exists or does not exist, or by determining that errors can be caused.

It is strongly advised:

  • don't expose http-faccess on the public internet.

  • don't run http-faccess as root, as an administrative user, as any user corresponding to a human user, or any highly privileged user.

  • don't set the base directory so that sensitive information on the host can be explored, such as the root directory ('/'), /etc, /usr or anyone's home directory.

For best results, limit the use of http-faccess to private networks, run it as a user with limited privileges, and set the base directory so that a narrowly restricted set of paths are accessible. If http-faccess only needs to be accessed by other components on the same host, consider using a Unix domain socket as the listener, so that it is not exposed on the network at all.

Be aware that http-faccess follows symbolic links, which may make it possible to explore the file system outside of the base directory. Consider eliminating symbolic links altogether from paths that can be reached from the base directory. If links are used, ensure that they are limited in scope, just as you would for the base directory.

INSTALLATION

To pull the Docker image:

docker pull uplex/http-faccess[:tag]

Building the binary requires an installation of the gogitversion tool. Re-building README.md requires goreadme. See the links in SEE ALSO below.

To install the binary:

make install

See the Makefile for additional targets, useful for development.

SEE ALSO

Copyright (c) 2020 UPLEX Nils Goroll Systemoptimierung. All rights reserved

Author: Geoffrey Simmons geoffrey.simmons@uplex.de

See LICENSE

generated with goreadme