Summary
The WPO365 | LOGIN plugin (wpo365-login) contains a critical authentication bypass in its SAML 2.0 single sign-on handling. Its anti-replay check never persisted the SAML message IDs it was supposed to track, so a captured, validly signed SAMLResponse can be submitted to the plugin's assertion consumer service endpoint again and again, with each submission accepted as a fresh login — including for administrator accounts. The flaw is tracked as CVE-2026-122220, rated critical at CVSS v4 9.1 and classified as CWE-294 (authentication bypass by capture-replay). Versions below 45.2 are affected; 45.2 fixes it.
Remediation
- Update WPO365 | LOGIN to version 45.2 or later, which replaces the broken check with database-backed assertion recording.
- After updating, confirm the table named with your site's base prefix plus wpo365_saml_assertions exists, since the plugin creates it on demand when the first assertion is recorded.
- Do not treat the plugin's duplicate-message-ID check on older versions as a mitigation, because it never stored anything and cannot detect a replay.
- Review WPO365 logs for WARN entries containing a short assertion-hash fingerprint and a NameID, which indicate a replayed assertion was rejected.
- Treat repeated replay warnings for a single user as a sign that a captured SAML response is being reused and investigate that account, whereas a single occurrence is more likely a browser back-navigation.
- If your SAML users are provisioned from Microsoft Entra ID or another identity provider, shorten assertion validity windows where your provider allows it to limit how long a captured response stays useful.
- If you still run OpenID Connect sign-ins on a version below 45.2, note that 45.2 also fixed a separate nonce race condition in that flow, so the upgrade covers both.
Root cause
The plugin's anti-replay routine, Saml2_Service::check_message_id(), was intended to record every processed SAML message ID in the wpo365_saml_message_ids transient and reject any ID seen before. A logic error caused the function to return before it reached the save step, so no message ID was ever stored. With nothing persisted, the duplicate-ID comparison could never find a match, and the replay detection branch was effectively dead code.
The fix
Version 45.2 removes check_message_id() and adds Saml2_Service::record_assertion(), which writes every validated assertion to a dedicated database table named with the site's base prefix plus wpo365_saml_assertions. The table is created on demand, so one table serves an entire multisite network. The assertion ID is hashed with SHA-256 and inserted with INSERT IGNORE against a primary key, so a second request carrying the same assertion inserts zero rows and is rejected. The patch records the assertion's ID rather than the response's ID, because an identity provider may sign only the assertion, in which case the response ID could be altered without breaking the signature. Stored records are given an expiry at least one day out and no earlier than the assertion's NotOnOrAfter plus the allowed clock drift, and expired rows are purged roughly once per hundred calls. Writing directly to the database avoids the transient mechanism entirely, so a persistent object cache can no longer interfere with replay tracking. The same release also changed Nonce_Service::mark_as_used() to return the number of affected rows, with the caller refusing the sign-in when another concurrent request has already consumed the nonce or when the database update fails.
Attack preconditions
- Required access: unauthenticated
- User interaction: not required
- The attacker must first obtain a validly signed SAMLResponse for the target user — no WordPress account or prior session is needed. The replay must happen while the assertion is still inside its validity window. The captured response is then submitted repeatedly to the plugin's SAML assertion consumer service endpoint, and each submission is accepted as a new login. Whether that endpoint is reachable without any prior session or state is not established in the available information.
Impact
Anyone who captures a validly signed SAMLResponse can authenticate as the user that assertion belongs to, including administrator accounts. Each replay is treated as a legitimate fresh sign-in, so the attacker can return for as long as the assertion remains within its validity window. Because the plugin's own duplicate-message-ID check is inert, this activity is not flagged by that mechanism. A critical severity and CVSS v4 score of 9.1 reflect high confidentiality and integrity impact. There is no information on whether real-world exploitation has been observed.
Am I affected?
- Your site runs WPO365 | LOGIN at a version below 45.2, so it is in the affected range.
- Your site uses the plugin's SAML 2.0 single sign-on feature, which is the vulnerable component.
- Your SAML identity provider issues signed SAMLResponse assertions that are valid for a meaningful window, leaving a period in which a captured response can be replayed.
- You have administrator or other privileged accounts signing in through SAML, since a replayed assertion grants the same access as the account it belongs to.
- You cannot confirm your plugin version, in which case check the installed version on the Plugins screen before assuming you are safe.
Exploits & detection
No public PoC or detection template found yet.
Timeline
- Published: 04 Nov 2026
- Last modified upstream: 04 Nov 2026
- VulnCrest analysis published: 05 Nov 2026
Sources & licenses
- CVE / CVSS / CWE
- NVD record ↗ (unmodified). This product uses the NVD API but is not endorsed or certified by the NVD. CVE® © The MITRE Corporation.
- Exploitation
- CISA KEV (CC0) · EPSS by FIRST.org
- References used for the analysis
- advisory WPO365 | SEAMLESS WORDPRESS + MICROSOFT INTEGRATION (WPO365 | LOGIN)
- advisory WPO365 LOGIN before 45.2 SAML Replay Protection Bypass
- patch Patch diff wpo365-login 45.1 → 45.2
- https://plugins.trac.wordpress.org/changeset/3783469/
- https://wordpress.org/plugins/wpo365-login/#developers
- https://www.vulncheck.com/advisories/wpo365-login-before-saml-replay-protection-bypass
- Analysis, summary and remediation
- © VulnCrest
