
CVE-2021-21972 – неавторизованная инъекция кода в VMware Client (RCE)
[CVE-2021-21972] Неавторизованная загрузка файлов в VMware vSphere Client с последующим удаленным выполнением кода (RCE)
Веб-клиент vSphere (HTML5) — это, по сути, административный интерфейс, позволяющий управлять установкой vSphere. Клиент vSphere предоставляет администратору доступ к ключевым функциям vSphere без необходимости прямого доступа к серверу vSphere. Он позволяет администраторам создавать новые виртуальные машины и управлять существующими, а также их ресурсами. Будучи кроссплатформенным веб-приложением, он может использоваться на всех поддерживаемых операционных системах через поддерживаемые версии различных веб-браузеров.
CVE-2021-21972 — это уязвимость неавторизованной загрузки файлов в vCenter Server, которая приводит к удаленному выполнению кода на удаленном сервере. Проблема связана с отсутствием аутентификации в плагине vRealize Operations для vCenter. Она получила критический балл CVSSv3 — 9.8 из 10.0. Неавторизованный удаленный злоумышленник может воспользоваться этой уязвимостью, загрузив специально созданный файл на общедоступную конечную точку уязвимого сервера vCenter. Уязвимости подвержены версии VMware vCenter Server 6.5, 6.7 и 7.0. Успешная эксплуатация этой уязвимости позволит злоумышленнику получить неограниченные привилегии удаленного выполнения кода (RCE) в базовой операционной системе сервера vCenter. Несмотря на то, что эта уязвимость исходит от плагина vRealize Operations для vCenter, совет VMware подтверждает, что этот плагин включен во все установки по умолчанию vCenter Server. Это означает, что уязвимая конечная точка доступна независимо от наличия vRealize Operations.
В оригинальной статье в блоге здесь обнаружение уязвимости объяснено максимально подробно, а также описаны два отдельных пути для достижения RCE. Для систем Windows злоумышленник может загрузить специально созданный .jsp-файл, чтобы получить привилегии NT AUTHORITY\SYSTEM в базовой операционной системе. Для систем Linux злоумышленнику необходимо сгенерировать и загрузить открытый ключ в путь authorized_keys сервера, а затем подключиться к уязвимому серверу по SSH, чтобы получить привилегии пользователя vsphere-ui. (если служба SSH запущена и доступна по сети)
vropsplugin-service.jar — это файл Java-архива плагина vropspluginui, который включает в себя некоторые классы и другие связанные функции и методы. Уязвимая часть кода показана ниже. Этот фрагмент кода принадлежит ServicesController.class в контроллере vropsplugin-service.jar. Как вы можете видеть в приведенном ниже фрагменте кода, функция uploadOvaFile отвечает за конечную точку/URL /ui/vropspluginui/rest/services/uploadova
Полный путь к уязвимому классу: vropsplugin-service\com\vmware\vropspluginui\mvc\ServicesController.class
@RequestMapping(value = {"/uploadova"}, method = {RequestMethod.POST})
public void uploadOvaFile(@RequestParam(value = "uploadFile", required = true) CommonsMultipartFile uploadFile, HttpServletResponse response) throws Exception {
logger.info("Entering uploadOvaFile api");
int code = uploadFile.isEmpty() ? 400 : 200;
PrintWriter wr = null;
try {
if (code != 200) {
response.sendError(code, "Arguments Missing");
return;
}
wr = response.getWriter();
} catch (IOException e) {
e.printStackTrace();
logger.info("upload Ova Controller Ended With Error");
}
response.setStatus(code);
String returnStatus = "SUCCESS";
if (!uploadFile.isEmpty())
try {
logger.info("Downloading OVA file has been started");
logger.info("Size of the file received : " + uploadFile.getSize());
InputStream inputStream = uploadFile.getInputStream();
File dir = new File("/tmp/unicorn_ova_dir");
if (!dir.exists()) {
dir.mkdirs();
} else {
String[] entries = dir.list();
for (String str : entries) {
File currentFile = new File(dir.getPath(), str);
currentFile.delete();
}
logger.info("Successfully cleaned : /tmp/unicorn_ova_dir");
}
TarArchiveInputStream in = new TarArchiveInputStream(inputStream);
TarArchiveEntry entry = in.getNextTarEntry();
List<String> result = new ArrayList<String>();
while (entry != null) {
if (entry.isDirectory()) {
entry = in.getNextTarEntry();
continue;
}
File curfile = new File("/tmp/unicorn_ova_dir", entry.getName());
File parent = curfile.getParentFile();
if (!parent.exists())
parent.mkdirs();
OutputStream out = new FileOutputStream(curfile);
IOUtils.copy((InputStream)in, out);
out.close();
result.add(entry.getName());
entry = in.getNextTarEntry();
}
in.close();
logger.info("Successfully deployed File at Location :/tmp/unicorn_ova_dir");
} catch (Exception e) {
logger.error("Unable to upload OVA file :" + e);
returnStatus = "FAILED";
}
wr.write(returnStatus);
wr.flush();
wr.close();
}
С точки зрения злоумышленника, обработчик этого класса выполняет следующие действия
uploadFile через POST-запрос (строка 2)uploadFile и запись его содержимого в переменную inputStream (строка 22)/tmp/unicorn_ova_dir + entry.getName() (строка 42 и 47)Доказательство концепции (PoC): Чтобы воспользоваться этой уязвимостью, можно выполнить следующие шаги
../..//statsreport/uploadedFileName.jspДля проверки наличия уязвимости можно использовать следующий запрос
GET /ui/vropspluginui/rest/services/getstatus HTTP/1.1
Host: vulnerablehost
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36
Connection: close
Если ответ на вышеуказанный запрос будет похож на ответы ниже, это означает, что удаленный хост уязвим к CVE-2021-21972
HTTP/1.1 200
Strict-Transport-Security: max-age=30758400;includeSubDomains
X-XSS-Protection: 1; mode=block
Set-Cookie: VSPHERE-UI-JSESSIONID=35CB9D3F277D6B8413F099F93FB3A5CE; Path=/ui; Secure; HttpOnly
Content-Type: text/plain;charset=ISO-8859-1
Content-Length: 141
Date: Tue, 06 Apr 2021 14:32:30 GMT
Connection: close
Server: Anonymous
{"States":"[]","Install Progress":"UNKNOWN","Config Progress":"UNKNOWN","Config Final Progress":"UNKNOWN","Install Final Progress":"UNKNOWN"}
HTTP/1.0 200 OK
strict-transport-security: max-age=30758400;includeSubDomains
x-xss-protection: 1; mode=block
set-cookie: VSPHERE-UI-JSESSIONID=3D8FE882F9BD3DD1C66C10DFD00022C9; Path=/ui; Secure; HttpOnly
content-type: text/plain;charset=ISO-8859-1
content-length: 374
date: Tue, 06 Apr 2021 14:33:22 GMT
server: envoy
x-envoy-upstream-service-time: 1
connection: close