mirror of
https://github.com/clearml/dropbear
synced 2025-03-03 10:41:39 +00:00
Fix to be able to compile normal(ish) binaries with --enable-fuzz
--HG-- branch : fuzz
This commit is contained in:
parent
c658b275fd
commit
5f2447edbb
26
Makefile.in
26
Makefile.in
@ -61,14 +61,22 @@ CONVERTOBJS=dropbearconvert.o keyimport.o
|
|||||||
SCPOBJS=scp.o progressmeter.o atomicio.o scpmisc.o compat.o
|
SCPOBJS=scp.o progressmeter.o atomicio.o scpmisc.o compat.o
|
||||||
|
|
||||||
ifeq (@DROPBEAR_FUZZ@, 1)
|
ifeq (@DROPBEAR_FUZZ@, 1)
|
||||||
COMMONOBJS += fuzz-common.o fuzz-wrapfd.o
|
allobjs = $(COMMONOBJS) fuzz-common.o fuzz-wrapfd.o $(CLISVROBJS) $(CLIOBJS) $(SVROBJS)
|
||||||
endif
|
allobjs:=$(subst svr-main.o, ,$(allobjs))
|
||||||
|
allobjs:=$(subst cli-main.o, ,$(allobjs))
|
||||||
|
allobjs:=$(sort $(allobjs))
|
||||||
|
|
||||||
dropbearobjs=$(COMMONOBJS) $(CLISVROBJS) $(SVROBJS)
|
dropbearobjs=$(allobjs) svr-main.o
|
||||||
dbclientobjs=$(COMMONOBJS) $(CLISVROBJS) $(CLIOBJS)
|
dbclientobjs=$(allobjs) cli-main.o
|
||||||
dropbearkeyobjs=$(COMMONOBJS) $(KEYOBJS)
|
dropbearkeyobjs=$(allobjs) $(KEYOBJS)
|
||||||
dropbearconvertobjs=$(COMMONOBJS) $(CONVERTOBJS)
|
dropbearconvertobjs=$(allobjs) $(CONVERTOBJS)
|
||||||
scpobjs=$(SCPOBJS)
|
else
|
||||||
|
dropbearobjs=$(COMMONOBJS) $(CLISVROBJS) $(SVROBJS)
|
||||||
|
dbclientobjs=$(COMMONOBJS) $(CLISVROBJS) $(CLIOBJS)
|
||||||
|
dropbearkeyobjs=$(COMMONOBJS) $(KEYOBJS)
|
||||||
|
dropbearconvertobjs=$(COMMONOBJS) $(CONVERTOBJS)
|
||||||
|
scpobjs=$(SCPOBJS)
|
||||||
|
endif
|
||||||
|
|
||||||
VPATH=@srcdir@
|
VPATH=@srcdir@
|
||||||
srcdir=@srcdir@
|
srcdir=@srcdir@
|
||||||
@ -185,7 +193,7 @@ dbclient: $(HEADERS) $(LIBTOM_DEPS) Makefile
|
|||||||
$(CC) $(LDFLAGS) -o $@$(EXEEXT) $($@objs) $(LIBTOM_LIBS) $(LIBS)
|
$(CC) $(LDFLAGS) -o $@$(EXEEXT) $($@objs) $(LIBTOM_LIBS) $(LIBS)
|
||||||
|
|
||||||
dropbearkey dropbearconvert: $(HEADERS) $(LIBTOM_DEPS) Makefile
|
dropbearkey dropbearconvert: $(HEADERS) $(LIBTOM_DEPS) Makefile
|
||||||
$(CC) $(LDFLAGS) -o $@$(EXEEXT) $($@objs) $(LIBTOM_LIBS)
|
$(CC) $(LDFLAGS) -o $@$(EXEEXT) $($@objs) $(LIBTOM_LIBS) $(LIBS)
|
||||||
|
|
||||||
# scp doesn't use the libs so is special.
|
# scp doesn't use the libs so is special.
|
||||||
scp: $(SCPOBJS) $(HEADERS) Makefile
|
scp: $(SCPOBJS) $(HEADERS) Makefile
|
||||||
@ -260,7 +268,7 @@ fuzzstandalone: fuzz-harness.o fuzz-targets
|
|||||||
svrfuzzobjs=$(subst svr-main.o, ,$(dropbearobjs))
|
svrfuzzobjs=$(subst svr-main.o, ,$(dropbearobjs))
|
||||||
|
|
||||||
# build all the fuzzers. This will require fail to link unless built with
|
# build all the fuzzers. This will require fail to link unless built with
|
||||||
# make fuzzers LIBS=-lFuzzer.a
|
# make fuzz-targetsk FUZZLIB=-lFuzzer.a
|
||||||
# or similar - the library provides main().
|
# or similar - the library provides main().
|
||||||
fuzz-targets: $(FUZZ_TARGETS) $(FUZZER_OPTIONS)
|
fuzz-targets: $(FUZZ_TARGETS) $(FUZZER_OPTIONS)
|
||||||
|
|
||||||
|
@ -323,7 +323,7 @@ AC_ARG_ENABLE(shadow,
|
|||||||
)
|
)
|
||||||
|
|
||||||
AC_ARG_ENABLE(fuzz,
|
AC_ARG_ENABLE(fuzz,
|
||||||
[ --enable-fuzz Build fuzzing],
|
[ --enable-fuzz Build fuzzing. Not recommended for deployment.],
|
||||||
[
|
[
|
||||||
AC_DEFINE(DROPBEAR_FUZZ, 1, Fuzzing)
|
AC_DEFINE(DROPBEAR_FUZZ, 1, Fuzzing)
|
||||||
AC_MSG_NOTICE(Enabling fuzzing)
|
AC_MSG_NOTICE(Enabling fuzzing)
|
||||||
|
2
dbutil.c
2
dbutil.c
@ -121,7 +121,7 @@ static void generic_dropbear_exit(int exitcode, const char* format,
|
|||||||
_dropbear_log(LOG_INFO, fmtbuf, param);
|
_dropbear_log(LOG_INFO, fmtbuf, param);
|
||||||
|
|
||||||
#if DROPBEAR_FUZZ
|
#if DROPBEAR_FUZZ
|
||||||
// longjmp before cleaning up svr_opts
|
/* longjmp before cleaning up svr_opts */
|
||||||
if (fuzz.do_jmp) {
|
if (fuzz.do_jmp) {
|
||||||
longjmp(fuzz.jmp, 1);
|
longjmp(fuzz.jmp, 1);
|
||||||
}
|
}
|
||||||
|
@ -154,13 +154,15 @@ int fuzz_run_preauth(const uint8_t *Data, size_t Size, int skip_kexmaths) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// get prefix. input format is
|
/*
|
||||||
// string prefix
|
get prefix. input format is
|
||||||
// uint32 wrapfd seed
|
string prefix
|
||||||
// ... to be extended later
|
uint32 wrapfd seed
|
||||||
// [bytes] ssh input stream
|
... to be extended later
|
||||||
|
[bytes] ssh input stream
|
||||||
|
*/
|
||||||
|
|
||||||
// be careful to avoid triggering buffer.c assertions
|
/* be careful to avoid triggering buffer.c assertions */
|
||||||
if (fuzz.input->len < 8) {
|
if (fuzz.input->len < 8) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -181,7 +183,7 @@ int fuzz_run_preauth(const uint8_t *Data, size_t Size, int skip_kexmaths) {
|
|||||||
} else {
|
} else {
|
||||||
m_malloc_free_epoch(1, 1);
|
m_malloc_free_epoch(1, 1);
|
||||||
TRACE(("dropbear_exit longjmped"))
|
TRACE(("dropbear_exit longjmped"))
|
||||||
// dropbear_exit jumped here
|
/* dropbear_exit jumped here */
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -19,7 +19,7 @@ int main(int argc, char ** argv) {
|
|||||||
|
|
||||||
for (i = 1; i < argc; i++) {
|
for (i = 1; i < argc; i++) {
|
||||||
if (argv[i][0] == '-') {
|
if (argv[i][0] == '-') {
|
||||||
// ignore arguments
|
/* ignore arguments */
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,7 +21,7 @@ struct fdwrap {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static struct fdwrap wrap_fds[IOWRAP_MAXFD+1];
|
static struct fdwrap wrap_fds[IOWRAP_MAXFD+1];
|
||||||
// for quick selection of in-use descriptors
|
/* for quick selection of in-use descriptors */
|
||||||
static int wrap_used[IOWRAP_MAXFD+1];
|
static int wrap_used[IOWRAP_MAXFD+1];
|
||||||
static unsigned int nused;
|
static unsigned int nused;
|
||||||
static unsigned short rand_state[3];
|
static unsigned short rand_state[3];
|
||||||
@ -66,7 +66,7 @@ void wrapfd_remove(int fd) {
|
|||||||
wrap_fds[fd].mode = UNUSED;
|
wrap_fds[fd].mode = UNUSED;
|
||||||
|
|
||||||
|
|
||||||
// remove from used list
|
/* remove from used list */
|
||||||
for (i = 0, j = 0; i < nused; i++) {
|
for (i = 0, j = 0; i < nused; i++) {
|
||||||
if (wrap_used[i] != fd) {
|
if (wrap_used[i] != fd) {
|
||||||
wrap_used[j] = wrap_used[i];
|
wrap_used[j] = wrap_used[i];
|
||||||
@ -94,7 +94,7 @@ int wrapfd_read(int fd, void *out, size_t count) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (fd < 0 || fd > IOWRAP_MAXFD || wrap_fds[fd].mode == UNUSED) {
|
if (fd < 0 || fd > IOWRAP_MAXFD || wrap_fds[fd].mode == UNUSED) {
|
||||||
// XXX - assertion failure?
|
/* XXX - assertion failure? */
|
||||||
TRACE(("Bad read descriptor %d\n", fd))
|
TRACE(("Bad read descriptor %d\n", fd))
|
||||||
errno = EBADF;
|
errno = EBADF;
|
||||||
return -1;
|
return -1;
|
||||||
@ -116,7 +116,7 @@ int wrapfd_read(int fd, void *out, size_t count) {
|
|||||||
buf = wrap_fds[fd].buf;
|
buf = wrap_fds[fd].buf;
|
||||||
if (buf) {
|
if (buf) {
|
||||||
maxread = MIN(buf->len - buf->pos, count);
|
maxread = MIN(buf->len - buf->pos, count);
|
||||||
// returns 0 if buf is EOF, as intended
|
/* returns 0 if buf is EOF, as intended */
|
||||||
if (maxread > 0) {
|
if (maxread > 0) {
|
||||||
maxread = nrand48(rand_state) % maxread + 1;
|
maxread = nrand48(rand_state) % maxread + 1;
|
||||||
}
|
}
|
||||||
@ -140,7 +140,7 @@ int wrapfd_write(int fd, const void* in, size_t count) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (fd < 0 || fd > IOWRAP_MAXFD || wrap_fds[fd].mode == UNUSED) {
|
if (fd < 0 || fd > IOWRAP_MAXFD || wrap_fds[fd].mode == UNUSED) {
|
||||||
// XXX - assertion failure?
|
/* XXX - assertion failure? */
|
||||||
TRACE(("Bad read descriptor %d\n", fd))
|
TRACE(("Bad read descriptor %d\n", fd))
|
||||||
errno = EBADF;
|
errno = EBADF;
|
||||||
return -1;
|
return -1;
|
||||||
@ -148,7 +148,7 @@ int wrapfd_write(int fd, const void* in, size_t count) {
|
|||||||
|
|
||||||
assert(count != 0);
|
assert(count != 0);
|
||||||
|
|
||||||
// force read to exercise sanitisers
|
/* force read to exercise sanitisers */
|
||||||
for (i = 0; i < count; i++) {
|
for (i = 0; i < count; i++) {
|
||||||
(void)volin[i];
|
(void)volin[i];
|
||||||
}
|
}
|
||||||
@ -186,7 +186,7 @@ int wrapfd_select(int nfds, fd_set *readfds, fd_set *writefds,
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// read
|
/* read */
|
||||||
if (readfds != NULL && erand48(rand_state) < CHANCE_READ1) {
|
if (readfds != NULL && erand48(rand_state) < CHANCE_READ1) {
|
||||||
for (i = 0, nset = 0; i < nfds; i++) {
|
for (i = 0, nset = 0; i < nfds; i++) {
|
||||||
if (FD_ISSET(i, readfds)) {
|
if (FD_ISSET(i, readfds)) {
|
||||||
@ -198,7 +198,7 @@ int wrapfd_select(int nfds, fd_set *readfds, fd_set *writefds,
|
|||||||
FD_ZERO(readfds);
|
FD_ZERO(readfds);
|
||||||
|
|
||||||
if (nset > 0) {
|
if (nset > 0) {
|
||||||
// set one
|
/* set one */
|
||||||
sel = fdlist[nrand48(rand_state) % nset];
|
sel = fdlist[nrand48(rand_state) % nset];
|
||||||
FD_SET(sel, readfds);
|
FD_SET(sel, readfds);
|
||||||
ret++;
|
ret++;
|
||||||
@ -213,7 +213,7 @@ int wrapfd_select(int nfds, fd_set *readfds, fd_set *writefds,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// write
|
/* write */
|
||||||
if (writefds != NULL && erand48(rand_state) < CHANCE_WRITE1) {
|
if (writefds != NULL && erand48(rand_state) < CHANCE_WRITE1) {
|
||||||
for (i = 0, nset = 0; i < nfds; i++) {
|
for (i = 0, nset = 0; i < nfds; i++) {
|
||||||
if (FD_ISSET(i, writefds)) {
|
if (FD_ISSET(i, writefds)) {
|
||||||
@ -224,7 +224,7 @@ int wrapfd_select(int nfds, fd_set *readfds, fd_set *writefds,
|
|||||||
}
|
}
|
||||||
FD_ZERO(writefds);
|
FD_ZERO(writefds);
|
||||||
|
|
||||||
// set one
|
/* set one */
|
||||||
if (nset > 0) {
|
if (nset > 0) {
|
||||||
sel = fdlist[nrand48(rand_state) % nset];
|
sel = fdlist[nrand48(rand_state) % nset];
|
||||||
FD_SET(sel, writefds);
|
FD_SET(sel, writefds);
|
||||||
|
1
fuzz.h
1
fuzz.h
@ -2,6 +2,7 @@
|
|||||||
#define DROPBEAR_FUZZ_H
|
#define DROPBEAR_FUZZ_H
|
||||||
|
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
|
||||||
#if DROPBEAR_FUZZ
|
#if DROPBEAR_FUZZ
|
||||||
|
|
||||||
#include "includes.h"
|
#include "includes.h"
|
||||||
|
@ -20,14 +20,14 @@ int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
|
|||||||
|
|
||||||
m_malloc_set_epoch(1);
|
m_malloc_set_epoch(1);
|
||||||
|
|
||||||
// choose a keytype based on input
|
/* choose a keytype based on input */
|
||||||
uint8_t b = 0;
|
uint8_t b = 0;
|
||||||
size_t i;
|
size_t i;
|
||||||
for (i = 0; i < Size; i++) {
|
for (i = 0; i < Size; i++) {
|
||||||
b ^= Data[i];
|
b ^= Data[i];
|
||||||
}
|
}
|
||||||
const char* algoname = fuzz_signkey_names[b%DROPBEAR_SIGNKEY_NUM_NAMED];
|
const char* algoname = fuzz_signkey_names[b%DROPBEAR_SIGNKEY_NUM_NAMED];
|
||||||
const char* keyblob = "blob"; // keep short
|
const char* keyblob = "blob"; /* keep short */
|
||||||
|
|
||||||
if (setjmp(fuzz.jmp) == 0) {
|
if (setjmp(fuzz.jmp) == 0) {
|
||||||
fuzz_checkpubkey_line(fuzz.input, 5, "/home/me/authorized_keys",
|
fuzz_checkpubkey_line(fuzz.input, 5, "/home/me/authorized_keys",
|
||||||
@ -37,7 +37,7 @@ int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
|
|||||||
} else {
|
} else {
|
||||||
m_malloc_free_epoch(1, 1);
|
m_malloc_free_epoch(1, 1);
|
||||||
TRACE(("dropbear_exit longjmped"))
|
TRACE(("dropbear_exit longjmped"))
|
||||||
// dropbear_exit jumped here
|
/* dropbear_exit jumped here */
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -57,7 +57,7 @@ int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) {
|
|||||||
} else {
|
} else {
|
||||||
m_malloc_free_epoch(1, 1);
|
m_malloc_free_epoch(1, 1);
|
||||||
TRACE(("dropbear_exit longjmped"))
|
TRACE(("dropbear_exit longjmped"))
|
||||||
// dropbear_exit jumped here
|
/* dropbear_exit jumped here */
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
8
packet.c
8
packet.c
@ -79,8 +79,8 @@ void write_packet() {
|
|||||||
it's likely to be necessary */
|
it's likely to be necessary */
|
||||||
#if DROPBEAR_FUZZ
|
#if DROPBEAR_FUZZ
|
||||||
if (fuzz.fuzzing) {
|
if (fuzz.fuzzing) {
|
||||||
// pretend to write one packet at a time
|
/* pretend to write one packet at a time */
|
||||||
// TODO(fuzz): randomise amount written based on the fuzz input
|
/* TODO(fuzz): randomise amount written based on the fuzz input */
|
||||||
written = iov[0].iov_len;
|
written = iov[0].iov_len;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -368,8 +368,8 @@ static int checkmac() {
|
|||||||
|
|
||||||
#if DROPBEAR_FUZZ
|
#if DROPBEAR_FUZZ
|
||||||
if (fuzz.fuzzing) {
|
if (fuzz.fuzzing) {
|
||||||
// fail 1 in 2000 times to test error path.
|
/* fail 1 in 2000 times to test error path.
|
||||||
// note that mac_bytes is all zero prior to kex, so don't test ==0 !
|
note that mac_bytes is all zero prior to kex, so don't test ==0 ! */
|
||||||
unsigned int value = *((unsigned int*)&mac_bytes);
|
unsigned int value = *((unsigned int*)&mac_bytes);
|
||||||
if (value % 2000 == 99) {
|
if (value % 2000 == 99) {
|
||||||
return DROPBEAR_FAILURE;
|
return DROPBEAR_FAILURE;
|
||||||
|
@ -186,7 +186,7 @@ void svr_dropbear_exit(int exitcode, const char* format, va_list param) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#if DROPBEAR_FUZZ
|
#if DROPBEAR_FUZZ
|
||||||
// longjmp before cleaning up svr_opts
|
/* longjmp before cleaning up svr_opts */
|
||||||
if (fuzz.do_jmp) {
|
if (fuzz.do_jmp) {
|
||||||
longjmp(fuzz.jmp, 1);
|
longjmp(fuzz.jmp, 1);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user