← Back to Feed CACHED · 2026-05-17 09:42:19 · cache_key CVE-2025-29912
tenable:109945 · CWE-674 · Disclosed 2018-03-27

OpenSSL 1

ASSESSED — NOISGATE V0.5
Vendor
Reassessed
Verdict:
01 · The Real Story

This is a smoke detector tripping in the basement, not the front door being kicked in

Plugin 109945 maps to CVE-2018-0739, an uncontrolled-recursion bug in OpenSSL ASN.1 parsing. Upstream affected ranges are 1.0.2b–1.0.2n and 1.1.0–1.1.0g, fixed in 1.0.2o and 1.1.0h. The crash path is tied to maliciously recursive ASN.1 structures such as those seen in PKCS7/CMS-style content, and the outcome is process DoS, not code execution or data theft.

The vendor MEDIUM label is technically defensible in a vacuum, but it overstates enterprise urgency for a generic OpenSSL version finding. OpenSSL's own advisory says the vulnerable structures are not used in SSL/TLS from untrusted sources, so the usual 'internet-facing TLS service with old OpenSSL' mental model is wrong here; add Tenable's version-only, self-reported detection and this becomes mostly a low-priority validation task, not a patch emergency.

"This is not a generic remote-TLS OpenSSL fire drill; for most fleets it is narrow, availability-only, and scanner-noisy."
02 · The Attack Path

4 steps from start to impact.

STEP 01

Find an app that actually feeds untrusted ASN.1 into OpenSSL

The attacker needs more than a host with old OpenSSL. They need an application path that hands attacker-controlled PKCS7/CMS/S/MIME or similar ASN.1 objects to the vulnerable parser, using the system's OpenSSL library. A plain HTTPS listener is usually not enough because the advisory explicitly says the unsafe structures are not part of normal untrusted SSL/TLS input.
Conditions required:
  • Affected OpenSSL build in the upstream vulnerable range or an unfixed vendor package
  • An exposed application workflow that parses attacker-supplied ASN.1/PKCS7/CMS/S/MIME content
Where this breaks in practice:
  • Most enterprise OpenSSL exposure is ordinary TLS, which is *not* the reachable path here
  • Many flagged hosts will never parse attacker-controlled PKCS7/CMS data at all
Detection/coverage: Network scanners generally cannot prove parser reachability. Plugin 109945 does not test exploitability; it keys off installed version data.
STEP 02

Generate a deeply recursive ASN.1 payload

The attacker then needs a crafted recursive ASN.1 object, typically produced with a custom generator or fuzz-derived testcase. This is not a stock Metasploit-style one-click exploit chain; it is a crash payload aimed at exhausting stack depth in the parser.
Conditions required:
  • Ability to craft malformed recursive ASN.1 content
  • Understanding of the target application's accepted file/message format
Where this breaks in practice:
  • Public weaponization is weak; Tenable marks 'no known exploits are available'
  • The payload must match a real ingest path, not just 'OpenSSL is installed'
Detection/coverage: Content-aware gateways may log malformed PKCS7/CMS/S/MIME artifacts, but generic vuln scanning will not.
STEP 03

Deliver the payload through the specific business workflow

The attacker must feed that payload into a feature such as certificate/message import, S/MIME processing, CMS verification, package-signature handling, or another ASN.1-consuming path. This is a workflow-specific delivery problem, not a broad network-reachable OpenSSL exploit surface.
Conditions required:
  • A reachable import/verification path
  • The target service actually delegates parsing to vulnerable OpenSSL code
Where this breaks in practice:
  • Many enterprises front these workflows with mail hygiene, file screening, or simply do not expose them externally
  • Lots of affected binaries sit behind authenticated or internal-only paths
Detection/coverage: Application logs, mail gateway logs, and crash logs are more useful than perimeter IDS here.
STEP 04

Crash the parsing process

If all prior conditions line up, the parser can recurse until the stack is exhausted and the process crashes. The blast radius is usually a service interruption for one application instance or worker process, not host takeover.
Conditions required:
  • Payload reaches the parser unchanged
  • No upstream or distro backport fix present
Where this breaks in practice:
  • Supervisors, worker recycling, and service restarts reduce practical impact
  • Outcome is availability-only; there is no demonstrated RCE path in the advisory
Detection/coverage: Look for segfaults, abrupt worker exits, coredumps, and repeated service restarts around ASN.1/PKCS7 processing.
03 · Intelligence Metadata

The supporting signals.

In-the-wild statusNo public active exploitation evidence found in the vendor/NVD corpus reviewed, and not present in CISA KEV as of 2026-02-14 (*inference from catalog search absence*).
Public exploit / PoCTenable records 'No known exploits are available' for this CVE/plugin. I did not find a mainstream Metasploit or Exploit-DB path in primary-source review.
EPSSTenable's CVE page, sourcing FIRST EPSS, shows 0.16197. That's non-zero exploit likelihood, but it does not override the big reachability friction here.
KEV statusNot KEV-listed on the CISA catalog page checked on 2026-02-14 (*inference from absence*). No due date pressure from KEV.
CVSS vector reality checkCVSS:3.0/AV:N/AC:L/PR:N/UI:R/S:U/C:N/I:N/A:H reads like a network bug, but the real reachable path is narrower because normal untrusted SSL/TLS traffic is explicitly called out as safe by OpenSSL.
Affected versionsUpstream affected: OpenSSL 1.0.2b–1.0.2n and 1.1.0–1.1.0g.
Fixed versionsUpstream fixed in 1.0.2o and 1.1.0h. Canonical backported fixes to distro packages such as xenial 1.0.2g-1ubuntu4.11 and bionic/cosmic/disco 1.0.2n-1ubuntu5.
Detection qualityPlugin 109945 says Nessus 'has not tested for this issue' and relies on the application's self-reported version number. That is a strong false-positive amplifier on backported distro builds.
Exposure / scanning dataThere is no meaningful Shodan/Censys-style census for this CVE alone because exposure depends on an application's use of OpenSSL's ASN.1 parser, not simply on port 443 being open.
Disclosure / creditDisclosed 2018-03-27. Reported by OSS-Fuzz; fix developed by Matt Caswell per the OpenSSL advisory.
04 · The Call

noisgate verdict.

Final Verdict
DOWNGRADED to LOW (2.6/10)

The decisive downgrade factor is that normal untrusted SSL/TLS traffic is not the vulnerable path; an attacker needs a much narrower application workflow that parses attacker-controlled ASN.1/PKCS7/CMS content. Combined with version-only scanner evidence and availability-only impact, this does not justify MEDIUM patch priority across a 10,000-host fleet.

HIGH OpenSSL's statement that the unsafe structures are not used in untrusted SSL/TLS
HIGH Tenable plugin `109945` being version-only and non-exploit-validated
MEDIUM Most enterprise hits being non-reachable in practice

Why this verdict

  • Major downward adjustment: reachable only through non-standard parser paths. The attacker position is *not* generic unauthenticated remote-to-TLS; it implies a specific app workflow that ingests attacker-controlled ASN.1/PKCS7/CMS data, which sharply shrinks the exposed population.
  • Impact is limited to DoS. Even where reachable, the practical outcome is a process crash or service interruption, not RCE, credential theft, or tenant-wide compromise.
  • Scanner evidence is weak. Plugin 109945 explicitly relies on self-reported versioning and does not test exploitability, so backported distro packages and non-reachable library instances inflate the queue.
  • No KEV / no exploitation signal. There is no CISA KEV pressure and no strong public weaponization evidence in the primary-source set reviewed.

Why not higher?

If this were a generic TLS-handshake bug on internet-facing services, a MEDIUM or HIGH argument would be easier. It is not: OpenSSL says the vulnerable recursive structures are not part of untrusted SSL/TLS input, and that single fact collapses the exposed population. Add version-only detection noise and the case for urgent fleet-wide action falls apart.

Why not lower?

I am not calling it IGNORE because some products really do parse untrusted PKCS7/CMS/S/MIME and can be crashed if they are on a truly unfixed upstream build. Also, some custom or appliance-style OpenSSL deployments will not benefit from distro backports, so a blanket suppression without validation would be sloppy.

05 · Compensating Control

What to do — in priority order.

  1. Re-scope the finding to parser-exposed apps — Identify which assets actually process attacker-controlled PKCS7/CMS/S/MIME/ASN.1 content and downgrade the rest. For a LOW verdict there is no mitigation SLA; do this as backlog hygiene during the next triage cycle so your patch queue reflects reachable risk, not library name alone.
  2. Prefer vendor-packaged OpenSSL over hand-built copies — Backported distro packages often fix this without changing the upstream-looking version family. For LOW, there is no hard mitigation deadline; use normal maintenance windows to replace stray custom builds with supported packages where feasible.
  3. Gate risky content ingestion paths — Where apps do accept signed mail, CMS blobs, certificate imports, or other ASN.1-heavy artifacts, put validation and content screening in front of them and restrict external reachability. For LOW, do this opportunistically as part of service hardening rather than emergency response.
What doesn't work
  • TLS 1.2-only or cipher-suite hardening doesn't solve this, because the advisory says the vulnerable recursive structures are not in normal untrusted SSL/TLS parsing.
  • A generic WAF is usually irrelevant unless the vulnerable ASN.1 payload is actually transiting an HTTP upload/import workflow the WAF can parse and block.
  • Blindly keying on the OpenSSL upstream version string doesn't prove exposure on backported distro builds.
06 · Verification

Crowdsourced verification payload.

Run this on the target host that Nessus flagged, not from an auditor workstation. Invoke it as python3 check_cve_2018_0739.py with normal user rights; it reads local openssl and package metadata and prints VULNERABLE, PATCHED, or UNKNOWN.

noisgate-verify.py
PYTHONREAD-ONLYSAFE
#!/usr/bin/env python3
# check_cve_2018_0739.py
# Purpose: classify likely exposure to CVE-2018-0739 on the local host.
# Exit codes: 0=PATCHED, 1=VULNERABLE, 2=UNKNOWN

import os
import re
import shutil
import subprocess
import sys


def run(cmd):
    try:
        p = subprocess.run(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True, timeout=10)
        return p.returncode, p.stdout.strip(), p.stderr.strip()
    except Exception as e:
        return 127, "", str(e)


def parse_upstream(ver):
    # Handles forms like 1.0.2n, 1.0.2o-fips, 1.1.0g
    m = re.search(r'(\d+)\.(\d+)\.(\d+)([a-z]?)', ver)
    if not m:
        return None
    major = int(m.group(1))
    minor = int(m.group(2))
    patch = int(m.group(3))
    letter = m.group(4) or ''
    letter_num = ord(letter) - 96 if letter else 0
    return (major, minor, patch, letter_num)


def cmp_tuple(a, b):
    return (a > b) - (a < b)


def upstream_status(openssl_ver):
    t = parse_upstream(openssl_ver)
    if not t:
        return 'UNKNOWN', 'Could not parse OpenSSL version string'

    v_102b = (1, 0, 2, 2)
    v_102n = (1, 0, 2, 14)
    v_102o = (1, 0, 2, 15)
    v_1100 = (1, 1, 0, 0)
    v_110g = (1, 1, 0, 7)
    v_110h = (1, 1, 0, 8)

    if cmp_tuple(t, v_102b) >= 0 and cmp_tuple(t, v_102n) <= 0:
        return 'POTENTIALLY_VULNERABLE', 'Upstream-style version falls in 1.0.2b-1.0.2n'
    if cmp_tuple(t, v_1100) >= 0 and cmp_tuple(t, v_110g) <= 0:
        return 'POTENTIALLY_VULNERABLE', 'Upstream-style version falls in 1.1.0-1.1.0g'
    if cmp_tuple(t, v_102o) >= 0 or cmp_tuple(t, v_110h) >= 0 or t[0] > 1 or (t[0] == 1 and t[1] > 1):
        return 'PATCHED', 'Upstream-style version is at or above fixed release'
    return 'UNKNOWN', 'Version is outside the known affected/fixed ranges or uses unusual packaging'


def ubuntu_backport_check():
    if not shutil.which('dpkg-query'):
        return None

    candidates = ['openssl', 'libssl1.1', 'libssl1.0.2', 'libssl1.0.0']
    installed = {}
    for pkg in candidates:
        rc, out, _ = run(['dpkg-query', '-W', '-f=${Status} ${Version}\n', pkg])
        if rc == 0 and out.startswith('install ok installed '):
            installed[pkg] = out.split()[-1]

    if not installed:
        return None

    # Canonical fixed examples from Ubuntu CVE page
    fixed_thresholds = [
        ('openssl', '1.1.0g-2ubuntu3'),
        ('openssl', '1.0.2g-1ubuntu13.4'),
        ('openssl', '1.0.2g-1ubuntu4.11'),
        ('openssl', '1.0.1f-1ubuntu2.24'),
        ('libssl1.0.2', '1.0.2n-1ubuntu5'),
        ('libssl1.1', '1.1.0g-2ubuntu3'),
    ]

    for pkg, fixed in fixed_thresholds:
        if pkg in installed and shutil.which('dpkg'):
            rc = subprocess.run(['dpkg', '--compare-versions', installed[pkg], 'ge', fixed]).returncode
            if rc == 0:
                return ('PATCHED', f'Debian/Ubuntu package {pkg}={installed[pkg]} is at/above known fixed threshold {fixed}')

    return ('VULNERABLE', 'Debian/Ubuntu package version appears below the known Ubuntu fixed thresholds')


def rpm_backport_check():
    if not shutil.which('rpm'):
        return None

    pkg_names = ['openssl', 'openssl-libs']
    found = []
    for pkg in pkg_names:
        rc, out, _ = run(['rpm', '-q', '--qf', '%{NAME} %{EPOCHNUM}:%{VERSION}-%{RELEASE}\n', pkg])
        if rc == 0 and out:
            found.append(out.strip())

    if not found:
        return None

    # Prefer authoritative comparison if rpmdev-vercmp exists.
    if shutil.which('rpmdev-vercmp'):
        target = '1:1.0.2k-16.el7_6.1'
        for line in found:
            nevra = line.split(None, 1)[1]
            rc, _, _ = run(['rpmdev-vercmp', nevra, target])
            # rpmdev-vercmp returns 0 even when printing relation; parse stdout is inconsistent across versions.
            # Fall back to a conservative exact-match / prefix heuristic if parsing is not available.
        # If rpmdev-vercmp exists but parsing is awkward in a portable script, return UNKNOWN rather than guessing.
        return ('UNKNOWN', 'RPM package found; authoritative version comparison needs local vendor advisory review because backports are common')

    return ('UNKNOWN', 'RPM package found, but safe comparison against backported vendor build levels is not available without distro-specific tooling')


def main():
    if not shutil.which('openssl'):
        print('UNKNOWN: openssl binary not found in PATH')
        sys.exit(2)

    rc, out, err = run(['openssl', 'version'])
    if rc != 0 or not out:
        print(f'UNKNOWN: failed to execute openssl version ({err})')
        sys.exit(2)

    base = out.splitlines()[0]
    status, reason = upstream_status(base)

    if status == 'PATCHED':
        print(f'PATCHED: {base} | {reason}')
        sys.exit(0)

    if status == 'UNKNOWN':
        print(f'UNKNOWN: {base} | {reason}')
        sys.exit(2)

    # Potentially vulnerable upstream version; check common backport-aware package managers.
    deb = ubuntu_backport_check()
    if deb:
        s, r = deb
        print(f'{s}: {base} | {r}')
        sys.exit(0 if s == 'PATCHED' else 1 if s == 'VULNERABLE' else 2)

    rpm = rpm_backport_check()
    if rpm:
        s, r = rpm
        print(f'{s}: {base} | {r}')
        sys.exit(0 if s == 'PATCHED' else 1 if s == 'VULNERABLE' else 2)

    # No package metadata; likely custom or raw upstream install.
    print(f'VULNERABLE: {base} | upstream version is in the affected range and no package-backport evidence was found')
    sys.exit(1)


if __name__ == '__main__':
    main()
07 · Bottom Line

If you remember one thing.

TL;DR
Monday morning, downgrade plugin 109945 findings out of the urgent queue and validate which flagged assets actually parse untrusted PKCS7/CMS/S/MIME/ASN.1 content. For a LOW verdict there is no noisgate mitigation SLA and no noisgate remediation SLA beyond backlog hygiene; document the rationale for plain TLS-only endpoints, suppress clear backport false positives, and patch the smaller set of truly exposed custom/upstream OpenSSL deployments in normal maintenance rather than treating this like a fleet-wide break/fix event.

Sources

  1. Tenable Plugin 109945
  2. OpenSSL Security Advisory 2018-03-27
  3. CVE Record
  4. NVD CVE-2018-0739
  5. Ubuntu CVE-2018-0739
  6. Red Hat Bugzilla 1561266
  7. Tenable CVE page with EPSS
  8. CISA Known Exploited Vulnerabilities Catalog
Peer Review

What defenders are saying.

Submit a review attribution: handle + country only
0 flags selected · stored anonymously
Validation Results

Crowdsourced verification outputs.

Results submitted by users who ran the verification payload against their environment.