From d410fa96fcb6f57440d8e95bcd320debbc9a5303 Mon Sep 17 00:00:00 2001 From: erlingrj Date: Thu, 23 Jan 2025 15:15:51 +0100 Subject: [PATCH 1/4] Validate that the port sizes are less than the MTU --- include/reactor-uc/federated.h | 2 +- include/reactor-uc/serialization.h | 7 ++++++- src/federated.c | 23 +++++++++++++++-------- src/serialization.c | 14 ++++++++++---- 4 files changed, 32 insertions(+), 14 deletions(-) diff --git a/include/reactor-uc/federated.h b/include/reactor-uc/federated.h index e606d7d1..6ef7c04e 100644 --- a/include/reactor-uc/federated.h +++ b/include/reactor-uc/federated.h @@ -11,7 +11,7 @@ typedef struct FederatedInputConnection FederatedInputConnection; typedef struct NetworkChannel NetworkChannel; // returns how many bytes of the buffer were used by the serialized string -typedef size_t (*serialize_hook)(const void *user_struct, size_t user_struct_size, unsigned char *msg_buffer); +typedef ssize_t (*serialize_hook)(const void *user_struct, size_t user_struct_size, unsigned char *msg_buffer); // returns if the deserialization was successful typedef lf_ret_t (*deserialize_hook)(void *user_struct, const unsigned char *msg_buffer, size_t msg_size); diff --git a/include/reactor-uc/serialization.h b/include/reactor-uc/serialization.h index 7f444a6f..334cbf8b 100644 --- a/include/reactor-uc/serialization.h +++ b/include/reactor-uc/serialization.h @@ -3,11 +3,16 @@ #include "proto/message.pb.h" #include "reactor-uc/error.h" +#include + +#ifndef SERIALIZATION_MAX_PAYLOAD_SIZE +#define SERIALIZATION_MAX_PAYLOAD_SIZE 832 +#endif int serialize_to_protobuf(const FederateMessage *message, unsigned char *buffer, size_t buffer_size); int deserialize_from_protobuf(FederateMessage *message, const unsigned char *buffer, size_t buffer_size); lf_ret_t deserialize_payload_default(void *user_struct, const unsigned char *msg_buf, size_t msg_size); -size_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf); +ssize_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf); #endif // REACTOR_UC_SERIALIZATION_H diff --git a/src/federated.c b/src/federated.c index f56bab72..8d35ce00 100644 --- a/src/federated.c +++ b/src/federated.c @@ -2,6 +2,7 @@ #include "reactor-uc/environment.h" #include "reactor-uc/logging.h" #include "reactor-uc/platform.h" +#include "reactor-uc/serialization.h" // TODO: Refactor so this function is available void LogicalConnection_trigger_downstreams(Connection *self, const void *value, size_t value_size); @@ -91,14 +92,18 @@ void FederatedOutputConnection_cleanup(Trigger *trigger) { tagged_msg->tag.microstep = sched->current_tag(sched).microstep; assert(self->bundle->serialize_hooks[self->conn_id]); - size_t msg_size = (*self->bundle->serialize_hooks[self->conn_id])(self->staged_payload_ptr, self->payload_pool.size, - tagged_msg->payload.bytes); - tagged_msg->payload.size = msg_size; - - LF_DEBUG(FED, "FedOutConn %p sending tagged message with tag=%" PRId64 ":%" PRIu32, trigger, tagged_msg->tag.time, - tagged_msg->tag.microstep); - if (channel->send_blocking(channel, &msg) != LF_OK) { - LF_ERR(FED, "FedOutConn %p failed to send message", trigger); + ssize_t msg_size = (*self->bundle->serialize_hooks[self->conn_id])( + self->staged_payload_ptr, self->payload_pool.size, tagged_msg->payload.bytes); + if (msg_size < 0) { + LF_ERR(FED, "Failed to serialize payload for federated output connection %p", trigger); + } else { + tagged_msg->payload.size = msg_size; + + LF_DEBUG(FED, "FedOutConn %p sending tagged message with tag=%" PRId64 ":%" PRIu32, trigger, tagged_msg->tag.time, + tagged_msg->tag.microstep); + if (channel->send_blocking(channel, &msg) != LF_OK) { + LF_ERR(FED, "FedOutConn %p failed to send message", trigger); + } } } else { LF_WARN(FED, "FedOutConn %p not connected. Dropping staged message", trigger); @@ -321,10 +326,12 @@ void FederatedConnectionBundle_validate(FederatedConnectionBundle *bundle) { validate(bundle->inputs[i]); validate(bundle->deserialize_hooks[i]); validate(bundle->inputs[i]->super.super.parent); + validate(bundle->inputs[i]->super.super.payload_pool->size < SERIALIZATION_MAX_PAYLOAD_SIZE); } for (size_t i = 0; i < bundle->outputs_size; i++) { validate(bundle->outputs[i]); validate(bundle->serialize_hooks[i]); validate(bundle->outputs[i]->super.super.parent); + validate(bundle->outputs[i]->super.super.payload_pool->size < SERIALIZATION_MAX_PAYLOAD_SIZE); } } diff --git a/src/serialization.c b/src/serialization.c index 1b111d6a..d471b7b6 100644 --- a/src/serialization.c +++ b/src/serialization.c @@ -31,11 +31,17 @@ int deserialize_from_protobuf(FederateMessage *message, const unsigned char *buf } lf_ret_t deserialize_payload_default(void *user_struct, const unsigned char *msg_buf, size_t msg_size) { - memcpy(user_struct, msg_buf, MIN(msg_size, 832)); // TODO: 832 is a magic number + if (msg_size > SERIALIZATION_MAX_PAYLOAD_SIZE) { + return LF_ERR; + } + memcpy(user_struct, msg_buf, msg_size); return LF_OK; } -size_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf) { - memcpy(msg_buf, user_struct, MIN(user_struct_size, 832)); // TODO: 832 is a magic number - return MIN(user_struct_size, 832); // TODO: 832 is a magic number +ssize_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf) { + if (user_struct_size > SERIALIZATION_MAX_PAYLOAD_SIZE) { + return -1; + } + memcpy(msg_buf, user_struct, user_struct_size); + return user_struct_size; } From 4bb20038c72b549723ff5db70ee35004a6a5d4c7 Mon Sep 17 00:00:00 2001 From: erlingrj Date: Thu, 23 Jan 2025 15:24:24 +0100 Subject: [PATCH 2/4] Choose CI runner version explicitly --- .github/workflows/benchmark.yml | 2 +- .github/workflows/flexpret.yml | 2 +- .github/workflows/memory.yml | 2 +- .github/workflows/pico.yml | 2 +- .github/workflows/posix.yml | 2 +- .github/workflows/riot.yml | 2 +- .github/workflows/zephyr.yml | 2 +- 7 files changed, 7 insertions(+), 7 deletions(-) diff --git a/.github/workflows/benchmark.yml b/.github/workflows/benchmark.yml index 6fbe1032..0e180281 100644 --- a/.github/workflows/benchmark.yml +++ b/.github/workflows/benchmark.yml @@ -10,7 +10,7 @@ on: jobs: ci: name: Run benchmarks - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: - name: Checkout uses: actions/checkout@v3 diff --git a/.github/workflows/flexpret.yml b/.github/workflows/flexpret.yml index 8f48bd88..1d583234 100644 --- a/.github/workflows/flexpret.yml +++ b/.github/workflows/flexpret.yml @@ -6,7 +6,7 @@ on: jobs: ci: name: Build FlexPRET examples - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: - name: Checkout uses: actions/checkout@v3 diff --git a/.github/workflows/memory.yml b/.github/workflows/memory.yml index 98ff9f26..f19a74c8 100644 --- a/.github/workflows/memory.yml +++ b/.github/workflows/memory.yml @@ -10,7 +10,7 @@ permissions: jobs: ci: name: Report memory usage - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: # To get the potential changes to CI - name: Checkout diff --git a/.github/workflows/pico.yml b/.github/workflows/pico.yml index 1570b214..c5fb8c58 100644 --- a/.github/workflows/pico.yml +++ b/.github/workflows/pico.yml @@ -6,7 +6,7 @@ on: jobs: ci: name: Build examples - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: - name: Checkout uses: actions/checkout@v3 diff --git a/.github/workflows/posix.yml b/.github/workflows/posix.yml index 5b825b6b..f1e07731 100644 --- a/.github/workflows/posix.yml +++ b/.github/workflows/posix.yml @@ -6,7 +6,7 @@ on: jobs: ci: name: Build examples - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 steps: - name: Checkout uses: actions/checkout@v3 diff --git a/.github/workflows/riot.yml b/.github/workflows/riot.yml index b0f7f0ad..632c6ed7 100644 --- a/.github/workflows/riot.yml +++ b/.github/workflows/riot.yml @@ -6,7 +6,7 @@ on: jobs: ci: name: Build examples and run tests - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 container: image: riot/riotbuild:latest env: diff --git a/.github/workflows/zephyr.yml b/.github/workflows/zephyr.yml index 3a3a35c9..b7f2d495 100644 --- a/.github/workflows/zephyr.yml +++ b/.github/workflows/zephyr.yml @@ -6,7 +6,7 @@ on: jobs: ci: name: Build examples - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 env: REACTOR_UC_PATH: ${{ github.workspace }} steps: From c1778ffd3dbfc8a27758b232db0585cc11adecc1 Mon Sep 17 00:00:00 2001 From: erlingrj Date: Fri, 24 Jan 2025 08:44:03 +0100 Subject: [PATCH 3/4] Add docs on how the max payload size must match the protobuf description --- include/reactor-uc/serialization.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/include/reactor-uc/serialization.h b/include/reactor-uc/serialization.h index 334cbf8b..21047b89 100644 --- a/include/reactor-uc/serialization.h +++ b/include/reactor-uc/serialization.h @@ -5,6 +5,8 @@ #include "reactor-uc/error.h" #include +// The maximum size of a serialized payload. +// NOTE: This MUST match the max size of the payload in the protobuf message definition. #ifndef SERIALIZATION_MAX_PAYLOAD_SIZE #define SERIALIZATION_MAX_PAYLOAD_SIZE 832 #endif From 34141e2045a4f6c534884325899516eba24d2d5a Mon Sep 17 00:00:00 2001 From: erlingrj Date: Fri, 24 Jan 2025 09:05:50 +0100 Subject: [PATCH 4/4] Format --- include/reactor-uc/serialization.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/reactor-uc/serialization.h b/include/reactor-uc/serialization.h index 21047b89..ddaac4da 100644 --- a/include/reactor-uc/serialization.h +++ b/include/reactor-uc/serialization.h @@ -5,7 +5,7 @@ #include "reactor-uc/error.h" #include -// The maximum size of a serialized payload. +// The maximum size of a serialized payload. // NOTE: This MUST match the max size of the payload in the protobuf message definition. #ifndef SERIALIZATION_MAX_PAYLOAD_SIZE #define SERIALIZATION_MAX_PAYLOAD_SIZE 832