make the various strings in the config fixed-length

will help in future restructuring to have fixed-size objects.
This commit is contained in:
Omar Polo 2022-10-05 15:10:44 +00:00
parent 4ceb570910
commit 534afd0ddc
8 changed files with 158 additions and 158 deletions

21
ge.c
View File

@ -53,9 +53,9 @@ load_local_cert(struct vhost *h, const char *hostname, const char *dir)
if (access(cert, R_OK) == -1 || access(key, R_OK) == -1)
gen_certificate(hostname, cert, key);
h->cert = cert;
h->key = key;
h->domain = hostname;
strlcpy(h->cert, cert, sizeof(h->cert));
strlcpy(h->key, key, sizeof(h->key));
strlcpy(h->domain, hostname, sizeof(h->domain));
}
/* wrapper around dirname(3). dn must be PATH_MAX+1 at least. */
@ -256,16 +256,21 @@ main(int argc, char **argv)
load_local_cert(host, hostname, certs_dir);
host->domain = "*";
strlcpy(host->domain, "*", sizeof(host->domain));
loc->auto_index = 1;
loc->match = "*";
strlcpy(loc->match, "*", sizeof(loc->match));
if (*argv == NULL) {
if (getcwd(path, sizeof(path)) == NULL)
fatal("getcwd");
loc->dir = path;
} else
loc->dir = absolutify_path(*argv);
strlcpy(loc->dir, path, sizeof(loc->dir));
} else {
char *tmp;
tmp = absolutify_path(*argv);
strlcpy(loc->dir, tmp, sizeof(loc->dir));
free(tmp);
}
if ((loc->dirfd = open(loc->dir, O_RDONLY|O_DIRECTORY)) == -1)
fatal("can't open %s", loc->dir);

40
gmid.c
View File

@ -65,7 +65,7 @@ load_vhosts(void)
TAILQ_FOREACH(h, &hosts, vhosts) {
TAILQ_FOREACH(l, &h->locations, locations) {
if (l->dir == NULL)
if (*l->dir == '\0')
continue;
if ((l->dirfd = open(l->dir, O_RDONLY | O_DIRECTORY)) == -1)
fatal("open %s for domain %s: %s", l->dir, h->domain,
@ -132,7 +132,7 @@ make_socket(int port, int family)
static void
add_keypair(struct vhost *h)
{
if (h->ocsp == NULL) {
if (*h->ocsp == '\0') {
if (tls_config_add_keypair_file(tlsconf, h->cert, h->key) == -1)
fatal("failed to load the keypair (%s, %s)",
h->cert, h->key);
@ -170,7 +170,7 @@ setup_tls(void)
h->cert, h->key);
/* same for OCSP */
if (h->ocsp != NULL &&
if (*h->ocsp != '\0' &&
tls_config_set_ocsp_staple_file(tlsconf, h->ocsp) == -1)
fatal("tls_config_set_ocsp_staple_file failed for (%s)",
h->ocsp);
@ -216,7 +216,7 @@ free_config(void)
struct proxy *p, *tp;
struct envlist *e, *te;
struct alist *a, *ta;
int v, i;
int v;
v = conf.verbose;
@ -229,13 +229,6 @@ free_config(void)
TAILQ_FOREACH_SAFE(l, &h->locations, locations, tl) {
TAILQ_REMOVE(&h->locations, l, locations);
free((char*)l->match);
free((char*)l->lang);
free((char*)l->default_mime);
free((char*)l->index);
free((char*)l->block_fmt);
free((char*)l->dir);
if (l->dirfd != -1)
close(l->dirfd);
@ -244,49 +237,26 @@ free_config(void)
TAILQ_FOREACH_SAFE(e, &h->params, envs, te) {
TAILQ_REMOVE(&h->params, e, envs);
free(e->name);
free(e->value);
free(e);
}
TAILQ_FOREACH_SAFE(a, &h->aliases, aliases, ta) {
TAILQ_REMOVE(&h->aliases, a, aliases);
free(a->alias);
free(a);
}
TAILQ_FOREACH_SAFE(p, &h->proxies, proxies, tp) {
TAILQ_REMOVE(&h->proxies, p, proxies);
free(p->match_proto);
free(p->match_host);
free(p->host);
free(p->sni);
tls_unload_file(p->cert, p->certlen);
tls_unload_file(p->key, p->keylen);
free(p);
}
free((char*)h->domain);
free((char*)h->cert);
free((char*)h->key);
free((char*)h->ocsp);
TAILQ_REMOVE(&hosts, h, vhosts);
free(h);
}
for (i = 0; i < FCGI_MAX; ++i) {
if (fcgi[i].path == NULL)
break;
free(fcgi[i].path);
free(fcgi[i].port);
fcgi[i].path = NULL;
fcgi[i].port = NULL;
}
memset(fcgi, 0, sizeof(fcgi));
tls_free(ctx);
tls_config_free(tlsconf);

45
gmid.h
View File

@ -77,6 +77,9 @@
#define MEDIATYPE_NAMEMAX 128 /* file name extension */
#define MEDIATYPE_TYPEMAX 128 /* length of type/subtype */
#define FCGI_NAME_MAX 511
#define FCGI_VAL_MAX 511
#define FCGI_MAX 32
#define PROC_MAX 16
@ -98,20 +101,20 @@ struct parser {
struct fcgi {
int id;
char *path;
char *port;
char path[PATH_MAX];
char port[32];
};
extern struct fcgi fcgi[FCGI_MAX];
TAILQ_HEAD(proxyhead, proxy);
struct proxy {
char *match_proto;
char *match_host;
const char *match_port;
char match_proto[32];
char match_host[HOST_NAME_MAX + 1];
char match_port[32];
char *host;
const char *port;
char *sni;
char host[HOST_NAME_MAX + 1];
char port[32];
char sni[HOST_NAME_MAX];
int notls;
uint32_t protocols;
int noverifyname;
@ -126,19 +129,19 @@ struct proxy {
TAILQ_HEAD(lochead, location);
struct location {
const char *match;
const char *lang;
const char *default_mime;
const char *index;
char match[128];
char lang[32];
char default_mime[MEDIATYPE_TYPEMAX];
char index[PATH_MAX];
int auto_index; /* 0 auto, -1 off, 1 on */
int block_code;
const char *block_fmt;
char block_fmt[GEMINI_URL_LEN];
int strip;
X509_STORE *reqca;
int disable_log;
int fcgi;
const char *dir;
char dir[PATH_MAX];
int dirfd;
TAILQ_ENTRY(location) locations;
@ -146,23 +149,23 @@ struct location {
TAILQ_HEAD(envhead, envlist);
struct envlist {
char *name;
char *value;
char name[FCGI_NAME_MAX];
char value[FCGI_VAL_MAX];
TAILQ_ENTRY(envlist) envs;
};
TAILQ_HEAD(aliashead, alist);
struct alist {
char *alias;
char alias[HOST_NAME_MAX + 1];
TAILQ_ENTRY(alist) aliases;
};
extern TAILQ_HEAD(vhosthead, vhost) hosts;
struct vhost {
const char *domain;
const char *cert;
const char *key;
const char *ocsp;
char domain[HOST_NAME_MAX + 1];
char cert[PATH_MAX];
char key[PATH_MAX];
char ocsp[PATH_MAX];
TAILQ_ENTRY(vhost) vhosts;

179
parse.y
View File

@ -27,6 +27,7 @@
#include <ctype.h>
#include <errno.h>
#include <netdb.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
@ -91,10 +92,9 @@ int check_prefork_num(int);
void advance_loc(void);
void advance_proxy(void);
void parsehp(char *, char **, const char **, const char *);
void only_once(const void*, const char*);
void only_oncei(int, const char*);
int fastcgi_conf(char *, char *, char *);
int fastcgi_conf(const char *, const char *, char *);
void add_param(char *, char *);
int getservice(const char *);
static struct vhost *host;
static struct location *loc;
@ -136,7 +136,7 @@ typedef struct {
%token <v.string> STRING
%token <v.number> NUM
%type <v.number> bool
%type <v.number> bool proxy_port
%type <v.string> string numberstring
%%
@ -242,15 +242,17 @@ vhost : SERVER string {
TAILQ_INIT(&host->proxies);
loc->match = xstrdup("*");
host->domain = $2;
(void) strlcpy(loc->match, "*", sizeof(loc->match));
(void) strlcpy(host->domain, $2, sizeof(host->domain));
if (strstr($2, "xn--") != NULL) {
yywarn("\"%s\" looks like punycode: you "
"should use the decoded hostname", $2);
}
free($2);
} '{' optnl servbody '}' {
if (host->cert == NULL || host->key == NULL)
if (*host->cert == '\0' || *host->key == '\0')
yyerror("invalid vhost definition: %s", $2);
}
| error '}' { yyerror("bad server directive"); }
@ -266,20 +268,24 @@ servopt : ALIAS string {
struct alist *a;
a = xcalloc(1, sizeof(*a));
a->alias = $2;
(void) strlcpy(a->alias, $2, sizeof(a->alias));
free($2);
TAILQ_INSERT_TAIL(&host->aliases, a, aliases);
}
| CERT string {
only_once(host->cert, "cert");
host->cert = ensure_absolute_path($2);
ensure_absolute_path($2);
(void) strlcpy(host->cert, $2, sizeof(host->cert));
free($2);
}
| KEY string {
only_once(host->key, "key");
host->key = ensure_absolute_path($2);
ensure_absolute_path($2);
(void) strlcpy(host->key, $2, sizeof(host->key));
free($2);
}
| OCSP string {
only_once(host->ocsp, "ocsp");
host->ocsp = ensure_absolute_path($2);
ensure_absolute_path($2);
(void) strlcpy(host->ocsp, $2, sizeof(host->ocsp));
free($2);
}
| PARAM string '=' string {
add_param($2, $4);
@ -289,7 +295,7 @@ servopt : ALIAS string {
proxy : PROXY { advance_proxy(); }
proxy_matches '{' optnl proxy_opts '}' {
if (proxy->host == NULL)
if (*proxy->host == '\0')
yyerror("invalid proxy block: missing `relay-to' option");
if ((proxy->cert == NULL && proxy->key != NULL) ||
@ -302,15 +308,24 @@ proxy_matches : /* empty */
| proxy_matches proxy_match
;
proxy_match : PROTO string {
only_once(proxy->match_proto, "proxy proto");
free(proxy->match_proto);
proxy->match_proto = $2;
proxy_port : /* empty */ { $$ = 1965; }
| PORT STRING {
if (($$ = getservice($2)) == -1)
yyerror("invalid port number %s", $2);
free($2);
}
| FOR_HOST string {
only_once(proxy->match_host, "proxy for-host");
free(proxy->match_host);
parsehp($2, &proxy->match_host, &proxy->match_port, "10965");
| PORT NUM { $$ = $2; }
;
proxy_match : PROTO string {
(void) strlcpy(proxy->match_proto, $2, sizeof(proxy->match_proto));
free($2);
}
| FOR_HOST string proxy_port {
(void) strlcpy(proxy->match_host, $2, sizeof(proxy->match_host));
(void) snprintf(proxy->match_port, sizeof(proxy->match_port),
"%d", $3);
free($2);
}
;
@ -319,7 +334,6 @@ proxy_opts : /* empty */
;
proxy_opt : CERT string {
only_once(proxy->cert, "proxy cert");
tls_unload_file(proxy->cert, proxy->certlen);
ensure_absolute_path($2);
proxy->cert = tls_load_file($2, &proxy->certlen, NULL);
@ -328,7 +342,6 @@ proxy_opt : CERT string {
free($2);
}
| KEY string {
only_once(proxy->key, "proxy key");
tls_unload_file(proxy->key, proxy->keylen);
ensure_absolute_path($2);
proxy->key = tls_load_file($2, &proxy->keylen, NULL);
@ -341,22 +354,21 @@ proxy_opt : CERT string {
yyerror("invalid protocols string \"%s\"", $2);
free($2);
}
| RELAY_TO string {
only_once(proxy->host, "proxy relay-to");
free(proxy->host);
parsehp($2, &proxy->host, &proxy->port, "1965");
| RELAY_TO string proxy_port {
(void) strlcpy(proxy->host, $2, sizeof(proxy->host));
(void) snprintf(proxy->port, sizeof(proxy->port),
"%d", $3);
free($2);
}
| REQUIRE CLIENT CA string {
only_once(proxy->reqca, "require client ca");
ensure_absolute_path($4);
if ((proxy->reqca = load_ca($4)) == NULL)
yyerror("couldn't load ca cert: %s", $4);
free($4);
}
| SNI string {
only_once(proxy->sni, "proxy sni");
free(proxy->sni);
proxy->sni = $2;
(void) strlcpy(proxy->sni, $2, sizeof(proxy->sni));
free($2);
}
| USE_TLS bool {
proxy->notls = !$2;
@ -370,7 +382,8 @@ location : LOCATION { advance_loc(); } string '{' optnl locopts '}' {
/* drop the starting '/' if any */
if (*$3 == '/')
memmove($3, $3+1, strlen($3));
loc->match = $3;
(void) strlcpy(loc->match, $3, sizeof(loc->match));
free($3);
}
| error '}'
;
@ -381,72 +394,75 @@ locopts : /* empty */
locopt : AUTO INDEX bool { loc->auto_index = $3 ? 1 : -1; }
| BLOCK RETURN NUM string {
only_once(loc->block_fmt, "block");
loc->block_fmt = check_block_fmt($4);
check_block_fmt($4);
(void) strlcpy(loc->block_fmt, $4, sizeof(loc->block_fmt));
loc->block_code = check_block_code($3);
free($4);
}
| BLOCK RETURN NUM {
only_once(loc->block_fmt, "block");
loc->block_fmt = xstrdup("temporary failure");
(void) strlcpy(loc->block_fmt, "temporary failure",
sizeof(loc->block_fmt));
loc->block_code = check_block_code($3);
if ($3 >= 30 && $3 < 40)
yyerror("missing `meta' for block return %d", $3);
}
| BLOCK {
only_once(loc->block_fmt, "block");
loc->block_fmt = xstrdup("temporary failure");
(void) strlcpy(loc->block_fmt, "temporary failure",
sizeof(loc->block_fmt));
loc->block_code = 40;
}
| DEFAULT TYPE string {
only_once(loc->default_mime, "default type");
loc->default_mime = $3;
(void) strlcpy(loc->default_mime, $3,
sizeof(loc->default_mime));
free($3);
}
| FASTCGI fastcgi
| INDEX string {
only_once(loc->index, "index");
loc->index = $2;
(void) strlcpy(loc->index, $2, sizeof(loc->index));
free($2);
}
| LANG string {
only_once(loc->lang, "lang");
loc->lang = $2;
(void) strlcpy(loc->lang, $2,
sizeof(loc->lang));
free($2);
}
| LOG bool { loc->disable_log = !$2; }
| REQUIRE CLIENT CA string {
only_once(loc->reqca, "require client ca");
ensure_absolute_path($4);
if ((loc->reqca = load_ca($4)) == NULL)
yyerror("couldn't load ca cert: %s", $4);
free($4);
}
| ROOT string {
only_once(loc->dir, "root");
loc->dir = ensure_absolute_path($2);
(void) strlcpy(loc->dir, $2, sizeof(loc->dir));
free($2);
}
| STRIP NUM { loc->strip = check_strip_no($2); }
;
fastcgi : SPAWN string {
only_oncei(loc->fcgi, "fastcgi");
loc->fcgi = fastcgi_conf(NULL, NULL, $2);
free($2);
}
| string {
only_oncei(loc->fcgi, "fastcgi");
loc->fcgi = fastcgi_conf($1, NULL, NULL);
free($1);
}
| TCP string PORT NUM {
char *c;
if (asprintf(&c, "%d", $4) == -1)
err(1, "asprintf");
only_oncei(loc->fcgi, "fastcgi");
loc->fcgi = fastcgi_conf($2, c, NULL);
free($2);
}
| TCP string {
only_oncei(loc->fcgi, "fastcgi");
loc->fcgi = fastcgi_conf($2, xstrdup("9000"), NULL);
loc->fcgi = fastcgi_conf($2, "9000", NULL);
free($2);
}
| TCP string PORT string {
only_oncei(loc->fcgi, "fastcgi");
loc->fcgi = fastcgi_conf($2, $4, NULL);
free($2);
free($4);
}
;
@ -1153,22 +1169,8 @@ parsehp(char *str, char **host, const char **port, const char *def)
yyerror("port is %s: %s", errstr, *port);
}
void
only_once(const void *ptr, const char *name)
{
if (ptr != NULL)
yyerror("`%s' specified more than once", name);
}
void
only_oncei(int i, const char *name)
{
if (i != -1)
yyerror("`%s' specified more than once", name);
}
int
fastcgi_conf(char *path, char *port, char *prog)
fastcgi_conf(const char *path, const char *port, char *prog)
{
struct fcgi *f;
int i;
@ -1178,20 +1180,17 @@ fastcgi_conf(char *path, char *port, char *prog)
for (i = 0; i < FCGI_MAX; ++i) {
f = &fcgi[i];
if (f->path == NULL) {
if (*f->path == '\0') {
f->id = i;
f->path = path;
f->port = port;
(void) strlcpy(f->path, path, sizeof(f->path));
(void) strlcpy(f->port, port, sizeof(f->port));
return i;
}
if (!strcmp(f->path, path) &&
((port == NULL && f->port == NULL) ||
!strcmp(f->port, port))) {
free(path);
free(port);
((port == NULL && *f->port == '\0') ||
!strcmp(f->port, port)))
return i;
}
}
yyerror("too much `fastcgi' rules defined.");
@ -1205,7 +1204,27 @@ add_param(char *name, char *val)
struct envhead *h = &host->params;
e = xcalloc(1, sizeof(*e));
e->name = name;
e->value = val;
(void) strlcpy(e->name, name, sizeof(e->name));
(void) strlcpy(e->value, val, sizeof(e->value));
TAILQ_INSERT_TAIL(h, e, envs);
}
int
getservice(const char *n)
{
struct servent *s;
const char *errstr;
long long llval;
llval = strtonum(n, 0, UINT16_MAX, &errstr);
if (errstr) {
s = getservbyname(n, "tcp");
if (s == NULL)
s = getservbyname(n, "udp");
if (s == NULL)
return (-1);
return (ntohs(s->s_port));
}
return ((unsigned short)llval);
}

View File

@ -326,7 +326,7 @@ proxy_setup_tls(struct client *c)
if (tls_configure(c->proxyctx, conf) == -1)
goto err;
if ((hn = p->sni) == NULL)
if (*(hn = p->sni) == '\0')
hn = p->host;
if (tls_connect_socket(c->proxyctx, c->pfd, hn) == -1)
goto err;

View File

@ -80,7 +80,7 @@ server "localhost.local" {
cert "$PWD/cert.pem"
key "$PWD/key.pem"
proxy {
relay-to "localhost:$port"
relay-to localhost port $port
$1
}
}

View File

@ -514,7 +514,7 @@ server_landlock(void)
TAILQ_FOREACH(h, &hosts, vhosts) {
TAILQ_FOREACH(l, &h->locations, locations) {
if (l->dir == NULL)
if (*l->dir == '\0')
continue;
if (landlock_unveil_path(fd, l->dir, perms) == -1)
@ -608,7 +608,7 @@ sandbox_server_process(int can_open_sockets)
TAILQ_FOREACH(h, &hosts, vhosts) {
TAILQ_FOREACH(l, &h->locations, locations) {
if (l->dir == NULL)
if (*l->dir == '\0')
continue;
if (unveil(l->dir, "r") == -1)

View File

@ -90,13 +90,16 @@ vhost_lang(struct vhost *v, const char *path)
loc = TAILQ_FIRST(&v->locations);
while ((loc = TAILQ_NEXT(loc, locations)) != NULL) {
if (loc->lang != NULL) {
if (*loc->lang != '\0') {
if (matches(loc->match, path))
return loc->lang;
}
}
return TAILQ_FIRST(&v->locations)->lang;
loc = TAILQ_FIRST(&v->locations);
if (*loc->lang == '\0')
return NULL;
return loc->lang;
}
const char *
@ -110,14 +113,14 @@ vhost_default_mime(struct vhost *v, const char *path)
loc = TAILQ_FIRST(&v->locations);
while ((loc = TAILQ_NEXT(loc, locations)) != NULL) {
if (loc->default_mime != NULL) {
if (*loc->default_mime != '\0') {
if (matches(loc->match, path))
return loc->default_mime;
}
}
loc = TAILQ_FIRST(&v->locations);
if (loc->default_mime != NULL)
if (*loc->default_mime != '\0')
return loc->default_mime;
return default_mime;
}
@ -133,14 +136,14 @@ vhost_index(struct vhost *v, const char *path)
loc = TAILQ_FIRST(&v->locations);
while ((loc = TAILQ_NEXT(loc, locations)) != NULL) {
if (loc->index != NULL) {
if (*loc->index != '\0') {
if (matches(loc->match, path))
return loc->index;
}
}
loc = TAILQ_FIRST(&v->locations);
if (loc->index != NULL)
if (*loc->index != '\0')
return loc->index;
return index;
}
@ -536,11 +539,11 @@ matched_proxy(struct client *c)
const char *port;
TAILQ_FOREACH(p, &c->host->proxies, proxies) {
if ((proto = p->match_proto) == NULL)
if (*(proto = p->match_proto) == '\0')
proto = "gemini";
if ((host = p->match_host) == NULL)
if (*(host = p->match_host) == '\0')
host = "*";
if ((port = p->match_port) == NULL)
if (*(port = p->match_port) == '\0')
port = "*";
if (matches(proto, c->iri.schema) &&
@ -719,7 +722,7 @@ apply_fastcgi(struct client *c)
log_debug(c, "opening fastcgi connection for (%s,%s)",
f->path, f->port);
if (f->port != NULL)
if (*f->port != '\0')
c->pfd = fcgi_open_sock(f);
else
c->pfd = fcgi_open_conn(f);