Add unpickle_megolm_outbound fuzzer. Enable C harness support.

This commit is contained in:
Denis Kasak 2021-07-13 11:13:15 +00:00
parent 811e56a0f0
commit e06ac20558
3 changed files with 133 additions and 4 deletions

View file

@ -146,13 +146,13 @@ $(TEST_BINARIES): LDFLAGS += $(DEBUG_OPTIMIZE_FLAGS) -L$(BUILD_DIR)
$(FUZZER_OBJECTS): CFLAGS += $(FUZZER_OPTIMIZE_FLAGS)
$(FUZZER_OBJECTS): CXXFLAGS += $(FUZZER_OPTIMIZE_FLAGS)
$(FUZZER_BINARIES): CPPFLAGS += -Ifuzzers/include
$(FUZZER_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR)
$(FUZZER_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR) -lstdc++
$(FUZZER_ASAN_BINARIES): CPPFLAGS += -Ifuzzers/include
$(FUZZER_ASAN_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR)
$(FUZZER_ASAN_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR) -lstdc++
$(FUZZER_MSAN_BINARIES): CPPFLAGS += -Ifuzzers/include
$(FUZZER_MSAN_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR)
$(FUZZER_MSAN_BINARIES): LDFLAGS += $(FUZZER_OPTIMIZE_FLAGS) -L$(BUILD_DIR) -lstdc++
$(FUZZER_DEBUG_BINARIES): CPPFLAGS += -Ifuzzers/include
$(FUZZER_DEBUG_BINARIES): LDFLAGS += $(DEBUG_OPTIMIZE_FLAGS)
$(FUZZER_DEBUG_BINARIES): LDFLAGS += $(DEBUG_OPTIMIZE_FLAGS) -lstdc++
$(JS_OBJECTS): CFLAGS += $(JS_OPTIMIZE_FLAGS)
$(JS_OBJECTS): CXXFLAGS += $(JS_OPTIMIZE_FLAGS)

View file

@ -0,0 +1,28 @@
#include <olm/outbound_group_session.h>
#include "fuzzing.h"
int main(int argc, const char *argv[]) {
if (argc != 1) {
printf("Usage: %s <input_file\n", argv[0]);
exit(3);
}
void *session_buffer = malloc(olm_outbound_group_session_size());
OlmOutboundGroupSession *session = olm_outbound_group_session(session_buffer);
int pickle_fd = STDIN_FILENO;
uint8_t *pickle_buffer;
ssize_t pickle_length = check_errno("Error reading message file",
read_file(pickle_fd, &pickle_buffer));
check_outbound_group_session(
session, "Error unpickling outbound group session",
olm_unpickle_outbound_group_session(session, "", 0, pickle_buffer,
pickle_length));
free(session_buffer);
free(pickle_buffer);
return EXIT_SUCCESS;
}

101
fuzzers/include/fuzzing.h Normal file
View file

@ -0,0 +1,101 @@
#include "olm/olm.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <stddef.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#define OLM_FUZZING 1
ssize_t read_file(
int fd,
uint8_t **buffer
) {
size_t buffer_size = 1;
size_t buffer_pos = 0;
uint8_t * current_buffer = (uint8_t *) malloc(buffer_size);
if (!current_buffer) return -1;
while (1) {
ssize_t count = read(
fd, current_buffer + buffer_pos, buffer_size - buffer_pos
);
if (count < 0) break; // A read error happened, so just fail immediately.
if (count == 0) {
// Nothing more left to read. We downsize the buffer to fit the
// data exactly, unless no data was read at all, in which case we
// skip the downsizing.
if (buffer_pos != 0) {
current_buffer = (uint8_t *) realloc(current_buffer, buffer_pos);
if (!current_buffer) break;
}
// The read was successful so we return the allocated buffer.
*buffer = current_buffer;
return buffer_pos;
}
buffer_pos += count;
// We've reached capacity, so enlarge the buffer.
if (buffer_pos == buffer_size) {
buffer_size *= 2;
uint8_t * new_buffer = (uint8_t *) realloc(current_buffer, buffer_size);
if (!new_buffer) break;
current_buffer = new_buffer;
}
}
free(current_buffer);
return -1;
}
ssize_t check_errno(
const char * message,
ssize_t value
) {
if (value == (ssize_t)-1) {
perror(message);
exit(1);
}
return value;
}
size_t check_error(
const char * message,
const char * olm_message,
size_t value
) {
if (value == olm_error()) {
(void)write(STDERR_FILENO, message, strlen(message));
(void)write(STDERR_FILENO, ": ", 2);
(void)write(STDERR_FILENO, olm_message, strlen(olm_message));
(void)write(STDERR_FILENO, "\n", 1);
exit(2);
}
return value;
}
size_t check_session(
OlmSession * session,
const char * message,
size_t value
) {
return check_error(message, olm_session_last_error(session), value);
}
size_t check_outbound_group_session(
OlmOutboundGroupSession * session,
const char * message,
size_t value
) {
return check_error(message, olm_outbound_group_session_last_error(session), value);
}