Home / Alt manpages / openssl-ts(1ssl)

  • openssl-ts(1ssl)
  • OpenSSL command
  • linux

Create and Verify RFC 3161 Timestamp Requests with openssl ts

You will create a DER-encoded RFC 3161 timestamp request for a file, inspect it, and verify a timestamp response when a TSA returns one. The command does not contact a TSA itself: OpenSSL 3.0.13's openssl ts creates requests, creates replies for a TSA operator, and verifies replies. Moving a request to a service and retrieving its response is a separate step.

Allow about 10 minutes for the local request and inspection. Verification takes a little longer if you need to obtain the TSA certificate chain. You need the openssl package, a file worth timestamping, and a TSA that accepts RFC 3161 requests. No elevated privileges are needed for these examples. Work in a directory where you can keep the original file, request, and response together.

1. Check the installed command

Start by checking the binary and the exact options available on this machine. This guide was checked with Ubuntu's openssl package version 3.0.13-0ubuntu3.15. The manpage is dated 18 August 2026 and identifies the command as OpenSSL 3.0.13.

openssl version -a
openssl ts -help

The three useful modes are -query, -reply, and -verify. A query contains a digest of your data, not the data itself. The TSA signs a timestamp token containing that digest and a time. Anyone verifying the response must still have the original data, or the original request and a trusted certificate source.

2. Create a timestamp request

Keep the input file unchanged after this point. The digest in the request represents its bytes, so editing, normalising line endings, or replacing it later will make data-based verification fail.

mkdir -p "$HOME/ts-work"
cd "$HOME/ts-work"
printf '%s\n' 'release candidate 2026-09-25' > release.txt
openssl ts -query \
  -data release.txt \
  -sha256 \
  -cert \
  -out release.tsq

-data makes OpenSSL hash the named file. The local manpage says SHA-256 is the default, but naming -sha256 makes the choice visible in scripts and review. -cert asks the TSA to include its signing certificate in the response. It does not make a certificate appear in the request itself. A nonce is included by default; keep it unless the TSA specifically requires -no_nonce, because the nonce helps protect against replay.

The command writes DER, a binary format, to release.tsq. A successful run prints no request details because the output has been redirected.

test -s release.tsq && echo "request written"
openssl ts -query -in release.tsq -text

Look for Hash Algorithm: sha256, a 32-byte message imprint, a nonce, and Certificate required: yes. If you omit -out, the default is standard output. That is useful for a pipeline, but it is an easy way to mix binary DER with terminal output, so use a file while learning.

Checkpoint: send the request without changing it

Transfer release.tsq to the TSA using the method agreed with its operator, such as an approved upload or email workflow. OpenSSL's ts command has no built-in HTTP or TCP transport. Do not send release.txt merely because it is convenient: the request is designed to disclose the digest rather than the source data.

Ask for a DER timestamp response, normally saved as release.tsr. A response status that is not granted is not a valid timestamp for this workflow. Keep the returned file unchanged and record which trust anchor is intended for verification.

3. Verify the response against the original file

Verification checks both the message imprint and the TSA signature chain. At least one trust source is mandatory, so replace the example path with a CA bundle that your organisation trusts. The bundle is an input, not a reason to disable certificate checks.

openssl ts -verify \
  -data release.txt \
  -in release.tsr \
  -CAfile /path/to/tsa-trust-chain.pem

Success is reported as:

Verification: OK

The command exits non-zero for a mismatched file, an invalid response, an untrusted signer, or certificate verification errors. Check the exit status in automation:

if openssl ts -verify -data release.txt -in release.tsr \
    -CAfile /path/to/tsa-trust-chain.pem >verify.log 2>&1; then
    echo "timestamp verified"
else
    status=$?
    sed -n '1,120p' verify.log
    echo "timestamp verification failed (exit $status)" >&2
    exit "$status"
fi

Use exactly one of -data, -digest, and -queryfile. For a file-based check, use -data as above. If the original file is unavailable but the original request is preserved, verify that request instead:

openssl ts -verify \
  -queryfile release.tsq \
  -in release.tsr \
  -CAfile /path/to/tsa-trust-chain.pem

That proves the response matches the request, while the request's digest can only be related back to the original file if you have independently preserved or recomputed that file.

4. Understand the TSA operator boundary

-reply is for the operator of a TSA, not a shortcut for obtaining a public timestamp. It needs a configuration file, a timestamping certificate and its private key. The signing certificate must have exactly one critical timeStamping extended key usage. The configuration names a serial file, signer certificate, private key, signing digest and default policy. The serial file is created if absent and incremented for each response, so protect it from concurrent writers and back it up according to the TSA's operating procedure.

For a reply, -queryfile reads the DER request, while -out writes a DER response. -text is for human-readable inspection, not for a response that another tool should verify. If the request asks for the signer certificate, -chain supplies additional PEM certificates; -reply does not build that chain automatically. Treat the private key and serial file as security-sensitive state. Do not run an untested reply configuration against production keys.

5. Diagnose the common failures

  • Digest mismatch: the input changed, the wrong file was supplied, or the response belongs to another request. Recreate the request from the intended file and obtain a new response.
  • Unable to build certificate chain: check -CAfile, -CApath, or -CAstore, then provide missing intermediates with -untrusted. Do not use -no_check_time as a general fix: it changes certificate-time checking.
  • Response format errors: check whether the file is a timestamp response or a bare timestamp token. Add -token_in only when the input really is a DER ContentInfo token.
  • Unexpected policy or algorithm: inspect the request and response with -text. A policy requested with -tspolicy must be accepted by the TSA; it is not a local override.

There is no useful undo for a timestamp already issued. Recovery means preserving the original file and request, rejecting failed verification, and obtaining a fresh response. You can remove only your disposable working copies after retention requirements are satisfied.

Done means

  • release.tsq is a non-empty DER request inspected with -text.
  • The original release.txt is preserved unchanged.
  • A TSA response is stored separately as release.tsr.
  • openssl ts -verify returns zero and prints Verification: OK using an explicitly trusted CA source.