diff --git a/libhttp/ssl.c b/libhttp/ssl.c index c8de457..ceb2eb8 100755 --- a/libhttp/ssl.c +++ b/libhttp/ssl.c @@ -58,6 +58,7 @@ #include #include #include +#include #include #include "libhttp/ssl.h" @@ -347,18 +348,32 @@ static void sslGenerateCertificate(const char *certificate, const char *serverName) { debug("Auto-generating missing certificate \"%s\" for \"%s\"", certificate, serverName); - char *cmd = stringPrintf(NULL, - "set -e; " - "exec 2>/dev/null '%s'", - serverName, certificate); - if (system(cmd)) { + + pid_t pid = fork(); + if (pid == -1) { warn("Failed to generate self-signed certificate \"%s\"", certificate); + } else if (pid == 0) { + int fd = NOINTR(open("/dev/null", O_RDONLY)); + check(fd != -1); + check(NOINTR(dup2(fd, STDERR_FILENO)) == STDERR_FILENO); + check(NOINTR(close(fd)) == 0); + fd = NOINTR(open("/dev/null", O_WRONLY)); + check(fd != -1); + check(NOINTR(dup2(fd, STDIN_FILENO)) == STDIN_FILENO); + check(NOINTR(close(fd)) == 0); + umask(077); + check(setenv("PATH", "/usr/bin:/usr/sbin", 1) == 0); + execlp("openssl", "openssl", "req", "-x509", "-nodes", "-days", "7300", + "-newkey", "rsa:1024", "-keyout", certificate, "-out", certificate, + "-subj", stringPrintf(NULL, "/CN=%s/", serverName), + (char *)NULL); + check(0); + } else { + int status; + check(NOINTR(waitpid(pid, &status, 0)) == pid); + if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) + warn("Failed to generate self-signed certificate \"%s\"", certificate); } - free(cmd); } static const unsigned char *sslSecureReadASCIIFileToMem(int fd) {