Cisco Modular Policy Framework (II)

En el anterior post dedicado a MPF vimos de forma sencilla cómo podemos inspeccionar tráfico a nivel de aplicación para su posterior filtrado; en el ejemplo vimos como se puede filtrar una consulta DNS dependiendo de la búsqueda realizada, no obstante, una gran funcionalidad que nos aporta MPF es la posibilidad de usar expresiones regulares, lo cual nos permite por ejemplo, implementar una firma para una vulnerabilidad reciente de la que todavía no existe parche publicado, y que todavía no tienen firma oficial nuestros sistemas IDS (como podría ser SNORT).

En este post, y dada la reciente entrada de Raúl vamos a usar MPF para, mediante una expresión regular, registrar y filtrar la reciente vulnerabilidad cgi-php.

Para llevar a cabo dicho filtrado, podríamos seguir los siguientes pasos:

1. Configuramos una expresión regular que nos permita detectar los patrones de tráfico interesantes, en este caso, los que identifican potenciales ataques contra la nueva vulnerabilidad:

ciscoasa(config)# regex php_cgi "\?\-[acndefhilmrBRFEHTsvwz]"

Podemos comprobar si una url hace match con la expresion regular mediante el comando test:

ciscoasa# test regex http://www.testpage.com/wordpress/?-s ?-[acndefhilmrBRFEHsvwz]
INFO: Regular expression match succeeded.

Nota: Tenemos que pulsar crtl+v para evitar que se interprete el simbolo ? en la consola del sistema.

2. Creamos un policy-map donde asociamos la expresión regular creada anteriormente y especificamos las acciones a llevar a cabo, en este caso, la filtramos y registramos el acceso:

ciscoasa(config)# policy-map type inspect http HTTP_PHP_CGI
ciscoasa(config-pmap)# match request args regex php_cgi
ciscoasa(config-pmap-c)# drop-connection log

3. Asociamos al policy-map existente la nueva inspección HTTP:

ciscoasa(config)# policy-map global_policy
ciscoasa(config-pmap)# class inspection_default
ciscoasa(config-pmap-c)# inspect http HTTP_PHP_CGI

Puesto que hemos modificado el policy-map creado por defecto, no sería necesario modificar o crear un nuevo service-policy.

Una vez tenemos la configuración finalizada, intentamos acceder a un recurso potencialmente vulnerable y comprobamos en el log que dicho acceso es filtrado correctamente por el sistema:

%ASA-4-415017: HTTP - matched request args regex php_cgi in policy-map HTTP_PHP_CGI,
  arguments matched - Dropping connection from outside:10.10.10.20/1185
  to dmz:172.18.0.150/80

Y en el debug podemos comprobar los pasos realizados durante la conexion HTTP y como es filtrada al hacer match con la expresión regular que inspecciona los argumentos de la petición:

sapi_inspect_http: ====== Opening New Connection D5534E50 =====

D5534E50:request:before deobfuscation httpState=sHTTP_START saveState=sHTTP_START
  matchState=0 data|GET /wordpress/?-s HTTP/1.1..Host: www.testpage.com..User-Agent:
  Mozilla/5.0 (Windows NT 5.1; rv:11.0) Gecko/20100101 Firefox/11.0..Accept:
  text/html,appl0

D5534E50:request:Deobfuscated 309 bytes

D5534E50:Number of outstanding requests=1

D5534E50:request:After deobfuscate httpState=sHTTP_FINAL  matchState=12 meth=2
    URI=/wordpress/
    Params=?-s HTTP/1.1..Host: www.testpage.com.User-Agent: Mozilla/5.0 (Windows NT
      5.1; rv:11.0) Gecko/20100101 Firefox/11.0.Accept: text
    Header=.Host: www.testpage.com.User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:11.0)
      Gecko/20100101 Firefox/11.0.Accept: text/html,applica
    URI Len:12 ARG Len:12 HDR Len:295

D5534E50:request:Searching parameters

request: Check args - Match regex:20,

D5534E50:appfw_action:syslogID:6415017

D5534E50:request:>>>Silently drop & disconnect
PKT|GET /wordpress/?-s HTTP/1.1..Host: www.testpage.com..User-Agent: Mozilla/5.0
  (Windows NT 5.1; rv:11.0) Gecko/20100101 Firefox/11.0..Accept: text/html|
inspectHttp: ======== Closing Connection D5534E50 =======!!

Una alternativa a esta configuración para no tener que inspeccionar todas las conexiones HTTP sería asociar el service-policy a la interfaz que queremos inspeccionar, o una solución aún mejor sería asociar la interfaz y al MPF creado a una lista de acceso para inspeccionar el tráfico solo dirigido a servidores web, para ello llevaríamos a cabo los siguientes pasos:

1. Creamos una ACL para identificar el tráfico a inspeccionar:

ciscoasa(config)# access-list ServidoresWeb extended permit ip any  host 172.18.0.150

2. Creamos un nuevo class-map al que asociamos la access-list creada:

ciscoasa(config)# class-map CM-ServidoresWeb
ciscoasa(config-cmap)# match access-list ServidoresWeb

3. Creamos un policy-map y le asociamos el class-map creado y sobre él, aplicamos la inspección de tráfico:

ciscoasa(config)# policy-map PM-ServidoresWeb
ciscoasa(config-pmap)# class CM-ServidoresWeb
ciscoasa(config-pmap-c)# inspect http HTTP_PHP_CGI

4. Finalmente, aplicamos mediante un service-policy, el nuevo policy-map a la interfaz:

ciscoasa(config)# service-policy PM-ServidoresWeb interface outside

Como podemos ver, gracias a MPF podemos usar funcionalidades de IPS a nuestro firewall; esperamos poder preparar algún post más sobre MPF próximamente.