Introducción a honggfuzz
honggfuzz es un fuzzer basado en la cobertura de código desarrollada por google, que mantiene el ritmo de afl y libfuzzer. También es una herramienta de fuzz impulsada por retroalimentación muy eficiente .
Proyecto | Honggfuzz |
---|---|
Dirección del proyecto | https://github.com/google/honggfuzz |
Desarrollador | |
Ya sea para actualizar | Seguir actualizando |
características de honggfuzz
- Multiproceso y multiproceso , por lo que el fuzz es muy rápido
- Admite persistente fuzz (persistente fuzzing) , el proceso de llamar a la API para fuzzing repetido durante mucho tiempo
- Fácil de usar, facilítelo a un catálogo de corpus simple (incluso puede estar vacío para pruebas de fuzz basadas en retroalimentación), evolucionará gradualmente y lo ampliará utilizando métricas de cobertura basadas en retroalimentación
- Utilice la interfaz subyacente para monitorear el proceso , y es más probable que encuentre e informe señales secuestradas e ignoradas por el bloqueo
- Admite múltiples modos fuzz (basados en hardware (CPU: conteo de sucursales / instrucciones, Intel BTS, Intel PT) y modo fuzzy basado en retroalimentación basado en software) (más que otros fuzzers basados en retroalimentación basados en cobertura)
Descargar proyecto
$ git clone https://github.com/google/honggfuzz
Compilar e instalar
$ make
$ sudo make install
Análisis práctico
La demostración de prueba es la siguiente (se puede comparar con afl: la guía de prueba difusa AFL de la herramienta Fuzzer clásica ), aquí para reflejar la función de instrumentación de afl, escribí específicamente algunas ramas si, y en la profundidad de la rama, se producirá un desbordamiento de la pila
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/fcntl.h>
int main(int argc, char const *argv[])
{
if(argc != 2)
{
printf("null args!\n");
return -1;
}
/* Get file state */
struct stat fstat;
if(stat(argv[1], &fstat))
{
printf("Failed ^_^\n");
return -1;
}
/* Open file */
FILE * fd = NULL;
fd = open(argv[1], O_RDONLY);
if(fd == -1)
{
printf("open file failed!\n");
return -1;
}
/* Select */
char buf[15];
if(read(fd, buf, 2) == -1)
{
printf("read failed!");
return -1;
}
if(buf[0] == 'a' && buf[1] == 'b')
{
if(read(fd, buf, 4) != -1)
{
if(buf[2] == 's')
{
read(fd, buf, fstat.st_size - 6);
printf("%s\n", buf);
}
}
}
return 0;
}
Si el código anterior llega al punto más profundo, es muy probable que se desborde la pila. Cuando el primer carácter ingresado por el usuario es a, el segundo carácter es b y el quinto carácter es s, la condición se cumple. Nuestro objetivo es dar solo un caso de uso que se ajuste al formato (semilla original, aquí hay un caso de prueba que permite que el programa se ejecute, es decir, una cadena). La herramienta fuzz se mutará automáticamente para generar más casos de prueba, buscando si el código puede ir a diferentes ramas (similar a la fuerza bruta).
Instrumentación de código fuente
hfuzz-clang hfuzzDemo.c -o hfuzzDemo
Cada instrucción if representa cada rama condicional, y lo que aparece en la ventana de desmontaje de IDA es un bloque básico. Una instrucción if es una nueva rama. Como se muestra a continuación, usamos hfuz-clang para compilar el código de desensamblaje. En cada instrucción if, se ha instrumentado automáticamente. Es _sanitizer_cov_trace_const
una función de instrumentación que se utiliza para registrar la contaminación. Esta es una opción de optimización que viene con el compilador LLVM y puede calcular aproximadamente la cobertura del código.
Generar un corpus
Cree un nuevo directorio en, cree un nuevo archivo en el directorio, escriba una semilla, y el algoritmo de mutación generará varios casos de prueba basados en esta mutación semilla y lo alimentará al programa, como escribir la siguiente información (de acuerdo con el código, cuando el primer carácter es un, el segundo Los caracteres son b, el quinto carácter es s, puede producirse un desbordamiento)
hello world
Comience a difuminar
honggfuzz -e txt -u -z -Q -i ./in -W ./result -- ./hgfuzzDemo ___FILE___
Análisis de parámetros
- e especifica la extensión del caso de prueba
- u Guardar todos los casos de prueba
- z Instrumentación del código fuente
- Q Imprimir la salida del programa bajo prueba
- i Corpus, es decir, la semilla, que es el caso de prueba original
- W directorio de trabajo
--
Separe honggfuzz del programa bajo prueba___FILE___
Los parámetros del programa bajo prueba utilizan marcadores de posición en lugar de nombres de archivo, similares a @@ en AFL
Ejecutar captura de pantalla
Análisis de resultados.
almacenar los resultados de directorio resultado, incluyendo el HONGGFUZZ.REPORT.TXT
bien de tal manera que los casos de prueba de choque
Q & A problemas
Pregunta uno:
linux/bfd.c:28:10: fatal error: bfd.h: No such file or directory
#include <bfd.h>
^~~~~~~
compilation terminated.
Makefile:259: recipe for target 'linux/bfd.o' failed
make: *** [linux/bfd.o] Error 1
Esto es porque no hay binutils-dev
apt-get install binutils-dev
Pregunta dos:
linux/unwind.c:27:10: fatal error: libunwind-ptrace.h: No such file or directory
#include <libunwind-ptrace.h>
^~~~~~~~~~~~~~~~~~~~
compilation terminated.
Makefile:259: recipe for target 'linux/unwind.o' failed
make: *** [linux/unwind.o] Error 1
Si se solicita el siguiente error, esto se debe a que no hay libunwind-dev
apt-get install libunwind-dev
Pregunta 3:
Ubuntu 18.0.4 se bloquea, por lo que el entorno de prueba es Kali
Resumen
En comparación con las herramientas tradicionales de fuzz, la mayor ventaja de honggfuzz es que el fuzzing es extremadamente rápido. Las ventajas de subprocesos múltiples y multiprocesos permiten a honggfuzz utilizar completamente los recursos de la CPU y mejorar en gran medida la tasa de detección de casos de prueba de choque. Aquí, el ejemplo que usamos, y el autor de la guía de la herramienta clásica formación de pelusa Fuzzer AFL ejemplo mencionado es el mismo, sin embargo,
Aquí utilicé un corpus hello world muy informal y rápidamente encontré el bloqueo ; en comparación con el AFL mencionado anteriormente, el autor configuró deliberadamente un caso de prueba que es muy similar al caso de prueba del bloqueo del programa * como el corpus original, que tomó mucho tiempo Solo se encontró crash *. Entonces, la eficiencia de honggfuzz es obvia.