Skip to main content
Skip table of contents

Post Processing Validators

The External Command Certificate Validator allows validating issuance based on other certificate values after the certificate (or eventual pre-certificate) has been generated but not issued, stored and published.

Validator Types 

External Command Certificate Validator

The External Command Certificate Validator allows calling an external script for the generated certificate. The exit code of the external call determines if the validation has failed. This can be used not only to validate certificate criteria, but also to call other external commands or scripts. The user running EJBCA's application server requires the OS file system permissions to do so.

To be able to view and edit the External Script Validator, access to external scripts must be enabled by activating Enable External Script Access under System Configuration → External Scripts.

The first token of the External command field must be the external command or script called, followed by its arguments, all separated by spaces. The certificate is stored as a temporary file on the EJBCA server, and its full path is used as first argument. All subsequent arguments are shifted to the right. If the placeholder %cert% is used as an argument at any position, the certificate is not stored on the EJBCA server file system. Instead the placeholder is removed, and the PEM encoded certificate is fed to the external command or script via STDIN.

The platform for MS Windows and Unix/Linux is auto-detected and the default shell command and shell options are set:

  • MS Windows: cmd.exe /C
  • Unix/Linux: /bin/sh -c

The following displays examples of external commands for Unix/Linux platforms:

$ /usr/local/opt/ -param1 -param2
$ /usr/local/opt/ -param1 -param2 %cert%
$ openssl x509 -text -noout -in %cert%    

Script Allow Listing

An administrator can restrict which scrips can be executed for security reasons, by configuring an allow list on the System Configuration External scripts tab. The allow list should contain a list of paths to all scripts allowed to be executed by the External Command Certificate Validator. If the allow list is enabled by an administrator, any execution of scripts not explicitly listed on the allow list is prevented by EJBCA.

If the External Scripts Allow List has been enabled by an administrator and a Validator tries to execute a command which is not on the allow list, the "Validator was not applicable" action is carried out.

The allow list is formatted according to the following: Each line contains the full path of the allow listed script. Lines beginning with the character # are treated as comments. The allow list can contain any number of scripts. An empty (enabled) allow list will effectively block execution of all external scripts.

The following displays an example of a syntactically valid allow list:

# -----------------------------------------------------------------------
# This is an example, this configuration does not necessarily make sense
# -----------------------------------------------------------------------
# X.509 Certificate Linter by Amazon 
# X.509 Certificate Linter based on CA/B Forum Baseline Requirements and RFC 5280 

This allow list allows the three scripts /opt/certlint/certlint, /opt/certlint/cablint, and /opt/scripts/ to be executed. There is no restriction on the parameters which can be given as input to these scripts. Any input validation should be done in the script itself.

Example Certificate Lint

You can use the External Command Certificate Validator to run a lint check on issued certificates, and abort issuance if certificates don't pass the tests.


  1. First, to enable external scripts, select CA UI → System Configuration → External Scripts:
    • For Enable External Script Access, select Activate
    • In Configure Scripts Allow List, select Use the allow list below and specify a full path. For example /opt/bin/
  2. To add an External Command Certificate Validator, go to Navigators:
    • In Validator Type, select External Command Certificate Validator.
    • In Full pathname of script, add the full path to the script ending with %cert%. For example /opt/bin/ %cert%.
    • Ensure that at least the options Fail on script error code and Log error out are selected.

  3. To enable the validator for the CA, go to Certificate Authorities, click Edit and select the Validator for the CA.

Issue a certificate using a server certificate Certificate Profile. You can see the Validator being triggered in the server.log. To test failures, set Key Usage to Key certificate sign in the Certificate Profile used to issue the end entity certificate. This option is not allowed in the CAB Forum Baseline Requirements. For more information, see Key Usage in Certificate Profile Fields.


ZLint is a X.509 certificate linter that can be downloaded and built from the ZLint homepage.

You must wrap zlint in a script to allow the script to return a 0 exit code on success, and 1 as exit code on failure.

Place the script in the same location as ZLint:

mydir="$(dirname "$(realpath "$0")")"
OUTPUT=`$mydir/zlint -pretty <&0|grep -1 '"error"'`
#echo Output:\"$OUTPUT\"
if [ -z "$OUTPUT" ]; then
  echo "No error in zlint"
  exit 0
  echo "Error in zlint"
  echo $OUTPUT >&2
  exit 1

Test by issuing certificate both with and without the Key Usage option set to Key certificate sign and view the log output in the server.log and the security audit log.


X509Lint is a certificate linter written in C, available for download on GitHub.

X509Lint expects the path to a PEM encoded certificate to be passed as first argument. Since EJBCA writes a DER-encoded certificate to disk, you need to parse the certificate to PEM before invoking the linter. We also need to parse the output to ensure EJBCA fails issuance if there is an error. The wrapper script below uses OpenSSL to convert the certificate to PEM and redirects any error messages to standard error.

Wrapper script for x509lint

# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# x509lint wrapper script for EJBCA.
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

# INSTRUCTIONS: Put this script ( together
# with the x509lint binary in the directory ${BIN} and
# create a new External Command Certificate Validator
# in EJBCA with the following settings:

# Full pathname of script: ${BIN}/
# Fail on script error code: true
# Fail on output to error out: true

# Issuance phase should be "Pre-certificate Validation"
# if CT is being used, and "Certificate Validation"
# otherwise.

mydir=$(dirname "$(realpath "$0")")
pem="/dev/shm/OpenSSL-$(date +%s%N).pem"
openssl x509 -in "$1" -inform DER -out "$pem" -outform PEM

if ! output=`$mydir/x509lint "$pem"`; then
  rm -f "$pem"
  exit 1

rm -f "$pem"

fatals=$(   echo "$output" | grep 'F: ')
errors=$(   echo "$output" | grep 'E: ')
warnings=$( echo "$output" | grep 'W: ')
notices=$(  echo "$output" | grep 'N: ')
infos=$(    echo "$output" | grep 'I: ')
bugs=$(     echo "$output" | grep 'B: ')

if [ ! -z "$fatals" ]; then
  >&2 echo "$fatals"
if [ ! -z "$errors" ]; then
  >&2 echo "$errors"
if [ ! -z "$warnings" ]; then
  echo "$warnings"
if [ ! -z "$notices" ]; then
  echo "$notices"
if [ ! -z "$infos" ]; then 
  echo "$infos"
if [ ! -z "$bugs" ]; then
  echo "$bugs"

Debian Weak Key Checks

Due to an issue (CVE-2008-0166) from 2006 in OpenSSL, whereby a vulnerable version of the library only used the PID as seed when generating RSA or DSA keys, an attacker can find the private key from the corresponding public without much effort. The buggy version of OpenSSL was distributed in two Debian packages between the 17th of September 2006 and the 13th of May 2008.

The Debian project created block lists, which are unfortunately not available any longer:

HARICA has generously generated new lists of weak keys that can be used by the CA community.

The script below was written for the Debian packages, and likely needs to be adjusted for the HARICA keys.

You can check certificates against these block lists before issuance by extracting all the block lists and use a simple script to check for the presence of the key in one of them.

To check the certificates against the block lists, do the following:

  1. Extract the fingerprint block lists into a single directory, and rename the files from the packages in order to keep them all in a single directory on the CA server (the directory /opt/weak-keys in the following example script):

  2. Add the following script to the directory as /opt/weak-keys/ (name and patch can be changed by editing the script to suit your environment).

    #echo $1
    OUTPUT=`grep $(openssl x509 -noout -pubkey -inform DER -in $1 \
        | openssl rsa -pubin -noout -modulus \
        | sha1sum | cut -d ' ' -f 1 | cut -c 21-) \
    if [ -z "$OUTPUT" ]; then
      echo "Key is not in block list"
      exit 0
      echo "Key is in block list"
      echo $OUTPUT >&2
      exit 1
  3. In the External Command Validator, specify the following:

    1. Full pathname of script: /opt/weak-keys/
    2. Fail on script error code: true.
    3. Fail on output to error out: true.
    4. Issuance phase should be Pre-sign Certificate Validation to ensure that checks are done before the CAs private key is used.
    5. Save the Validator.
  4. It is not easy to find examples of weak keys, without generating them yourself. You can test the script by editing the validator again, uploading the following certificate downloaded from to Test Certificate Path and clicking Test Command.

    -----END CERTIFICATE-----
  5. The output should say Test Out: "Exit code: 1STDOUT: Key is in block listERROUT:(name of block list and fingerprint that matches)".

    When uploading another certificate, not on the block list, the Exit code should be 0.
    The following displays an example configuration.

External Command Validator for checking for weak keys

JavaScript errors detected

Please note, these errors can depend on your browser setup.

If this problem persists, please contact our support.