1 .\" Copyright (c) 2021 Omar Polo <op@omarpolo.com>
3 .\" Permission to use, copy, modify, and distribute this software for any
4 .\" purpose with or without fee is hereby granted, provided that the above
5 .\" copyright notice and this permission notice appear in all copies.
7 .\" THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
8 .\" WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
9 .\" MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
10 .\" ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
11 .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
12 .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
13 .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
14 .Dd $Mdocdate: July 29 2021$
19 .Nd simple and secure Gemini server
25 .Op Fl D Ar macro Ns = Ns Ar value
39 is a simple and minimal gemini server that can serve static files,
40 execute CGI scripts and talk to FastCGI applications.
41 It can run without a configuration file with a limited set of features
45 rereads the configuration file when it receives
48 The options are as follows:
51 Specify the configuration file.
52 .It Fl D Ar macro Ns = Ns Ar value
58 Overrides the definition of
60 in the config file if present.
62 Stays and logs on the foreground.
64 Check that the configuration is valid, but don't start the server.
65 If specified two or more time, dump the configuration in addition to
68 Write daemon's pid to the given location.
70 will also act as lock: if another process is holding a lock on that
76 If no configuration file is given,
80 .Pq i.e. runs in the foreground to serve a directory from the shell
81 and looks for the following options
85 .It Fl d Pa certs-path
86 Directory where certificates for the config-less mode are stored.
88 .Pa $XDG_DATA_HOME/gmid ,
90 .Pa ~/.local/share/gmid .
97 Certificates for the given
99 are searched inside the
101 directory given with the
105 .Pa hostname.cert.pem
107 .Pa hostname.key.pem .
108 If a certificate or a key doesn't exist for a given hostname, they
109 will be generated automatically.
111 Print the usage and exit.
113 The port to listen on, by default 1965.
114 .It Fl V , Fl -version
115 Print the version and exit.
120 options increase the verbosity.
125 See the description of the
129 section below to learn how
132 Cannot be provided more than once.
134 The root directory to serve.
135 By default the current working directory is assumed.
137 .Sh CONFIGURATION FILE
138 The configuration file is divided into three sections:
141 User-defined variables may be defined and used later, simplifying the
143 .It Sy Global Options
147 Virtual hosts definition.
150 Within the sections, empty lines are ignored and comments can be put
151 anywhere in the file using a hash mark
153 and extend to the end of the current line.
154 A boolean is either the symbol
158 A string is a sequence of characters wrapped in double quotes,
160 Multiple strings one next to the other are joined into a single
162 .Bd -literal -offset indent
163 # equivalent to "temporary-failure"
164 block return 40 "temporary" "-" "failure"
167 Furthermore, quoting is necessary only when a string needs to contain
169 .Pq like spaces or punctuation ,
170 something that looks like a number or a reserved keyword.
171 The last example could have been written also as:
172 .Bd -literal -offset indent
173 block return 40 temporary "-" failure
176 Strict ordering of the sections is not enforced, so that is possible
177 to mix macros, options and
180 However, defining all the
182 blocks after the macros and the global options is recommended.
184 Newlines are often optional, except around top-level instructions, and
187 can also be optionally used to separate options.
189 Additional configuration files can be included with the
191 keyword, for example:
192 .Bd -literal -offset indent
193 include "/etc/gmid.conf.local"
196 Macros can be defined that will later be expanded in context.
197 Macro names must start with a letter, digit or underscore and may
198 contain any of those characters.
199 Macros names may not be reserved words.
200 Macros are not expanded inside quotes.
202 Two kinds of macros are supported: variable-like and proper macros.
203 When a macro is invoked with a
205 before its name its expanded as a string, whereas when it's invoked
208 its expanded in-place.
211 .Bd -literal -offset indent
213 certdir = "/etc/keys"
214 common = "lang it; auto index on"
217 root $dir "/foo" # -> /var/gemini/foo
218 cert $certdir "/foo.crt" # -> /etc/keys/foo.crt
219 key $certdir "/foo.pem" # -> /etc/keys/foo.pem
225 .It Ic chroot Pa path
227 the process to the given
229 The daemon has to be run with root privileges and thus the option
231 needs to be provided, so privileges can be dropped.
234 will enter the chroot after loading the TLS keys, but before opening
235 the virtual host root directories.
236 It's recommended to keep the TLS keys outside the chroot.
241 Enable or disable IPv6 support, off by default.
242 .It Ic map Ar mime-type Cm to-ext Ar file-extension
247 Both argument are strings.
248 .It Ic port Ar portno
249 The port to listen on.
251 .It Ic prefork Ar number
252 Run the specified number of server processes.
253 This increases the performance and prevents delays when connecting to
255 When not in config-less mode,
257 runs 3 server processes by default.
258 The maximum number allowed is 16.
259 .It Ic protocols Ar string
260 Specify the TLS protocols to enable.
262 .Xr tls_config_parse_protocols 3
263 for the valid protocol string values.
264 By default, both TLSv1.3 and TLSv1.2 are enabled.
267 to enable only TLSv1.3.
268 .It Ic user Ar string
269 Run the daemon as the given user.
272 Every virtual host is defined by a
276 .It Ic server Ar hostname Brq ...
277 Match the server name using shell globbing rules.
278 It can be an explicit name,
279 .Ar www.example.com ,
280 or a name including a wildcards,
284 Followed by a block of options that is enclosed in curly brackets:
287 Specify an additional alias
290 .It Ic auto Ic index Ar bool
291 If no index file is found, automatically generate a directory listing.
293 .It Ic block Op Ic return Ar code Op Ar meta
294 Send a reply and close the connection;
301 .Dq temporary failure .
304 is in the 3x range, then
309 the following special sequences are supported:
310 .Bl -tag -width Ds -compact
312 is replaced with a single
315 is replaced with the request path.
317 is replaced with the query string of the request.
319 is replaced with the server port.
321 is replaced with the server name.
324 Path to the certificate to use for this server.
327 should contain a PEM encoded certificate.
328 This option is mandatory.
334 using shell globbing rules.
335 .It Ic default type Ar string
336 Set the default media type that is used if the media type for a
337 specified extension is not found.
338 If not specified, the
341 .Dq application/octet-stream .
342 .It Ic entrypoint Pa path
343 Handle all the requests for the current virtual host using the
347 relative to the current document root.
348 .It Ic env Ar name Cm = Ar value
349 Set the environment variable
353 when executing CGI scripts.
354 Can be provided more than once.
355 .\" don't document the "spawn <prog>" form because it probably won't
357 .It Ic fastcgi Oo Ic tcp Oc Pa socket Oo Cm port Ar port Oc
360 instead of serving files.
363 can either be a UNIX-domain socket or a TCP socket.
364 If the FastCGI application is listening on a UNIX domain socket,
366 is a local path name within the
372 keyword must be provided and
374 is interpreted as a hostname or an IP address.
376 can be either a port number or the name of a service enclosed in
378 If not specified defaults to 9000.
379 .It Ic index Ar string
380 Set the directory index file.
381 If not specified, it defaults to
384 Specify the private key to use for this server.
387 should contain a PEM encoded private key.
388 This option is mandatory.
389 .It Ic lang Ar string
390 Specify the language tag for the text/gemini content served.
393 parameter will be added in the response.
394 .It Ic location Pa path Brq ...
395 Specify server configuration rules for a specific location.
398 argument will be matched against the request path with shell globbing
400 In case of multiple location statements in the same context, the first
401 matching location will be put into effect and the later ones ignored.
402 Therefore is advisable to match for more specific paths first and for
403 generic ones later on.
406 section may include most of the server configuration rules
408 .Ic alias , Ic cert , Ic cgi , Ic entrypoint , Ic env , Ic key ,
409 .Ic location , Ic param No and Ic proxy .
411 Enable or disable the logging for the current server or location block.
412 .It Ic param Ar name Cm = Ar value
419 Specify an OCSP response to be stapled during TLS handshakes
423 should contain a DER-format OCSP response retrieved from an
427 If the OCSP response in
429 is empty, OCSP stapling will not be used.
430 The default is to not use OCSP stapling.
431 .It Ic proxy Ar option
432 Enable requests proxying.
434 can forward Gemini requests to other hosts on behalf of the client
435 if configured to do so.
436 Multiple options may be specified within curly braces.
440 Specify the client certificate to use when making requests.
442 Specify the client certificate key to use when making requests.
443 .It Ic protocols Ar string
444 Specify the TLS protocols allowed when making remote requests.
446 .Xr tls_config_parse_protocols 3
447 function for the valid protocol string values.
448 By default, both TLSv1.2 and TLSv1.3 are enabled.
449 .It Ic relay-to Ar host : Ns Op Ar port
450 Relay the request to the given
455 .It Ic verifyname Ar bool
456 Enable or disable the TLS server name verification
457 .Pq enabled by default.
459 .It Ic root Pa directory
460 Specify the root directory for this server
461 .Pq alas the current Dq document root .
462 It's relative to the chroot if enabled.
463 .It Ic require Ic client Ic ca Pa path
464 Allow requests only from clients that provide a certificate signed by
465 the CA certificate in
467 It needs to be a PEM-encoded certificate and it's not relative to the
469 .It Ic strip Ar number
472 components from the beginning of the path before doing a lookup in the
474 It's also considered for the
476 parameter in the scope of a
480 When a request for an executable file matches the
482 rule, that file will be executed and its output fed to the client.
484 The CGI scripts are executed in the directory they reside and inherit
487 with these additional variables set:
489 .It Ev GATEWAY_INTERFACE
491 .It Ev GEMINI_DOCUMENT_ROOT
492 The root directory of the virtual host.
493 .It Ev GEMINI_SCRIPT_FILENAME
494 Full path to the CGI script being executed.
496 The full IRI of the request.
497 .It Ev GEMINI_URL_PATH
498 The path of the request.
500 The portion of the requested path that is derived from the the IRI
501 path hierarchy following the part that identifies the script itself.
503 .It Ev PATH_TRANSLATED
504 Present if and only if
507 It represent the translation of the
510 builds this by appending the
512 to the virtual host directory root.
514 The decoded query string.
515 .It Ev REMOTE_ADDR , Ev REMOTE_HOST
516 Textual representation of the client IP.
517 .It Ev REQUEST_METHOD
518 This is present only for RFC3875 (CGI) compliance.
519 It's always set to the empty string.
523 that identifies the current CGI script.
525 The name of the server
527 The port the server is listening on.
528 .It Ev SERVER_PROTOCOL
530 .It Ev SERVER_SOFTWARE
531 The name and version of the server, i.e.
534 The string "Certificate" if the client used a certificate, otherwise
537 The subject of the client certificate if provided, otherwise unset.
538 .It Ev TLS_CLIENT_ISSUER
539 The is the issuer of the client certificate if provided, otherwise
541 .It Ev TLS_CLIENT_HASH
542 The hash of the client certificate if provided, otherwise unset.
546 The TLS version negotiated with the peer.
548 The cipher suite negotiated with the peer.
549 .It Ev TLS_CIPHER_STRENGTH
550 The strength in bits for the symmetric cipher that is being used with
552 .It Ev TLS_CLIENT_NOT_AFTER
553 The time corresponding to the end of the validity period of the peer
554 certificate in the ISO 8601 format
555 .Pq e.g. Dq 2021-02-07T20:17:41Z .
556 .It Ev TLS_CLIENT_NOT_BEFORE
557 The time corresponding to the start of the validity period of the peer
558 certificate in the ISO 8601 format.
562 optionally supports FastCGI.
565 rule must be present in a server or location block.
566 Then, all requests matching that server or location will be handled
567 via the specified FastCGI backend.
569 By default the following variables
571 are sent, and carry the same semantics as with CGI.
572 More parameters can be added with the
610 TLS_CLIENT_NOT_BEFORE
615 To auto-detect the MIME type of the response
617 looks at the file extension and consults its internal table.
618 By default the following mappings are loaded, but they can be
619 overridden or extended using the
621 configuration option.
622 If no MIME is found, the value of
626 will be used, which is
627 .Dq application/octet-stream
630 .Bl -tag -offset indent -width 14m -compact
657 Messages and requests are logged by
661 facility or printed on
664 Requests are logged with the
667 Each request log entry has the following fields, separated by
672 Client IP address and the source port number, separated by a colon
684 Serve the current directory
685 .Bd -literal -offset indent
689 To serve the directory
691 and enable CGI scripts inside
693 .Bd -literal -offset indent
695 $ cat <<EOF > docs/cgi/hello
697 printf "20 text/plain\er\en"
700 $ chmod +x docs/cgi/hello
701 $ gmid -x '/cgi/*' docs
704 An X.509 certificate must be provided to run
706 using a configuration file.
707 First, the RSA certificate is created using a wildcard common name:
708 .Bd -literal -offset indent
709 # openssl genrsa \-out /etc/ssl/private/example.com.key 4096
710 # openssl req \-new \-x509 \e
711 \-key /etc/ssl/private/example.com.key \e
712 \-out /etc/ssl/example.com.crt \e
713 \-days 36500 \-nodes \e
714 \-subj "/CN=example.com"
715 # chmod 600 /etc/ssl/example.com.crt
716 # chmod 600 /etc/ssl/private/example.com.key
719 In the example above, a certificate is valid for one hundred years from
720 the date it was created, which is normal for TOFU.
722 The following is an example of a possible configuration for a site
723 that enables only TLSv1.3, adds a mime type for the file extension
725 and defines two virtual host:
726 .Bd -literal -offset indent
727 ipv6 on # enable ipv6
731 map "application/rtf" to-ext "rtf"
733 server "example.com" {
734 cert "/etc/ssl/example.com.crt"
735 key "/etc/ssl/private/example.com.key"
736 root "/var/gemini/example.com"
739 server "it.example.com" {
740 cert "/etc/ssl/example.com.crt"
741 key "/etc/ssl/private/example.com.key"
742 root "/var/gemini/it.example.com"
744 # enable cgi scripts inside "cgi-bin"
747 # set the language for text/gemini files
752 Yet another example, showing how to enable a
757 .Bd -literal -offset indent
761 server "example.com" {
762 cert "/path/to/cert.pem" # absolute path
763 key "/path/to/key.pem" # also absolute
764 root "/example.com" # relative to the chroot
766 location "/static/*" {
767 # load the following rules only for
768 # requests that matches "/static/*"
778 .Dq Flexible and Economical
779 UTF-8 decoder written by
780 .An Bjoern Hoehrmann .
785 program was written by
786 .An Omar Polo Aq Mt op@omarpolo.com .
790 All the root directories are opened during the daemon startup; if a
791 root directory is deleted and then re-created,
793 won't be able to serve files inside that directory until a restart.
794 This restriction only applies to the root directories and not their
797 a %2F sequence is indistinguishable from a literal slash: this is not
800 a %00 sequence is treated as invalid character and thus rejected.