forked from aniani/gmnisrv
Support REMOTE_USER in CGI
This commit is contained in:
parent
d7bd3c6a0d
commit
9f2481dcdf
@ -184,6 +184,9 @@ The following environment variables will be set:
|
|||||||
| *TLS_CLIENT_SERIAL_NUMBER*
|
| *TLS_CLIENT_SERIAL_NUMBER*
|
||||||
: 717823108622037499122666796829184010024179612962
|
: 717823108622037499122666796829184010024179612962
|
||||||
: Serial number (decimal) of the client certificate.
|
: Serial number (decimal) of the client certificate.
|
||||||
|
| *REMOTE_USER*
|
||||||
|
: gemini user
|
||||||
|
: Subject common name of the client certificate.
|
||||||
|
|
||||||
\[1]: gemini://example.org/cgi-bin/foo.sh/bar?hello=world
|
\[1]: gemini://example.org/cgi-bin/foo.sh/bar?hello=world
|
||||||
|
|
||||||
|
18
src/serve.c
18
src/serve.c
@ -200,7 +200,7 @@ serve_cgi(struct gmnisrv_client *client, const char *path,
|
|||||||
|
|
||||||
// barebones client cert implementation
|
// barebones client cert implementation
|
||||||
// adapted from openssl(1)'s implementation
|
// adapted from openssl(1)'s implementation
|
||||||
// TODO: support REMOTE_USER, TLS_CLIENT_NOT_{BEFORE,AFTER}
|
// TODO: support TLS_CLIENT_NOT_{BEFORE,AFTER}
|
||||||
X509 *client_cert = SSL_get_peer_certificate(client->ssl);
|
X509 *client_cert = SSL_get_peer_certificate(client->ssl);
|
||||||
if (client_cert != NULL) {
|
if (client_cert != NULL) {
|
||||||
// 32 bytes because we're always using SHA256, but
|
// 32 bytes because we're always using SHA256, but
|
||||||
@ -239,8 +239,24 @@ serve_cgi(struct gmnisrv_client *client, const char *path,
|
|||||||
const char *error = "Invalid certificate serial number";
|
const char *error = "Invalid certificate serial number";
|
||||||
client_submit_response(client,
|
client_submit_response(client,
|
||||||
GEMINI_STATUS_CERTIFICATE_NOT_VALID, error, NULL);
|
GEMINI_STATUS_CERTIFICATE_NOT_VALID, error, NULL);
|
||||||
|
goto post_client_cert_parsing;
|
||||||
|
}
|
||||||
|
|
||||||
|
X509_NAME* subject_name = X509_get_subject_name(client_cert);
|
||||||
|
int cn_index = X509_NAME_get_index_by_NID(subject_name,
|
||||||
|
NID_commonName, -1);
|
||||||
|
if (cn_index != -1) {
|
||||||
|
ASN1_STRING *cn_asn = X509_NAME_ENTRY_get_data(
|
||||||
|
X509_NAME_get_entry(subject_name, cn_index));
|
||||||
|
unsigned char *cn = malloc(ASN1_STRING_length(cn_asn));
|
||||||
|
ASN1_STRING_to_UTF8(&cn, cn_asn);
|
||||||
|
setenv("REMOTE_USER", (char*) cn, 1);
|
||||||
|
OPENSSL_free(cn);
|
||||||
|
} else {
|
||||||
|
setenv("REMOTE_USER", "", 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
post_client_cert_parsing:
|
||||||
|
|
||||||
execlp(path, path, NULL);
|
execlp(path, path, NULL);
|
||||||
server_error("execlp: %s", strerror(errno));
|
server_error("execlp: %s", strerror(errno));
|
||||||
|
Loading…
Reference in New Issue
Block a user