CVE-2026-21439 Overview
CVE-2026-21439 is an output injection vulnerability affecting badkeys, a tool and library for checking cryptographic public keys for known vulnerabilities. In versions 0.0.15 and below, an attacker may inject content with ASCII control characters like vertical tabs, ANSI escape sequences, and other control characters that can create misleading output from the badkeys command-line tool. This impacts scanning DKIM keys (both --dkim and --dkim-dns), SSH keys (--ssh-lines mode), and filenames in various modes.
Critical Impact
Attackers can manipulate terminal output to deceive administrators by injecting control characters into cryptographic key data, potentially masking security warnings or displaying misleading information during key vulnerability scans.
Affected Products
- badkeys versions 0.0.15 and below
- badkeys DKIM key scanning functionality (--dkim, --dkim-dns)
- badkeys SSH key scanning functionality (--ssh-lines mode)
Discovery Timeline
- 2026-01-06 - CVE CVE-2026-21439 published to NVD
- 2026-01-08 - Last updated in NVD database
Technical Details for CVE-2026-21439
Vulnerability Analysis
This vulnerability falls under CWE-150 (Improper Neutralization of Escape, Meta, or Control Sequences). The badkeys command-line tool processes cryptographic key data from various sources including DKIM DNS records, SSH key files, and user-provided filenames. When the tool outputs results to the terminal, it fails to properly sanitize or escape control characters embedded within this data.
An attacker who controls the content of cryptographic keys or filenames being scanned can embed ASCII control characters (such as vertical tabs, carriage returns, or ANSI escape sequences) within the key comments, DKIM record values, or filenames. When badkeys processes and displays these values, the injected control characters are interpreted by the terminal, allowing manipulation of the displayed output.
The practical impact includes the ability to hide security warnings by overwriting previous terminal lines, inject fake "safe" messages that appear to come from badkeys, or create visual confusion that could lead an administrator to trust a compromised key.
Root Cause
The root cause is improper output encoding in the badkeys CLI module. User-controlled input from SSH key comments, DKIM key type values, and filenames was passed directly to terminal output without escaping control characters. The runcli.py module lacked an escape function to neutralize dangerous characters before display, and the dkim.py module directly interpolated untrusted values into warning messages.
Attack Vector
This vulnerability requires local access to control the input data being processed by badkeys. An attacker must be able to influence the content of cryptographic keys or filenames that will be scanned. Attack scenarios include:
Malicious SSH Key Comments: An attacker places an SSH public key with crafted comments containing ANSI escape sequences on a system. When an administrator runs badkeys with --ssh-lines, the terminal output is manipulated.
DKIM Record Poisoning: If an attacker can influence DNS DKIM records (through DNS hijacking or compromised domain), they can embed control characters in the key type field that manipulate output when scanned.
Filename Manipulation: Crafted filenames containing control characters can manipulate output when badkeys scans directories.
The following patches demonstrate the security fix implemented in version 0.0.16:
Patch 1: Adding escape function import in runcli.py
from .scanssh import scanssh
from .scantls import scantls
from .update import update_bl
-from .utils import _errexit, _getret, _setret, _warnmsg
+from .utils import _errexit, _esc, _getret, _setret, _warnmsg
MAXINPUTSIZE = 2048000
Source: GitHub Commit 635a2f3
Patch 2: Implementing the escape function in utils.py
_retval = 0
+def _esc(inp):
+ return repr(inp)[1:-1]
+
+
@functools.cache
def _setret(rv):
global _retval
Source: GitHub Commit 635a2f3
Patch 3: Removing user-controlled values from warning messages in dkim.py
return False
der = EDASN1 + rawed
return PUBPRE + base64.b64encode(der).decode() + PUBPOST
- _warnmsg(f"Unknown DKIM key type {dkim['k']}")
+ _warnmsg("Unknown DKIM key type")
return False
Source: GitHub Commit de631f6
Detection Methods for CVE-2026-21439
Indicators of Compromise
- Presence of ASCII control characters (0x00-0x1F, 0x7F) in SSH key comment fields
- ANSI escape sequences (\\x1b[) embedded in DKIM DNS TXT records
- Filenames containing vertical tabs (\\x0b), carriage returns (\\x0d), or other control characters in directories scanned by badkeys
- Unusual terminal behavior when running badkeys scans
Detection Strategies
- Monitor for anomalous characters in DNS DKIM TXT records using DNS monitoring tools
- Implement file integrity monitoring to detect filenames containing non-printable characters
- Review SSH authorized_keys files for embedded control sequences in key comments
- Audit badkeys version in use across systems to identify vulnerable installations
Monitoring Recommendations
- Enable logging of badkeys CLI output to files rather than relying solely on terminal display
- Implement automated version checking for security tools including badkeys
- Monitor DNS query logs for DKIM record lookups that return responses with unusual character patterns
- Use terminal recording tools when performing security audits to capture raw output for later analysis
How to Mitigate CVE-2026-21439
Immediate Actions Required
- Upgrade badkeys to version 0.0.16 or later immediately
- Review recent badkeys scan outputs for potential manipulation if using affected versions
- Redirect badkeys output to log files and review with tools that display control characters visibly
- Validate the integrity of any security decisions made based on badkeys output from affected versions
Patch Information
The vulnerability is fixed in badkeys version 0.0.16. The fix introduces an _esc() function that escapes control characters in user-controlled output by using Python's repr() function to convert control characters to their escaped representations. Additionally, the DKIM module was updated to remove user-controlled values from warning messages entirely.
For detailed patch information, see:
Workarounds
- Redirect badkeys output to a file and review with a hex editor or tool that renders control characters visibly (e.g., cat -v, hexdump)
- Pipe badkeys output through cat -v to make control characters visible: badkeys --dkim example.com | cat -v
- Avoid using badkeys in interactive terminal sessions until upgraded; use non-interactive batch processing with log capture instead
- Manually validate cryptographic keys using alternative tools to cross-check badkeys results
# Configuration example: Safe execution with output sanitization
# Run badkeys with output piped through cat -v to reveal control characters
badkeys --ssh-lines authorized_keys | cat -v > scan_results.txt
# Alternative: Use hexdump for detailed character inspection
badkeys --dkim-dns example.com 2>&1 | hexdump -C > dkim_scan.hex
# Upgrade to patched version
pip install --upgrade badkeys>=0.0.16
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

