Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
894 views
in Technique[技术] by (71.8m points)

bash - How to determine the default location for openssl.cnf?

Background

I'm writing a bash script that will use openssl to generate a certificate signing request with X509v3 extension compliant subject alternative names.

Since there's no command line option for this, a solution has been to use the -config option in conjunction with the -reqexts option by appending the SAN values inline to the default configuration file.

openssl req -new -sha256 -key domain.key -subj "/C=US/ST=CA/O=Acme, Inc./CN=example.com" -reqexts SAN -config <(cat /etc/ssl/openssl.cnf <(printf "[SAN]
subjectAltName=DNS:example.com,DNS:www.example.com")) -out domain.csr

Question

My problem is portability. While a similar question assures me that this works in my Ubuntu environment because the default configuration file is /etc/ssl/openssl.cnf, unfortunately this won't work everywhere, with Windows being the obvious example.

How do I programmatically determine the full path to the openssl default configuration file?

What I've Tried

There's a glaring hint in the documentation

-config filename
this allows an alternative configuration file to be specified, this overrides the compile time filename or any specified in the OPENSSL_CONF environment variable.

I've read the config documentation and searched the source code, but I can't discover the mechanism by which it chooses from where to load the "compile time" default config file. If I could find that, then I would prefer to load it as a variable into the script instead of the hard-coded path.

Moreover, my $OPENSSL_CONF variable is empty.

A Bad Alternative

Currently my script checks these conditions, and uses the first one that evaluates to true:

  1. $OPENSSL_CONF variable is populated, and file exists
  2. /etc/ssl/openssl.cnf exists

If neither of those are true, then it includes a copy of a standard configuration. This is undesirable because it would in effect override custom settings established by the client. I want to use the environment's conditions completely, and simply add the SAN section as an addendum.

I could further extend this chain with the paths of the usual suspects or even a system search. But in the event that multiple exist, then I have no assurance of which is in fact used by openssl as a default.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

As mentioned in one of the comments, the easy answer should be to find the path using the following command:

openssl version -d

If this doesn't work, you could presume that OpenSSL is not correctly configured, or at least doesn't have the configuration you need. Here is an example in Node.js on how you could get the location of openssl.cnf:

const util = require('util');
const path = require('path');
const exec = util.promisify(require('child_process').exec);

(async () => {
    const opensslCnfPath = path.normalize(`${(await exec('openssl version -d')).stdout.match(/"(.*)"/).pop()}/openssl.cnf`);
    console.log(opensslCnfPath);
})();

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...