diff --git a/fuzz/.gitignore b/fuzz/.gitignore index 99ebd93bc..b8da0a0c9 100644 --- a/fuzz/.gitignore +++ b/fuzz/.gitignore @@ -1,7 +1,8 @@ fuzz_certs fuzz_crls +fuzz_ids +fuzz_ike fuzz_ocsp_req fuzz_ocsp_rsp -fuzz_ids fuzz_pa_tnc fuzz_pb_tnc diff --git a/fuzz/Makefile.am b/fuzz/Makefile.am index 60510474a..f42e887a8 100644 --- a/fuzz/Makefile.am +++ b/fuzz/Makefile.am @@ -1,5 +1,6 @@ AM_CPPFLAGS = @CPPFLAGS@ \ @FUZZING_CFLAGS@ \ + -I$(top_srcdir)/src/libcharon \ -I$(top_srcdir)/src/libstrongswan \ -I$(top_srcdir)/src/libimcv \ -I$(top_srcdir)/src/libtncif \ @@ -25,8 +26,12 @@ pb_tnc_ldflags = \ $(top_builddir)/src/libtncif/.libs/libtncif.a \ $(fuzz_ldflags) +ike_ldflags = \ + $(top_builddir)/src/libcharon/.libs/libcharon.a \ + $(fuzz_ldflags) + FUZZ_TARGETS=fuzz_certs fuzz_crls fuzz_ocsp_req fuzz_ocsp_rsp \ - fuzz_ids fuzz_pa_tnc fuzz_pb_tnc + fuzz_ids fuzz_pa_tnc fuzz_pb_tnc fuzz_ike all-local: $(FUZZ_TARGETS) @@ -53,6 +58,9 @@ fuzz_pa_tnc: fuzz_pa_tnc.c ${libfuzzer} fuzz_pb_tnc: fuzz_pb_tnc.c ${libfuzzer} $(CC) $(AM_CPPFLAGS) $(CFLAGS) -o $@ $< $(pb_tnc_ldflags) +fuzz_ike: fuzz_ike.c ${libfuzzer} + $(CC) $(AM_CPPFLAGS) $(CFLAGS) -o $@ $< $(ike_ldflags) + noinst_LIBRARIES = libFuzzerLocal.a libFuzzerLocal_a_SOURCES = libFuzzerLocal.c libFuzzerLocal_a_LIBADD = $(top_builddir)/src/libstrongswan/libstrongswan.la @@ -60,7 +68,8 @@ libFuzzerLocal_a_LIBADD = $(top_builddir)/src/libstrongswan/libstrongswan.la check: all for f in $(FUZZ_TARGETS); do \ corpus=$${f#fuzz_}; \ - ./$$f $(FUZZING_CORPORA)/$${corpus}/* || exit 1; \ - crashes=$(FUZZING_CORPORA)/$${corpus}-crash; \ + initial=$(FUZZING_CORPORA)/$${corpus}; \ + crashes=$${initial}-crash; \ + test ! -d $${initial} || ./$$f $${initial}/* || exit 1; \ test ! -d $${crashes} || ./$$f $${crashes}/* || exit 1; \ done diff --git a/fuzz/fuzz_ike.c b/fuzz/fuzz_ike.c new file mode 100644 index 000000000..77010c1dd --- /dev/null +++ b/fuzz/fuzz_ike.c @@ -0,0 +1,58 @@ +/* + * Copyright (C) 2026 Arthur SC Chan + * + * Copyright (C) secunet Security Networks AG + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. See . + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * for more details. + */ + +#include +#include + +int LLVMFuzzerInitialize(int *argc, char ***argv) +{ + dbg_default_set_level(-1); + library_init(NULL, "fuzz_ike"); + return 0; +} + +int LLVMFuzzerTestOneInput(const uint8_t *buf, size_t len) +{ + message_t *message; + packet_t *packet; + + /* Minimum IKE header size for fuzzing meaningful IKE headers effectively */ + if (len < 28) + { + return 0; + } + + /* Create packet from fuzzer input */ + packet = packet_create_from_data(host_create_from_string("192.0.2.1", 500), + host_create_from_string("192.0.2.2", 500), + chunk_clone(chunk_create((u_char*)buf, len))); + if (!packet) + { + return 0; + } + + /* Fuzz IKE message parsing and processing */ + message = message_create_from_packet(packet); + if (message) + { + if (message->parse_header(message) == SUCCESS) + { + message->parse_body(message, NULL); + } + message->destroy(message); + } + return 0; +}