From 8d40570979a3cb12b478dc35c59d14bc0d4e6219 Mon Sep 17 00:00:00 2001 From: Sam Hocevar Date: Fri, 5 Jan 2007 07:52:30 +0000 Subject: [PATCH] * Network support. --- doc/zzuf.1 | 13 +++++++------ src/libzzuf.c | 5 +++++ src/libzzuf.h | 1 + src/load-fd.c | 44 ++++++++++++++++++++++++++++++++++++++++++++ src/zzuf.c | 18 ++++++++++++------ 5 files changed, 69 insertions(+), 12 deletions(-) diff --git a/doc/zzuf.1 b/doc/zzuf.1 index 85c592a..30eeef0 100644 --- a/doc/zzuf.1 +++ b/doc/zzuf.1 @@ -2,13 +2,13 @@ .SH NAME zzuf \- multiple purpose fuzzer .SH SYNOPSIS -\fBzzuf\fR [\fB\-cdiqS\fR] [\fB\-r\fR \fIratio\fR] [\fB\-s\fR \fIseed\fR | \fB\-s\fR \fIstart:stop\fR] +\fBzzuf\fR [\fB\-cdiNqS\fR] [\fB\-r\fR \fIratio\fR] [\fB\-s\fR \fIseed\fR | \fB\-s\fR \fIstart:stop\fR] .br - [\fB\-F\fR \fIchildren\fR] [\fB\-B\fR \fIbytes\fR] [\fB\-T\fR \fIseconds\fR] + [\fB\-F\fR \fIchildren\fR] [\fB\-B\fR \fIbytes\fR] [\fB\-T\fR \fIseconds\fR] .br - [\fB\-P\fR \fIlist\fR] [\fB\-R\fR \fIlist\fR] + [\fB\-P\fR \fIlist\fR] [\fB\-R\fR \fIlist\fR] .br - [\fB\-I\fR \fIinclude\fR] [\fB\-E\fR \fIexclude\fR] \fIPROGRAM\fR [\fIARGS\fR]... + [\fB\-I\fR \fIinclude\fR] [\fB\-E\fR \fIexclude\fR] \fIPROGRAM\fR [\fIARGS\fR]... .br \fBzzuf \-h\fR | \fB\-\-help\fR .br @@ -77,6 +77,9 @@ and you only want specific files to be fuzzed. Multiple \fB\-I\fR flags can be specified, in which case files matching any one of the regular expressions will be fuzzed. See also the \fB\-c\fR flag. .TP +\fB\-N\fR, \fB\-\-network\fR +Fuzz the application's network input. By default \fBzzuf\fR only fuzzes files. +.TP \fB\-P\fR, \fB\-\-protect\fR=\fIlist\fR Protect a list of characters so that if they appear in input data that would normally be fuzzed, they are left unmodified instead. @@ -220,8 +223,6 @@ processes, it will fail in the presence of any mechanism that disables preloading. For instance setuid root binaries will not be fuzzed when run as an unprivileged user. This limitation will probably not be addressed. .PP -Network fuzzing is not implemented. This feature will be added. -.PP It is not yet possible to insert or drop bytes from the input, to fuzz according to the file format, or to do all these complicated operations. These features are planned. diff --git a/src/libzzuf.c b/src/libzzuf.c index 2ab094e..3c3ae85 100644 --- a/src/libzzuf.c +++ b/src/libzzuf.c @@ -45,6 +45,7 @@ int _zz_hasdebug = 0; float _zz_ratio = 0.004f; int _zz_seed = 0; int _zz_signal = 0; +int _zz_network = 0; /* Global tables */ int _zz_protect[256]; @@ -106,6 +107,10 @@ void _zz_init(void) if(tmp && *tmp == '1') _zz_signal = 1; + tmp = getenv("ZZUF_NETWORK"); + if(tmp && *tmp == '1') + _zz_network = 1; + _zz_fd_init(); tmp = getenv("ZZUF_STDIN"); diff --git a/src/libzzuf.h b/src/libzzuf.h index b23d61a..dacd02c 100644 --- a/src/libzzuf.h +++ b/src/libzzuf.h @@ -38,6 +38,7 @@ extern int _zz_hasdebug; extern float _zz_ratio; extern int _zz_seed; extern int _zz_signal; +extern int _zz_network; /* Internal tables TODO: merge them and use bitmasks */ extern int _zz_protect[256]; diff --git a/src/load-fd.c b/src/load-fd.c index 0f8e31f..00cc554 100644 --- a/src/load-fd.c +++ b/src/load-fd.c @@ -32,6 +32,7 @@ #include #include +#include #include #include #include @@ -46,6 +47,9 @@ static int (*open_orig) (const char *file, int oflag, ...); #ifdef HAVE_OPEN64 static int (*open64_orig) (const char *file, int oflag, ...); #endif +static int (*accept_orig) (int sockfd, struct sockaddr *addr, + socklen_t *addrlen); +static int (*socket_orig) (int domain, int type, int protocol); static ssize_t (*read_orig) (int fd, void *buf, size_t count); static off_t (*lseek_orig) (int fd, off_t offset, int whence); #ifdef HAVE_LSEEK64 @@ -59,6 +63,8 @@ void _zz_load_fd(void) #ifdef HAVE_OPEN64 LOADSYM(open64); #endif + LOADSYM(accept); + LOADSYM(socket); LOADSYM(read); LOADSYM(lseek); #ifdef HAVE_LSEEK64 @@ -112,6 +118,44 @@ int open64(const char *file, int oflag, ...) } #endif +int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen) +{ + int ret; + + if(!_zz_ready) + LOADSYM(accept); + ret = accept_orig(sockfd, addr, addrlen); + if(!_zz_ready || _zz_disabled || !_zz_network) + return ret; + + if(ret >= 0) + { + debug("accept(%i, %p, %p) = %i", sockfd, addr, addrlen, ret); + _zz_register(ret); + } + + return ret; +} + +int socket(int domain, int type, int protocol) +{ + int ret; + + if(!_zz_ready) + LOADSYM(socket); + ret = socket_orig(domain, type, protocol); + if(!_zz_ready || _zz_disabled || !_zz_network) + return ret; + + if(ret >= 0) + { + debug("socket(%i, %i, %i) = %i", domain, type, protocol, ret); + _zz_register(ret); + } + + return ret; +} + ssize_t read(int fd, void *buf, size_t count) { int ret; diff --git a/src/zzuf.c b/src/zzuf.c index 1a16156..12d973e 100644 --- a/src/zzuf.c +++ b/src/zzuf.c @@ -110,6 +110,7 @@ int main(int argc, char *argv[]) { "help", 0, NULL, 'h' }, { "stdin", 0, NULL, 'i' }, { "include", 1, NULL, 'I' }, + { "network", 1, NULL, 'N' }, { "protect", 1, NULL, 'P' }, { "quiet", 0, NULL, 'q' }, { "ratio", 1, NULL, 'r' }, @@ -119,11 +120,11 @@ int main(int argc, char *argv[]) { "max-time", 1, NULL, 'T' }, { "version", 0, NULL, 'v' }, }; - int c = getopt_long(argc, argv, "B:cdE:F:hiI:P:qr:R:s:ST:v", + int c = getopt_long(argc, argv, "B:cdE:F:hiI:NP:qr:R:s:ST:v", long_options, &option_index); # else # define MOREINFO "Try `%s -h' for more information.\n" - int c = getopt(argc, argv, "B:cdE:F:hiI:P:qr:R:s:ST:v"); + int c = getopt(argc, argv, "B:cdE:F:hiI:NP:qr:R:s:ST:v"); # endif if(c == -1) break; @@ -152,6 +153,9 @@ int main(int argc, char *argv[]) case 'i': /* --stdin */ setenv("ZZUF_STDIN", "1", 1); break; + case 'N': /* --network */ + setenv("ZZUF_NETWORK", "1", 1); + break; case 's': /* --seed */ parser = strchr(optarg, ':'); seed = atoi(optarg); @@ -549,10 +553,10 @@ static void version(void) #if defined(HAVE_GETOPT_H) static void usage(void) { - printf("Usage: zzuf [ -cdiqS ] [ -r ratio ] [ -s seed | -s start:stop ]\n"); - printf(" [ -F children ] [ -B bytes ] [ -T seconds ]\n"); - printf(" [ -P protect ] [ -R refuse ]\n"); - printf(" [ -I include ] [ -E exclude ] COMMAND [ARGS]...\n"); + printf("Usage: zzuf [ -cdiNqS ] [ -r ratio ] [ -s seed | -s start:stop ]\n"); + printf(" [ -F children ] [ -B bytes ] [ -T seconds ]\n"); + printf(" [ -P protect ] [ -R refuse ]\n"); + printf(" [ -I include ] [ -E exclude ] COMMAND [ARGS]...\n"); printf(" zzuf -h\n"); printf(" zzuf -v\n"); printf("Run COMMAND and randomly fuzz its input.\n"); @@ -566,6 +570,7 @@ static void usage(void) printf(" -F, --fork number of concurrent children (default 1)\n"); printf(" -i, --stdin fuzz standard input\n"); printf(" -I, --include only fuzz files matching \n"); + printf(" -N, --network fuzz network input\n"); printf(" -P, --protect protect bytes and characters in \n"); printf(" -q, --quiet do not print children's messages\n"); printf(" -r, --ratio bit fuzzing ratio (default 0.004)\n"); @@ -584,6 +589,7 @@ static void usage(void) printf(" -F number of concurrent forks (default 1)\n"); printf(" -i fuzz standard input\n"); printf(" -I only fuzz files matching \n"); + printf(" -N fuzz network input\n"); printf(" -P protect bytes and characters in \n"); printf(" -q do not print the fuzzed application's messages\n"); printf(" -r bit fuzzing ratio (default 0.004)\n");