jueves, 26 de junio de 2014

Defeating WebShells Detection Tools II: bypassing NeoPI y Linux Malware Detector

¡Saludos!

    Hoy toca conseguir pasar desapercibido ante la herramienta NeoPI. Antes de nada decir que originalmente Seth escribió un artículo hace algunos años donde también conseguía saltarse los análisis de esta herramienta, pero no he encontrado ningún enlace porque su web ha desaparecido. Su técnica se basaba en introducir un carácter muchas veces repetido dentro de la cadena en base64 que contenía la webshell, de tal forma que el análisis de entropía lo pasaba sin problemas. En mi caso el bypass lo he conseguido de otra forma.

Tras hacer el post y dejarlo en borrador antes de publicarlo me dispuse a intentar bypassear Linux Malware Detect, pero no me detectaba la webshell (era la misma que usé para saltarme NeoPI). Imagino que se debe a que ambos deben de  compartir las mismas técnicas de análisis estadístico. La combinación de las técnicas usadas saltar Web Shell Detector y para NeoPI sirven también para LMD, por lo que veo innecesario crear un post adrede. Por ello lo añado aquí.

    NeoPI (https://github.com/Neohapsis/NeoPI ) es un script en python destinado a la detección de webshells alojadas en servidores. Utiliza un sistema de firmas para detectar funciones maliciosas y además se vale de métodos estadísticos para detectar posibles trozos de texto codificados. A través de estas técnicas se establece un ranking de archivos con más posibilidades de contener código malicioso.

  Para comprobar su funcionamiento vamos a utilizar el mismo archivo que en el post anterior se generó para bypassear Web Shell Detector y la C100 sin tocar, ambos alojadas en una instalación limpia de un WordPress. El log de NeoPI es el siguiente (remarco en rojo las webshells):

python neopi.py -a -A /opt/lampp/htdocs/wordpress

       )         (   (
    ( /(         )\ ))\ )
    )\())  (    (()/(()/(
   ((_)\  ))\ (  /(_))(_))
    _((_)/((_))\(_))(_))
   | \| (_)) ((_) _ \_ _|
   | .` / -_) _ \  _/| |
   |_|\_\___\___/_| |___| Ver. *.USEGIT
 

[[ Total files scanned: 2495 ]]
[[ Total files ignored: 0 ]]
[[ Scan Time: 7.080000 seconds ]]

[[ Average IC for Search ]]
0.0374353036826

[[ Top 10 lowest IC files ]]
  0.0254        /opt/lampp/htdocs/wordpress/out.php
  0.0262        /opt/lampp/htdocs/wordpress/c100.php
  0.0285        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Source.php
  0.0303        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
  0.0315        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
  0.0320        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp-pure.php
  0.0326        /opt/lampp/htdocs/wordpress/wp-includes/feed-rdf.php
  0.0330        /opt/lampp/htdocs/wordpress/wp-content/plugins/akismet/widget.php
  0.0330        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Locator.php
  0.0331        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php

[[ Top 10 entropic files for a given search ]]
  5.9758        /opt/lampp/htdocs/wordpress/c100.php
  5.7239        /opt/lampp/htdocs/wordpress/wp-config.php
  5.5975        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Net/IPv6.php
  5.5953        /opt/lampp/htdocs/wordpress/wp-includes/class-json.php
  5.5943        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Parse/Date.php
  5.5918        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
  5.5818        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.flac.php
  5.5537        /opt/lampp/htdocs/wordpress/wp-includes/default-constants.php
  5.5489        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Content/Type/Sniffer.php
  5.5436        /opt/lampp/htdocs/wordpress/out.php

[[ Top 10 longest word files ]]
  407291        /opt/lampp/htdocs/wordpress/out.php
   31483        /opt/lampp/htdocs/wordpress/c100.php
     522        /opt/lampp/htdocs/wordpress/wp-includes/functions.php
     364        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.mp3.php
     354        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Misc.php
     307        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php
     267        /opt/lampp/htdocs/wordpress/wp-includes/formatting.php
     250        /opt/lampp/htdocs/wordpress/wp-includes/class-wp-editor.php
     236        /opt/lampp/htdocs/wordpress/wp-includes/class-phpmailer.php
     189        /opt/lampp/htdocs/wordpress/wp-admin/tools.php

[[ Top 10 signature match counts ]]
     141        /opt/lampp/htdocs/wordpress/c100.php
      26        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
      13        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/native.php
      13        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-wp-filesystem-ssh2.php
       9        /opt/lampp/htdocs/wordpress/wp-includes/class-phpmailer.php
       8        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/config.php
       7        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/classes/PSpellShell.php
       6        /opt/lampp/htdocs/wordpress/wp-admin/includes/file.php
       5        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/shell.php
       4        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/changelog.txt

[[ Top 10 SUPER-signature match counts (These are usually bad!) ]]
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Renderer/inline.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/native.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/xdiff.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/string.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/shell.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Renderer.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/XML/Declaration/Parser.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Net/IPv6.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Content/Type/Sniffer.php

[[ Top cumulative ranked files ]]
       7        /opt/lampp/htdocs/wordpress/c100.php
      52        /opt/lampp/htdocs/wordpress/out.php
      71        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php
      76        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
      86        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/MySQL.php
      96        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
     107        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Source.php
     120        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp-pure.php
     124        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.mp3.php
     129        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Misc.php


   Podemos observar como ha detectado a la perfección nuestras dos webshells. Es decir, que el bypass que hicimos a Web Shell Detector en el post anterior no es suficiente, ya que sigue cantando.  Si nos fijamos out.php ha sido detectada de forma brutal en el test de tamaño de strings y en el de índice de coincidencia. Esto es debido a que tenemos un gigantesco string en base64 que es el que contiene el source codificado de la c100. Igualmente tambien es detectado en décimo lugar por el análisis de entropía.

   Para no ser detectado por los análisis estadísticos deberemos de cortar el string gigantesco en subcadenas y proceder a concatenarlas. Con un sencillo script en perl podemos separarlo en bloques de 4 caracteres. Después sólo queda sustituir el string original por el resultado obtenido. Por ejemplo:

open(FILEA,"<","sucio.txt"); #Contiene la cadena en base64 gigante
open(FILEB, ">>", "limpio.txt");
@string = <FILEA>;
$string = join("", @string);
$size = length($string);
$i = 0;
print FILEB '$z = ""'."\n";
while ($i < $size) {
$prob = substr($string, $i, 4);
print FILEB '$z .= "'.$prob.'";'."\n";
$i = $i + 4;
}
close(FILEA);
close(FILEB);

El resultado una vez sustituido en el archivo original sería algo similar a:

Sección de la webshell ofuscada


Una vez editado out.php, procedemos a pasarle neopi de nuevo:

python neopi.py -a -A /opt/lampp/htdocs/wordpress

       )         (   (
    ( /(         )\ ))\ )
    )\())  (    (()/(()/(
   ((_)\  ))\ (  /(_))(_))
    _((_)/((_))\(_))(_))
   | \| (_)) ((_) _ \_ _|
   | .` / -_) _ \  _/| |
   |_|\_\___\___/_| |___| Ver. *.USEGIT
   

[[ Total files scanned: 2495 ]]
[[ Total files ignored: 0 ]]
[[ Scan Time: 8.070000 seconds ]]

[[ Average IC for Search ]]
0.0368664717785

[[ Top 10 lowest IC files ]]
  0.0262        /opt/lampp/htdocs/wordpress/c100.php
  0.0285        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Source.php
  0.0303        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
  0.0315        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
  0.0320        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp-pure.php
  0.0326        /opt/lampp/htdocs/wordpress/wp-includes/feed-rdf.php
  0.0330        /opt/lampp/htdocs/wordpress/wp-content/plugins/akismet/widget.php
  0.0330        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Locator.php
  0.0331        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php
  0.0333        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/rpc.php

[[ Top 10 entropic files for a given search ]]
  5.9758        /opt/lampp/htdocs/wordpress/c100.php
  5.7239        /opt/lampp/htdocs/wordpress/wp-config.php
  5.5975        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Net/IPv6.php
  5.5953        /opt/lampp/htdocs/wordpress/wp-includes/class-json.php
  5.5943        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Parse/Date.php
  5.5918        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
  5.5818        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.flac.php
  5.5537        /opt/lampp/htdocs/wordpress/wp-includes/default-constants.php
  5.5489        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Content/Type/Sniffer.php
  5.5282        /opt/lampp/htdocs/wordpress/wp-includes/load.php

[[ Top 10 longest word files ]]
   31483        /opt/lampp/htdocs/wordpress/c100.php
     522        /opt/lampp/htdocs/wordpress/wp-includes/functions.php
     364        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.mp3.php
     354        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Misc.php
     307        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php
     267        /opt/lampp/htdocs/wordpress/wp-includes/formatting.php
     250        /opt/lampp/htdocs/wordpress/wp-includes/class-wp-editor.php
     236        /opt/lampp/htdocs/wordpress/wp-includes/class-phpmailer.php
     189        /opt/lampp/htdocs/wordpress/wp-admin/tools.php
     189        /opt/lampp/htdocs/wordpress/wp-admin/options-writing.php

[[ Top 10 signature match counts ]]
     141        /opt/lampp/htdocs/wordpress/c100.php
      26        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
      13        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/native.php
      13        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-wp-filesystem-ssh2.php
       9        /opt/lampp/htdocs/wordpress/wp-includes/class-phpmailer.php
       8        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/config.php
       7        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/classes/PSpellShell.php
       6        /opt/lampp/htdocs/wordpress/wp-admin/includes/file.php
       5        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/shell.php
       4        /opt/lampp/htdocs/wordpress/wp-includes/js/tinymce/plugins/spellchecker/changelog.txt

[[ Top 10 SUPER-signature match counts (These are usually bad!) ]]
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Renderer/inline.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/native.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/xdiff.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/string.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Engine/shell.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff/Renderer.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/Text/Diff.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/XML/Declaration/Parser.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Net/IPv6.php
       0        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Content/Type/Sniffer.php

[[ Top cumulative ranked files ]]
       5        /opt/lampp/htdocs/wordpress/c100.php
      68        /opt/lampp/htdocs/wordpress/wp-includes/class-simplepie.php
      74        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/DB.php
      83        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Cache/MySQL.php
      93        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp.php
     104        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Source.php
     117        /opt/lampp/htdocs/wordpress/wp-admin/includes/class-ftp-pure.php
     121        /opt/lampp/htdocs/wordpress/wp-includes/ID3/module.audio.mp3.php
     126        /opt/lampp/htdocs/wordpress/wp-includes/SimplePie/Misc.php
     157        /opt/lampp/htdocs/wordpress/wp-includes/ID3/getid3.lib.php



   Con un truco así de sencillo hemos conseguido escapar del radar. No aparece en ninguno de los diferentes análisis: hemos subido el IC, disminuido la entropia y todos los strings son pequeños.


Otras dos herramientas (NeoPI, y sin querer Linux Malware Detector) que han sido vencidas.


Byt3z!
5 0verl0ad Labs: Defeating WebShells Detection Tools II: bypassing NeoPI y Linux Malware Detector ¡Saludos!     Hoy toca conseguir pasar desapercibido ante la herramienta NeoPI. Antes de nada decir que originalmente Seth escribió un art...

3 comentarios:

seth dijo...

Mi post esta en archive.org. Usaba file_put_contents() seguido de include() para reemplazar eval(). Creo que nunca se me ocurrio probar con mayusculas.

Tengo una herramienta en mente que probablemente vas a usar, cuando quieras hablame y te cuento.

The X-C3LL dijo...

Lo de mayúsculas es para PHP WebShell Detector. La expresión regular la hace case sensitive.

The X-C3LL dijo...

Btw. intentaré pasarme por el IRC esta semana y hablamos.

< >