Browse Source

Add first version of fuzzer corpus generator

Stefan Profanter 7 years ago
parent
commit
816e0727dd
66 changed files with 754 additions and 6 deletions
  1. 13 0
      CMakeLists.txt
  2. 7 0
      src/server/ua_server_binary.c
  3. 10 6
      tests/fuzz/CMakeLists.txt
  4. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00001_hel.bin
  5. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00002_opn.bin
  6. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00003_msg_GetEndpointsRequest.bin
  7. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00004_msg_CreateSessionRequest.bin
  8. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00005_msg_ActivateSessionRequest.bin
  9. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00006_msg_FindServersRequest.bin
  10. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00007_msg_FindServersOnNetworkRequest.bin
  11. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00008_msg_RegisterServerRequest.bin
  12. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00009_msg_RegisterServer2Request.bin
  13. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00010_msg_BrowseRequest.bin
  14. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00011_msg_BrowseNextRequest.bin
  15. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00012_msg_BrowseNextRequest.bin
  16. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00013_msg_BrowseNextRequest.bin
  17. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00014_msg_RegisterNodesRequest.bin
  18. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00015_msg_UnregisterNodesRequest.bin
  19. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00016_msg_TranslateBrowsePathsToNodeIdsRequest.bin
  20. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00017_msg_CreateSubscriptionRequest.bin
  21. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00018_msg_ModifySubscriptionRequest.bin
  22. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00019_msg_SetPublishingModeRequest.bin
  23. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00020_msg_CreateMonitoredItemsRequest.bin
  24. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00021_msg_PublishRequest.bin
  25. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00022_msg_RepublishRequest.bin
  26. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00023_msg_ModifyMonitoredItemsRequest.bin
  27. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00024_msg_SetMonitoringModeRequest.bin
  28. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00025_msg_DeleteMonitoredItemsRequest.bin
  29. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00026_msg_DeleteSubscriptionsRequest.bin
  30. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00027_msg_CallRequest.bin
  31. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00028_msg_AddNodesRequest.bin
  32. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00029_msg_AddReferencesRequest.bin
  33. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00030_msg_DeleteReferencesRequest.bin
  34. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00031_msg_DeleteNodesRequest.bin
  35. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00032_msg_CloseSessionRequest.bin
  36. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00033_clo.bin
  37. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00034_hel.bin
  38. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00035_opn.bin
  39. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00036_msg_GetEndpointsRequest.bin
  40. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00037_msg_CreateSessionRequest.bin
  41. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00038_msg_ActivateSessionRequest.bin
  42. BIN
      tests/fuzz/fuzz_binary_message_corpus/generated/00039_clo.bin
  43. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/000_hello.bin
  44. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/010_open_secure_channel_request.bin
  45. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/015_get_endpoints_request.bin
  46. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/016_find_servers_on_network_request.bin
  47. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/017_find_servers_request.bin
  48. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/020_create_session_request.bin
  49. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/030_activate_session_request.bin
  50. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/035_register_server_2_request.bin
  51. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/040_read_request.bin
  52. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/050_browse_request.bin
  53. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/060_create_subscription_request.bin
  54. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/070_create_monitored_items_request.bin
  55. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/080_publish_request.bin
  56. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/090_read_request.bin
  57. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/100_write_request.bin
  58. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/110_delete_monitored_items_request.bin
  59. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/120_delete_subscriptions_request.bin
  60. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/130_translate_browse_paths_to_node_ids_request.bin
  61. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/140_call_request.bin
  62. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/150_call_request.bin
  63. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/160_close_session_request.bin
  64. BIN
      tests/fuzz/fuzz_binary_message_corpus/requests/170_close_secure_channel_request.bin
  65. 17 0
      tools/corpus_generator/CMakeLists.txt
  66. 707 0
      tools/corpus_generator/corpus_generator.c

+ 13 - 0
CMakeLists.txt

@@ -123,6 +123,13 @@ if(UA_BUILD_FUZZING)
     add_definitions(-DFUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION)
 endif()
 
+option(UA_BUILD_FUZZING_CORPUS "Build the fuzzing corpus" OFF)
+mark_as_advanced(UA_BUILD_FUZZING_CORPUS)
+if(UA_BUILD_FUZZING_CORPUS)
+    add_definitions(-DUA_DEBUG_DUMP_PKGS_FILE)
+    set(UA_ENABLE_TYPENAMES ON CACHE STRING "" FORCE)
+endif()
+
 option(UA_BUILD_OSS_FUZZ "Special build switch used in oss-fuzz" OFF)
 mark_as_advanced(UA_BUILD_OSS_FUZZ)
 
@@ -635,6 +642,12 @@ if(UA_BUILD_FUZZING OR UA_BUILD_OSS_FUZZ)
     add_subdirectory(tests/fuzz)
 endif()
 
+
+if(UA_BUILD_FUZZING_CORPUS)
+    add_subdirectory(tools/corpus_generator)
+endif()
+
+
 ############################
 # Linting run (clang-tidy) #
 ############################

+ 7 - 0
src/server/ua_server_binary.c

@@ -23,6 +23,10 @@ UA_NodeId unsafe_fuzz_authenticationToken = {
 };
 #endif
 
+#ifdef UA_DEBUG_DUMP_PKGS_FILE
+void UA_debug_dumpCompleteChunk(UA_Server *const server, UA_Connection *const connection, UA_ByteString *messageBuffer);
+#endif
+
 /********************/
 /* Helper Functions */
 /********************/
@@ -649,6 +653,9 @@ processCompleteChunk(void *const application,
                      UA_Connection *const connection,
                      UA_ByteString *const chunk) {
     UA_Server *const server = (UA_Server*)application;
+#ifdef UA_DEBUG_DUMP_PKGS_FILE
+    UA_debug_dumpCompleteChunk(server, connection, chunk);
+#endif
     if(!connection->channel)
         return processCompleteChunkWithoutChannel(server, connection, chunk);
     return UA_SecureChannel_processChunk(connection->channel, chunk,

+ 10 - 6
tests/fuzz/CMakeLists.txt

@@ -62,14 +62,18 @@ endmacro()
 add_fuzzer(fuzz_binary_message fuzz_binary_message.cc)
 add_fuzzer(fuzz_binary_decode fuzz_binary_decode.cc)
 
+file(GLOB CORPUS_FILES ${PROJECT_SOURCE_DIR}/tests/fuzz/fuzz_binary_message_corpus/generated/*.bin)
+
+set(CORPUS_CMDS)
+
+SET(CORPUS_CMDS "")
+FOREACH(f ${CORPUS_FILES})
+    LIST(APPEND CORPUS_CMDS COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message "${f}")
+ENDFOREACH(f)
+
 add_custom_target(
         run_fuzzer
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_Browse.bin
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_CLO.bin
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_CreateActivateSession.bin
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_HELOPN.bin
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_Read.bin
-        COMMAND ${CMAKE_RUNTIME_OUTPUT_DIRECTORY}/fuzz_binary_message ${CMAKE_CURRENT_SOURCE_DIR}/fuzz_binary_message_corpus/client_Write.bin
+        ${CORPUS_CMDS}
         WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
         DEPENDS ${FUZZER_TARGETS}
         ${MAYBE_USES_TERMINAL})

BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00001_hel.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00002_opn.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00003_msg_GetEndpointsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00004_msg_CreateSessionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00005_msg_ActivateSessionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00006_msg_FindServersRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00007_msg_FindServersOnNetworkRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00008_msg_RegisterServerRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00009_msg_RegisterServer2Request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00010_msg_BrowseRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00011_msg_BrowseNextRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00012_msg_BrowseNextRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00013_msg_BrowseNextRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00014_msg_RegisterNodesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00015_msg_UnregisterNodesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00016_msg_TranslateBrowsePathsToNodeIdsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00017_msg_CreateSubscriptionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00018_msg_ModifySubscriptionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00019_msg_SetPublishingModeRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00020_msg_CreateMonitoredItemsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00021_msg_PublishRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00022_msg_RepublishRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00023_msg_ModifyMonitoredItemsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00024_msg_SetMonitoringModeRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00025_msg_DeleteMonitoredItemsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00026_msg_DeleteSubscriptionsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00027_msg_CallRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00028_msg_AddNodesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00029_msg_AddReferencesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00030_msg_DeleteReferencesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00031_msg_DeleteNodesRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00032_msg_CloseSessionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00033_clo.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00034_hel.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00035_opn.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00036_msg_GetEndpointsRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00037_msg_CreateSessionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00038_msg_ActivateSessionRequest.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/generated/00039_clo.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/000_hello.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/010_open_secure_channel_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/015_get_endpoints_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/016_find_servers_on_network_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/017_find_servers_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/020_create_session_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/030_activate_session_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/035_register_server_2_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/040_read_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/050_browse_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/060_create_subscription_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/070_create_monitored_items_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/080_publish_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/090_read_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/100_write_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/110_delete_monitored_items_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/120_delete_subscriptions_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/130_translate_browse_paths_to_node_ids_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/140_call_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/150_call_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/160_close_session_request.bin


BIN
tests/fuzz/fuzz_binary_message_corpus/requests/170_close_secure_channel_request.bin


+ 17 - 0
tools/corpus_generator/CMakeLists.txt

@@ -0,0 +1,17 @@
+include_directories(${PROJECT_SOURCE_DIR}/src)
+
+#############################
+# Compiled binaries folders #
+#############################
+
+set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin/corpus_generator)
+
+add_definitions(-DUA_CORPUS_OUTPUT_DIR="${PROJECT_BINARY_DIR}/corpus")
+file(MAKE_DIRECTORY ${PROJECT_BINARY_DIR}/corpus)
+
+add_executable(corpus_generator corpus_generator.c)
+target_link_libraries(corpus_generator open62541 ${open62541_LIBRARIES})
+assign_source_group(corpus_generator)
+add_dependencies(corpus_generator open62541-amalgamation-header)
+set_target_properties(corpus_generator PROPERTIES FOLDER "open62541/corpus_generator")
+set_target_properties(corpus_generator PROPERTIES VS_DEBUGGER_WORKING_DIRECTORY "${CMAKE_BINARY_DIR}/bin/corpus_generator")

+ 707 - 0
tools/corpus_generator/corpus_generator.c

@@ -0,0 +1,707 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+/**
+ * This code is used to generate a binary file for every request type
+ * which can be sent from a client to the server.
+ * These files form the basic corpus for fuzzing the server.
+ * This script is intended to be executed manually and then commit the new
+ * corpus to the repository.
+ */
+
+#ifndef UA_DEBUG_DUMP_PKGS_FILE
+#error UA_DEBUG_DUMP_PKGS_FILE must be defined
+#endif
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <pthread.h>
+#include <ua_types.h>
+#include <sys/stat.h>
+#include <server/ua_server_internal.h>
+#include <dirent.h>
+#include <src_generated/ua_types_generated.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <ua_client_highlevel.h>
+
+#include "ua_server.h"
+#include "ua_client.h"
+#include "ua_config_default.h"
+#include "ua_client_highlevel.h"
+#include "ua_network_tcp.h"
+#include "ua_transport_generated.h"
+#include "ua_transport_generated_encoding_binary.h"
+#include "ua_securechannel.h"
+#include "ua_types_generated_encoding_binary.h"
+#include "server/ua_services.h"
+
+unsigned int chunkCount = 0;
+
+char dumpOutputFile[255];
+
+char *messageTypes[] = {"ack", "hel", "msg", "opn", "clo", "err", "unk"};
+char *messageTypePrefix = NULL;
+char requestServiceName[200];
+
+void UA_debug_dumpCompleteChunk(UA_Server *const server, UA_Connection *const connection, UA_ByteString *messageBuffer);
+
+static void setMessageTypePrefix(UA_UInt32 messageType) {
+    switch(messageType & 0x00ffffff) {
+        case UA_MESSAGETYPE_ACK:
+            messageTypePrefix = messageTypes[0];
+            break;
+        case UA_MESSAGETYPE_HEL:
+            messageTypePrefix = messageTypes[1];
+            break;
+        case UA_MESSAGETYPE_MSG:
+            messageTypePrefix = messageTypes[2];
+            break;
+        case UA_MESSAGETYPE_OPN:
+            messageTypePrefix = messageTypes[3];
+            break;
+        case UA_MESSAGETYPE_CLO:
+            messageTypePrefix = messageTypes[4];
+            break;
+        case UA_MESSAGETYPE_ERR:
+            messageTypePrefix = messageTypes[5];
+            break;
+        default:
+            messageTypePrefix = messageTypes[6];
+    }
+}
+
+
+static UA_StatusCode setRequestedServiceName(const UA_ByteString *msg) {
+    /* At 0, the nodeid starts... */
+    size_t offset = 0;
+
+    /* Decode the nodeid */
+    UA_NodeId requestTypeId;
+    UA_StatusCode retval = UA_NodeId_decodeBinary(msg, &offset, &requestTypeId);
+    if(retval != UA_STATUSCODE_GOOD)
+        return retval;
+    if(requestTypeId.identifierType != UA_NODEIDTYPE_NUMERIC || requestTypeId.namespaceIndex != 0) {
+        snprintf(requestServiceName, 200, "invalid_request_id");
+        return UA_STATUSCODE_BADUNEXPECTEDERROR;
+    }
+
+    const UA_DataType *requestType = NULL;
+
+    for (size_t i=0; i<UA_TYPES_COUNT; i++) {
+        if (UA_TYPES[i].binaryEncodingId == requestTypeId.identifier.numeric) {
+            requestType = &UA_TYPES[i];
+            break;
+        }
+    }
+    if (requestType == NULL) {
+        snprintf(requestServiceName, 200, "invalid_request_no_type");
+        return UA_STATUSCODE_BADUNEXPECTEDERROR;
+    }
+
+    snprintf(requestServiceName, 200, "_%s", requestType->typeName);
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode
+processCompleteChunkWithoutChannel(UA_Server *server, UA_Connection *connection,
+                                   UA_ByteString *message) {
+    size_t offset = 0;
+    UA_TcpMessageHeader tcpMessageHeader;
+    UA_StatusCode retval =
+            UA_TcpMessageHeader_decodeBinary(message, &offset, &tcpMessageHeader);
+    if(retval != UA_STATUSCODE_GOOD)
+        return retval;
+
+    setMessageTypePrefix(tcpMessageHeader.messageTypeAndChunkType & 0x00ffffff);
+
+    if ((tcpMessageHeader.messageTypeAndChunkType & 0x00ffffff) == UA_MESSAGETYPE_MSG) {
+        // this should not happen in normal operation
+        UA_LOG_ERROR(server->config.logger, UA_LOGCATEGORY_SERVER, "Got MSG package without channel.");
+        return UA_STATUSCODE_BADUNEXPECTEDERROR;
+    }
+    return UA_STATUSCODE_GOOD;
+}
+
+/* Takes decoded messages starting at the nodeid of the content type. */
+static UA_StatusCode
+processSecureChannelMessage(void *application, UA_SecureChannel *channel,
+                            UA_MessageType messagetype, UA_UInt32 requestId,
+                            const UA_ByteString *message) {
+    //UA_Server *server = (UA_Server*)application;
+    UA_StatusCode retval = UA_STATUSCODE_GOOD;
+    setMessageTypePrefix(messagetype);
+    if (messagetype == UA_MESSAGETYPE_MSG) {
+        setRequestedServiceName(message);
+    }
+    return retval;
+}
+
+
+void UA_debug_dumpCompleteChunk(UA_Server *const server, UA_Connection *const connection, UA_ByteString *messageBuffer) {
+
+    messageTypePrefix = NULL;
+    requestServiceName[0] = 0;
+
+    UA_StatusCode retval;
+    if(!connection->channel)
+        retval = processCompleteChunkWithoutChannel(server, connection, messageBuffer);
+    else {
+        // make a backup of the sequence number and reset it, because processChunk increases it
+        UA_UInt32 seqBackup = connection->channel->receiveSequenceNumber;
+        retval = UA_SecureChannel_processChunk(connection->channel, messageBuffer,
+                                               processSecureChannelMessage,
+                                               server);
+        connection->channel->receiveSequenceNumber = seqBackup;
+    }
+
+    snprintf(dumpOutputFile, 255, "%s/%05d_%s%s.bin", UA_CORPUS_OUTPUT_DIR, ++chunkCount, messageTypePrefix ? messageTypePrefix : "", requestServiceName);
+    UA_LOG_INFO(server->config.logger, UA_LOGCATEGORY_SERVER, "Dumping package %s", dumpOutputFile);
+
+    FILE *write_ptr;
+
+    write_ptr = fopen(dumpOutputFile, "ab");
+
+    fwrite(messageBuffer->data, messageBuffer->length, 1, write_ptr); // write 10 bytes from our buffer
+    fclose(write_ptr);
+}
+
+
+UA_Server *server;
+UA_ServerConfig *config;
+UA_Boolean *running;
+pthread_t server_thread;
+
+static void * serverloop(void *_) {
+    while(*running)
+        UA_Server_run_iterate(server, true);
+    return NULL;
+}
+
+static void start_server(void) {
+    running = UA_Boolean_new();
+    *running = true;
+    config = UA_ServerConfig_new_default();
+    server = UA_Server_new(config);
+    UA_Server_run_startup(server);
+    pthread_create(&server_thread, NULL, serverloop, NULL);
+}
+
+static void teardown_server(void) {
+    *running = false;
+    pthread_join(server_thread, NULL);
+    UA_Server_run_shutdown(server);
+    UA_Boolean_delete(running);
+    UA_Server_delete(server);
+    UA_ServerConfig_delete(config);
+}
+
+static void emptyCorpusDir() {
+    DIR *theFolder = opendir(UA_CORPUS_OUTPUT_DIR);
+    struct dirent *next_file;
+    char filepath[256];
+
+    while ( (next_file = readdir(theFolder)) != NULL )
+    {
+        // build the path for each file in the folder
+        sprintf(filepath, "%s/%s", UA_CORPUS_OUTPUT_DIR, next_file->d_name);
+        remove(filepath);
+    }
+    closedir(theFolder);
+}
+
+
+#define ASSERT_GOOD(X) if (X != UA_STATUSCODE_GOOD) return X;
+
+/*************************************************
+ * The following list of client requests is based
+ * on ua_server_binary.c:getServicePointers to
+ * cover all possible services and their inputs
+ ************************************************/
+
+static UA_StatusCode findServersRequest(UA_Client *client) {
+    UA_ApplicationDescription* applicationDescriptionArray = NULL;
+    size_t applicationDescriptionArraySize = 0;
+
+    size_t serverUrisSize = 1;
+    UA_String *serverUris = UA_String_new();
+    serverUris[0] = UA_String_fromChars("urn:some:server:uri");
+
+    size_t localeIdsSize = 1;
+    UA_String *localeIds = UA_String_new();
+    localeIds[0] = UA_String_fromChars("en");
+
+    ASSERT_GOOD(UA_Client_findServers(client, "opc.tcp://localhost:4840",
+                                  serverUrisSize, serverUris, localeIdsSize, localeIds,
+                                  &applicationDescriptionArraySize, &applicationDescriptionArray));
+
+    UA_Array_delete(serverUris, serverUrisSize, &UA_TYPES[UA_TYPES_STRING]);
+    UA_Array_delete(localeIds, localeIdsSize, &UA_TYPES[UA_TYPES_STRING]);
+    UA_Array_delete(applicationDescriptionArray, applicationDescriptionArraySize,
+                    &UA_TYPES[UA_TYPES_APPLICATIONDESCRIPTION]);
+
+    return UA_STATUSCODE_GOOD;
+
+}
+
+static UA_StatusCode findServersOnNetworkRequest(UA_Client *client) {
+    UA_ServerOnNetwork* serverOnNetwork = NULL;
+    size_t serverOnNetworkSize = 0;
+
+
+    size_t  serverCapabilityFilterSize = 2;
+    UA_String *serverCapabilityFilter = (UA_String*)UA_malloc(sizeof(UA_String) * serverCapabilityFilterSize);
+    serverCapabilityFilter[0] = UA_String_fromChars("LDS");
+    serverCapabilityFilter[1] = UA_String_fromChars("NA");
+
+
+    ASSERT_GOOD(UA_Client_findServersOnNetwork(client, "opc.tcp://localhost:4840", 0, 0,
+                                           serverCapabilityFilterSize, serverCapabilityFilter,
+                                           &serverOnNetworkSize, &serverOnNetwork));
+
+    UA_Array_delete(serverCapabilityFilter, serverCapabilityFilterSize,
+                        &UA_TYPES[UA_TYPES_STRING]);
+    UA_Array_delete(serverOnNetwork, serverOnNetworkSize, &UA_TYPES[UA_TYPES_SERVERONNETWORK]);
+    return UA_STATUSCODE_GOOD;
+}
+
+static void initUaRegisterServer(UA_RegisteredServer *requestServer) {
+    requestServer->isOnline = UA_TRUE;
+    requestServer->serverUri = server->config.applicationDescription.applicationUri;
+    requestServer->productUri = server->config.applicationDescription.productUri;
+    requestServer->serverType = server->config.applicationDescription.applicationType;
+    requestServer->gatewayServerUri = server->config.applicationDescription.gatewayServerUri;
+
+    // create the semaphore
+    int fd = open("/tmp/open62541-corpus-semaphore", O_RDWR|O_CREAT, S_IRWXU | S_IRWXG | S_IRWXO);
+    close(fd);
+    requestServer->semaphoreFilePath = UA_STRING_ALLOC("/tmp/open62541-corpus-semaphore");
+
+    requestServer->serverNames = &server->config.applicationDescription.applicationName;
+    requestServer->serverNamesSize = 1;
+
+    size_t nl_discurls = server->config.networkLayersSize;
+    requestServer->discoveryUrls = (UA_String*)UA_malloc(sizeof(UA_String) * nl_discurls);
+    requestServer->discoveryUrlsSize = nl_discurls;
+    for(size_t i = 0; i < nl_discurls; ++i) {
+        UA_ServerNetworkLayer *nl = &server->config.networkLayers[i];
+        requestServer->discoveryUrls[i] = nl->discoveryUrl;
+    }
+
+}
+
+static UA_StatusCode registerServerRequest(UA_Client *client) {
+
+    /* Prepare the request. Do not cleanup the request after the service call,
+     * as the members are stack-allocated or point into the server config. */
+    UA_RegisterServerRequest request;
+    UA_RegisterServerRequest_init(&request);
+    /* Copy from RegisterServer2 request */
+    request.requestHeader.timestamp = UA_DateTime_now();
+    request.requestHeader.timeoutHint = 10000;
+
+    initUaRegisterServer(&request.server);
+
+
+    UA_RegisterServerResponse response;
+    UA_RegisterServerResponse_init(&response);
+
+    __UA_Client_Service(client, &request,
+                        &UA_TYPES[UA_TYPES_REGISTERSERVERREQUEST],
+                        &response,
+                        &UA_TYPES[UA_TYPES_REGISTERSERVERRESPONSE]);
+
+    UA_free(request.server.discoveryUrls);
+    ASSERT_GOOD(response.responseHeader.serviceResult);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode registerServer2Request(UA_Client *client) {
+    /* Prepare the request. Do not cleanup the request after the service call,
+     * as the members are stack-allocated or point into the server config. */
+    UA_RegisterServer2Request request;
+    UA_RegisterServer2Request_init(&request);
+    request.requestHeader.timestamp = UA_DateTime_now();
+    request.requestHeader.timeoutHint = 10000;
+
+    initUaRegisterServer(&request.server);
+
+    UA_MdnsDiscoveryConfiguration mdnsConfig;
+    UA_MdnsDiscoveryConfiguration_init(&mdnsConfig);
+
+    request.discoveryConfigurationSize = 1;
+    request.discoveryConfiguration = UA_ExtensionObject_new();
+    UA_ExtensionObject_init(&request.discoveryConfiguration[0]);
+    request.discoveryConfiguration[0].encoding = UA_EXTENSIONOBJECT_DECODED_NODELETE;
+    request.discoveryConfiguration[0].content.decoded.type = &UA_TYPES[UA_TYPES_MDNSDISCOVERYCONFIGURATION];
+    request.discoveryConfiguration[0].content.decoded.data = &mdnsConfig;
+
+    mdnsConfig.mdnsServerName = server->config.mdnsServerName;
+    mdnsConfig.serverCapabilities = server->config.serverCapabilities;
+    mdnsConfig.serverCapabilitiesSize = server->config.serverCapabilitiesSize;
+
+    // First try with RegisterServer2, if that isn't implemented, use RegisterServer
+    UA_RegisterServer2Response response;
+    UA_RegisterServer2Response_init(&response);
+    __UA_Client_Service(client, &request, &UA_TYPES[UA_TYPES_REGISTERSERVER2REQUEST],
+                        &response, &UA_TYPES[UA_TYPES_REGISTERSERVER2RESPONSE]);
+
+    ASSERT_GOOD(response.responseHeader.serviceResult);
+    UA_free(request.server.discoveryUrls);
+    UA_ExtensionObject_delete(request.discoveryConfiguration);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode readValueRequest(UA_Client *client) {
+    UA_ReadValueId rvi;
+    UA_ReadValueId_init(&rvi);
+    rvi.nodeId = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER_SERVERSTATUS_STARTTIME);
+    rvi.attributeId = UA_ATTRIBUTEID_VALUE;
+
+    UA_DataValue resp = UA_Server_read(server, &rvi, UA_TIMESTAMPSTORETURN_BOTH);
+    ASSERT_GOOD(resp.status);
+
+    UA_DataValue_deleteMembers(&resp);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+
+static UA_StatusCode writeValueRequest(UA_Client *client) {
+    UA_WriteValue wValue;
+    UA_WriteValue_init(&wValue);
+    UA_LocalizedText testValue = UA_LOCALIZEDTEXT("en-EN", "MyServer");
+    UA_Variant_setScalar(&wValue.value.value, &testValue, &UA_TYPES[UA_TYPES_LOCALIZEDTEXT]);
+    wValue.value.hasValue = true;
+    wValue.nodeId = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER);
+    wValue.attributeId = UA_ATTRIBUTEID_DISPLAYNAME;
+    ASSERT_GOOD(UA_Server_write(server, &wValue));
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode browseAndBrowseNextRequest(UA_Client *client) {
+    // Browse node in server folder
+    UA_BrowseRequest bReq;
+    UA_BrowseRequest_init(&bReq);
+    // normally is set to 0, to get all the nodes, but we want to test browse next
+    bReq.requestedMaxReferencesPerNode = 1;
+    bReq.nodesToBrowse = UA_BrowseDescription_new();
+    bReq.nodesToBrowseSize = 1;
+    bReq.nodesToBrowse[0].nodeId = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER);
+    bReq.nodesToBrowse[0].resultMask = UA_BROWSERESULTMASK_ALL;
+
+    UA_BrowseResponse bResp = UA_Client_Service_browse(client, bReq);
+    ASSERT_GOOD(bResp.responseHeader.serviceResult);
+
+    // browse next
+    UA_BrowseNextRequest bNextReq;
+    UA_BrowseNextRequest_init(&bNextReq);
+    // normally is set to 0, to get all the nodes, but we want to test browse next
+    bNextReq.releaseContinuationPoints = UA_FALSE;
+    bNextReq.continuationPoints = &bResp.results[0].continuationPoint;
+    bNextReq.continuationPointsSize = 1;
+
+    UA_BrowseNextResponse bNextResp = UA_Client_Service_browseNext(client, bNextReq);
+    ASSERT_GOOD(bNextResp.responseHeader.serviceResult);
+
+    UA_BrowseNextResponse_deleteMembers(&bNextResp);
+
+    bNextResp = UA_Client_Service_browseNext(client, bNextReq);
+    ASSERT_GOOD(bNextResp.responseHeader.serviceResult);
+
+    UA_BrowseNextResponse_deleteMembers(&bNextResp);
+
+    // release continuation point. Result is then empty
+    bNextReq.releaseContinuationPoints = UA_TRUE;
+    bNextResp = UA_Client_Service_browseNext(client, bNextReq);
+    UA_BrowseNextResponse_deleteMembers(&bNextResp);
+    ASSERT_GOOD(bNextResp.responseHeader.serviceResult);
+
+    UA_BrowseRequest_deleteMembers(&bReq);
+    UA_BrowseResponse_deleteMembers(&bResp);
+    // already deleted by browse request
+    bNextReq.continuationPoints = NULL;
+    bNextReq.continuationPointsSize = 0;
+    UA_BrowseNextRequest_deleteMembers(&bNextReq);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode registerUnregisterNodesRequest(UA_Client *client) {
+    UA_RegisterNodesRequest req;
+    UA_RegisterNodesRequest_init(&req);
+
+    req.nodesToRegister = UA_NodeId_new();
+    req.nodesToRegister[0] = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER_SERVERSTATUS_CURRENTTIME);
+    req.nodesToRegisterSize = 1;
+
+    UA_RegisterNodesResponse res = UA_Client_Service_registerNodes(client, req);
+    ASSERT_GOOD(res.responseHeader.serviceResult);
+
+    UA_UnregisterNodesRequest reqUn;
+    UA_UnregisterNodesRequest_init(&reqUn);
+
+    reqUn.nodesToUnregister = UA_NodeId_new();
+    reqUn.nodesToUnregister[0] = res.registeredNodeIds[0];
+    reqUn.nodesToUnregisterSize = 1;
+
+    UA_UnregisterNodesResponse resUn = UA_Client_Service_unregisterNodes(client, reqUn);
+    ASSERT_GOOD(resUn.responseHeader.serviceResult);
+
+    UA_UnregisterNodesRequest_deleteMembers(&reqUn);
+    UA_UnregisterNodesResponse_deleteMembers(&resUn);
+    UA_RegisterNodesRequest_deleteMembers(&req);
+    UA_RegisterNodesResponse_deleteMembers(&res);
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode translateBrowsePathsToNodeIdsRequest(UA_Client *client) {
+    // Just for testing we want to translate the following path to its corresponding node id
+    // /Objects/Server/ServerStatus/State
+    // Equals the following node IDs:
+    // /85/2253/2256/2259
+
+    #define BROWSE_PATHS_SIZE 3
+    char *paths[BROWSE_PATHS_SIZE] = {"Server", "ServerStatus", "State"};
+    UA_UInt32 ids[BROWSE_PATHS_SIZE] = {UA_NS0ID_ORGANIZES, UA_NS0ID_HASCOMPONENT, UA_NS0ID_HASCOMPONENT};
+    UA_BrowsePath browsePath;
+    UA_BrowsePath_init(&browsePath);
+    browsePath.startingNode = UA_NODEID_NUMERIC(0, UA_NS0ID_OBJECTSFOLDER);
+    browsePath.relativePath.elements = (UA_RelativePathElement*)UA_Array_new(BROWSE_PATHS_SIZE, &UA_TYPES[UA_TYPES_RELATIVEPATHELEMENT]);
+    browsePath.relativePath.elementsSize = BROWSE_PATHS_SIZE;
+
+    for(size_t i = 0; i < BROWSE_PATHS_SIZE; i++) {
+        UA_RelativePathElement *elem = &browsePath.relativePath.elements[i];
+        elem->referenceTypeId = UA_NODEID_NUMERIC(0, ids[i]);
+        elem->targetName = UA_QUALIFIEDNAME_ALLOC(0, paths[i]);
+    }
+
+    UA_TranslateBrowsePathsToNodeIdsRequest request;
+    UA_TranslateBrowsePathsToNodeIdsRequest_init(&request);
+    request.browsePaths = &browsePath;
+    request.browsePathsSize = 1;
+
+    UA_TranslateBrowsePathsToNodeIdsResponse response = UA_Client_Service_translateBrowsePathsToNodeIds(client, request);
+    ASSERT_GOOD(response.responseHeader.serviceResult);
+
+    UA_BrowsePath_deleteMembers(&browsePath);
+    UA_TranslateBrowsePathsToNodeIdsResponse_deleteMembers(&response);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+
+static void monitoredItemHandler(UA_UInt32 monId, UA_DataValue *value, void *context) {
+
+}
+
+static UA_StatusCode subscriptionRequests(UA_Client *client) {
+    UA_UInt32 subId;
+    // createSubscriptionRequest
+    ASSERT_GOOD(UA_Client_Subscriptions_new(client, UA_SubscriptionSettings_default, &subId));
+
+
+    // modifySubscription
+    UA_ModifySubscriptionRequest modifySubscriptionRequest;
+    UA_ModifySubscriptionRequest_init(&modifySubscriptionRequest);
+    modifySubscriptionRequest.subscriptionId = subId;
+    modifySubscriptionRequest.maxNotificationsPerPublish = UA_SubscriptionSettings_default.maxNotificationsPerPublish;
+    modifySubscriptionRequest.priority = UA_SubscriptionSettings_default.priority;
+    modifySubscriptionRequest.requestedLifetimeCount = UA_SubscriptionSettings_default.requestedLifetimeCount;
+    modifySubscriptionRequest.requestedMaxKeepAliveCount = UA_SubscriptionSettings_default.requestedMaxKeepAliveCount;
+    modifySubscriptionRequest.requestedPublishingInterval = UA_SubscriptionSettings_default.requestedPublishingInterval;
+    UA_ModifySubscriptionResponse modifySubscriptionResponse;
+    __UA_Client_Service(client, &modifySubscriptionRequest, &UA_TYPES[UA_TYPES_MODIFYSUBSCRIPTIONREQUEST],
+                        &modifySubscriptionResponse, &UA_TYPES[UA_TYPES_MODIFYSUBSCRIPTIONRESPONSE]);
+    ASSERT_GOOD(modifySubscriptionResponse.responseHeader.serviceResult);
+    UA_ModifySubscriptionRequest_deleteMembers(&modifySubscriptionRequest);
+    UA_ModifySubscriptionResponse_deleteMembers(&modifySubscriptionResponse);
+
+    // setPublishingMode
+    UA_SetPublishingModeRequest setPublishingModeRequest;
+    UA_SetPublishingModeRequest_init(&setPublishingModeRequest);
+    setPublishingModeRequest.subscriptionIdsSize = 1;
+    setPublishingModeRequest.subscriptionIds = UA_malloc(sizeof(UA_UInt32));
+    setPublishingModeRequest.subscriptionIds[0] = subId;
+    setPublishingModeRequest.publishingEnabled = UA_TRUE;
+    UA_SetPublishingModeResponse setPublishingModeResponse;
+    __UA_Client_Service(client, &setPublishingModeRequest, &UA_TYPES[UA_TYPES_SETPUBLISHINGMODEREQUEST],
+                        &setPublishingModeResponse, &UA_TYPES[UA_TYPES_SETPUBLISHINGMODERESPONSE]);
+    ASSERT_GOOD(setPublishingModeResponse.responseHeader.serviceResult);
+    UA_SetPublishingModeRequest_deleteMembers(&setPublishingModeRequest);
+    UA_SetPublishingModeResponse_deleteMembers(&setPublishingModeResponse);
+    
+
+    // createMonitoredItemsRequest
+    UA_UInt32 monId;
+    ASSERT_GOOD(UA_Client_Subscriptions_addMonitoredItem(client, subId, UA_NODEID_NUMERIC(0, 2259),
+                                                      UA_ATTRIBUTEID_VALUE, monitoredItemHandler,
+                                                      NULL, &monId));
+
+    // publishRequest
+    ASSERT_GOOD(UA_Client_Subscriptions_manuallySendPublishRequest(client));
+
+    // republishRequest
+    UA_RepublishRequest republishRequest;
+    UA_RepublishRequest_init(&republishRequest);
+    republishRequest.retransmitSequenceNumber = 0;
+    republishRequest.subscriptionId = subId;
+    UA_RepublishResponse republishResponse;
+    __UA_Client_Service(client, &republishRequest, &UA_TYPES[UA_TYPES_REPUBLISHREQUEST],
+                        &republishResponse, &UA_TYPES[UA_TYPES_REPUBLISHRESPONSE]);
+    // here we don't care about the return value since it may be UA_STATUSCODE_BADMESSAGENOTAVAILABLE
+    // ASSERT_GOOD(republishResponse.responseHeader.serviceResult);
+    UA_RepublishRequest_deleteMembers(&republishRequest);
+    UA_RepublishResponse_deleteMembers(&republishResponse);
+
+    // modifyMonitoredItems
+    UA_ModifyMonitoredItemsRequest modifyMonitoredItemsRequest;
+    UA_ModifyMonitoredItemsRequest_init(&modifyMonitoredItemsRequest);
+    modifyMonitoredItemsRequest.subscriptionId = subId;
+    modifyMonitoredItemsRequest.itemsToModifySize = 1;
+    modifyMonitoredItemsRequest.itemsToModify = UA_malloc(sizeof(UA_MonitoredItemModifyRequest));
+    modifyMonitoredItemsRequest.itemsToModify[0].monitoredItemId = monId;
+    UA_MonitoringParameters_init(&modifyMonitoredItemsRequest.itemsToModify[0].requestedParameters);
+    UA_ModifyMonitoredItemsResponse modifyMonitoredItemsResponse;
+    __UA_Client_Service(client, &modifyMonitoredItemsRequest, &UA_TYPES[UA_TYPES_MODIFYMONITOREDITEMSREQUEST],
+                        &modifyMonitoredItemsResponse, &UA_TYPES[UA_TYPES_MODIFYMONITOREDITEMSRESPONSE]);
+    ASSERT_GOOD(modifyMonitoredItemsResponse.responseHeader.serviceResult);
+    UA_ModifyMonitoredItemsRequest_deleteMembers(&modifyMonitoredItemsRequest);
+    UA_ModifyMonitoredItemsResponse_deleteMembers(&modifyMonitoredItemsResponse);
+    
+    // setMonitoringMode
+    UA_SetMonitoringModeRequest setMonitoringModeRequest;
+    UA_SetMonitoringModeRequest_init(&setMonitoringModeRequest);
+    setMonitoringModeRequest.subscriptionId = subId;
+    setMonitoringModeRequest.monitoredItemIdsSize = 1;
+    setMonitoringModeRequest.monitoredItemIds = UA_malloc(sizeof(UA_UInt32));
+    setMonitoringModeRequest.monitoredItemIds[0] = monId;
+    setMonitoringModeRequest.monitoringMode = UA_MONITORINGMODE_REPORTING;
+    UA_SetMonitoringModeResponse setMonitoringModeResponse;
+    __UA_Client_Service(client, &setMonitoringModeRequest, &UA_TYPES[UA_TYPES_SETMONITORINGMODEREQUEST],
+                        &setMonitoringModeResponse, &UA_TYPES[UA_TYPES_SETMONITORINGMODERESPONSE]);
+    ASSERT_GOOD(setMonitoringModeResponse.responseHeader.serviceResult);
+    UA_SetMonitoringModeRequest_deleteMembers(&setMonitoringModeRequest);
+    UA_SetMonitoringModeResponse_deleteMembers(&setMonitoringModeResponse);
+
+    // deleteMonitoredItemsRequest
+    ASSERT_GOOD(UA_Client_Subscriptions_removeMonitoredItem(client, subId, monId));
+
+
+    // deleteSubscriptionRequest
+    ASSERT_GOOD(UA_Client_Subscriptions_remove(client, subId));
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode callRequest(UA_Client *client) {
+    /* Set up the request */
+    UA_CallRequest request;
+    UA_CallRequest_init(&request);
+    UA_CallMethodRequest item;
+    UA_CallMethodRequest_init(&item);
+    item.methodId = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER_GETMONITOREDITEMS);
+    item.objectId = UA_NODEID_NUMERIC(0, UA_NS0ID_SERVER);
+
+
+    UA_Variant input;
+    UA_UInt32 subId = 12345;
+    UA_Variant_init(&input);
+    UA_Variant_setScalarCopy(&input, &subId, &UA_TYPES[UA_TYPES_UINT32]);
+    item.inputArgumentsSize = 1;
+    item.inputArguments = &input;
+
+    request.methodsToCall = &item;
+    request.methodsToCallSize = 1;
+
+    /* Call the service */
+    UA_CallResponse response = UA_Client_Service_call(client, request);
+    ASSERT_GOOD(response.responseHeader.serviceResult);
+
+    UA_CallResponse_deleteMembers(&response);
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode nodemanagementRequests(UA_Client *client) {
+    UA_ObjectAttributes attr = UA_ObjectAttributes_default;
+    attr.description = UA_LOCALIZEDTEXT("en-US", "Some Coordinates");
+    attr.displayName = UA_LOCALIZEDTEXT("en-US", "Coordinates");
+
+    UA_NodeId newObjectId;
+
+    ASSERT_GOOD(UA_Client_addObjectNode(client, UA_NODEID_NULL,
+                                     UA_NODEID_NUMERIC(0, UA_NS0ID_OBJECTSFOLDER),
+                                     UA_NODEID_NUMERIC(0, UA_NS0ID_ORGANIZES),
+                                     UA_QUALIFIEDNAME(1, "Coordinates"),
+                                     UA_NODEID_NUMERIC(0, UA_NS0ID_FOLDERTYPE), attr, &newObjectId));
+
+
+    UA_ExpandedNodeId target = UA_EXPANDEDNODEID_NULL;
+    target.nodeId = newObjectId;
+    ASSERT_GOOD(UA_Client_addReference(client, UA_NODEID_NUMERIC(0, UA_NS0ID_ROOTFOLDER), UA_NODEID_NUMERIC(0, UA_NS0ID_ORGANIZES),
+                                    UA_TRUE, UA_STRING_NULL, target, UA_NODECLASS_OBJECT));
+
+    ASSERT_GOOD(UA_Client_deleteReference(client, UA_NODEID_NUMERIC(0, UA_NS0ID_ROOTFOLDER),
+                                       UA_NODEID_NUMERIC(0, UA_NS0ID_ORGANIZES),
+                                       true, target, true));
+
+    ASSERT_GOOD(UA_Client_deleteNode(client, newObjectId, UA_TRUE));
+
+    return UA_STATUSCODE_GOOD;
+}
+
+static UA_StatusCode executeClientServices(UA_Client *client) {
+
+    ASSERT_GOOD(findServersRequest(client));
+    ASSERT_GOOD(findServersOnNetworkRequest(client));
+    ASSERT_GOOD(registerServerRequest(client));
+    ASSERT_GOOD(registerServer2Request(client));
+    ASSERT_GOOD(readValueRequest(client));
+    ASSERT_GOOD(writeValueRequest(client));
+    ASSERT_GOOD(browseAndBrowseNextRequest(client));
+    ASSERT_GOOD(registerUnregisterNodesRequest(client));
+    ASSERT_GOOD(translateBrowsePathsToNodeIdsRequest(client));
+    ASSERT_GOOD(subscriptionRequests(client));
+    ASSERT_GOOD(callRequest(client));
+    ASSERT_GOOD(nodemanagementRequests(client));
+
+
+    return UA_STATUSCODE_GOOD;
+}
+
+int main(void) {
+    emptyCorpusDir();
+    start_server();
+    UA_StatusCode retval;
+
+    UA_Client *client = UA_Client_new(UA_ClientConfig_default);
+    // this will also call getEndpointsRequest
+    retval = UA_Client_connect(client, "opc.tcp://localhost:4840");
+    if (retval == UA_STATUSCODE_GOOD)
+        retval = executeClientServices(client);
+    UA_Client_disconnect(client);
+    UA_Client_delete(client);
+
+    if (retval == UA_STATUSCODE_GOOD) {
+        // now also connect with user/pass so that fuzzer also knows how to do that
+        client = UA_Client_new(UA_ClientConfig_default);
+        retval = UA_Client_connect_username(client, "opc.tcp://localhost:4840", "user", "password");
+        retval = retval == UA_STATUSCODE_BADUSERACCESSDENIED ? UA_STATUSCODE_GOOD : retval;
+        UA_Client_disconnect(client);
+        UA_Client_delete(client);
+    }
+
+    teardown_server();
+
+    if (retval != UA_STATUSCODE_GOOD) {
+        printf("\n--------- AN ERROR OCCURED ----------\nStatus = %s\n", UA_StatusCode_name(retval));
+    } else {
+        printf("\n--------- SUCCESS -------\nThe corpus is stored in %s\nYou manually need to copy them into the direcotry tests/fuss/fuzz_binary_message_corpus/generated", UA_CORPUS_OUTPUT_DIR);
+    }
+    return (int) retval;
+}