Skip to content

Commit 7f5fd0e

Browse files
authored
Validate that the port sizes are less than the MTU (#196)
* Validate that the port sizes are less than the MTU * Choose CI runner version explicitly * Add docs on how the max payload size must match the protobuf description * Format
1 parent b29081a commit 7f5fd0e

File tree

4 files changed

+34
-14
lines changed

4 files changed

+34
-14
lines changed

include/reactor-uc/federated.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ typedef struct FederatedInputConnection FederatedInputConnection;
1111
typedef struct NetworkChannel NetworkChannel;
1212

1313
// returns how many bytes of the buffer were used by the serialized string
14-
typedef size_t (*serialize_hook)(const void *user_struct, size_t user_struct_size, unsigned char *msg_buffer);
14+
typedef ssize_t (*serialize_hook)(const void *user_struct, size_t user_struct_size, unsigned char *msg_buffer);
1515

1616
// returns if the deserialization was successful
1717
typedef lf_ret_t (*deserialize_hook)(void *user_struct, const unsigned char *msg_buffer, size_t msg_size);

include/reactor-uc/serialization.h

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,18 @@
33

44
#include "proto/message.pb.h"
55
#include "reactor-uc/error.h"
6+
#include <stddef.h>
7+
8+
// The maximum size of a serialized payload.
9+
// NOTE: This MUST match the max size of the payload in the protobuf message definition.
10+
#ifndef SERIALIZATION_MAX_PAYLOAD_SIZE
11+
#define SERIALIZATION_MAX_PAYLOAD_SIZE 832
12+
#endif
613

714
int serialize_to_protobuf(const FederateMessage *message, unsigned char *buffer, size_t buffer_size);
815
int deserialize_from_protobuf(FederateMessage *message, const unsigned char *buffer, size_t buffer_size);
916

1017
lf_ret_t deserialize_payload_default(void *user_struct, const unsigned char *msg_buf, size_t msg_size);
1118

12-
size_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf);
19+
ssize_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf);
1320
#endif // REACTOR_UC_SERIALIZATION_H

src/federated.c

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
#include "reactor-uc/environment.h"
33
#include "reactor-uc/logging.h"
44
#include "reactor-uc/platform.h"
5+
#include "reactor-uc/serialization.h"
56

67
// TODO: Refactor so this function is available
78
void LogicalConnection_trigger_downstreams(Connection *self, const void *value, size_t value_size);
@@ -91,14 +92,18 @@ void FederatedOutputConnection_cleanup(Trigger *trigger) {
9192
tagged_msg->tag.microstep = sched->current_tag(sched).microstep;
9293

9394
assert(self->bundle->serialize_hooks[self->conn_id]);
94-
size_t msg_size = (*self->bundle->serialize_hooks[self->conn_id])(self->staged_payload_ptr, self->payload_pool.size,
95-
tagged_msg->payload.bytes);
96-
tagged_msg->payload.size = msg_size;
97-
98-
LF_DEBUG(FED, "FedOutConn %p sending tagged message with tag=%" PRId64 ":%" PRIu32, trigger, tagged_msg->tag.time,
99-
tagged_msg->tag.microstep);
100-
if (channel->send_blocking(channel, &msg) != LF_OK) {
101-
LF_ERR(FED, "FedOutConn %p failed to send message", trigger);
95+
ssize_t msg_size = (*self->bundle->serialize_hooks[self->conn_id])(
96+
self->staged_payload_ptr, self->payload_pool.size, tagged_msg->payload.bytes);
97+
if (msg_size < 0) {
98+
LF_ERR(FED, "Failed to serialize payload for federated output connection %p", trigger);
99+
} else {
100+
tagged_msg->payload.size = msg_size;
101+
102+
LF_DEBUG(FED, "FedOutConn %p sending tagged message with tag=%" PRId64 ":%" PRIu32, trigger, tagged_msg->tag.time,
103+
tagged_msg->tag.microstep);
104+
if (channel->send_blocking(channel, &msg) != LF_OK) {
105+
LF_ERR(FED, "FedOutConn %p failed to send message", trigger);
106+
}
102107
}
103108
} else {
104109
LF_WARN(FED, "FedOutConn %p not connected. Dropping staged message", trigger);
@@ -321,10 +326,12 @@ void FederatedConnectionBundle_validate(FederatedConnectionBundle *bundle) {
321326
validate(bundle->inputs[i]);
322327
validate(bundle->deserialize_hooks[i]);
323328
validate(bundle->inputs[i]->super.super.parent);
329+
validate(bundle->inputs[i]->super.super.payload_pool->size < SERIALIZATION_MAX_PAYLOAD_SIZE);
324330
}
325331
for (size_t i = 0; i < bundle->outputs_size; i++) {
326332
validate(bundle->outputs[i]);
327333
validate(bundle->serialize_hooks[i]);
328334
validate(bundle->outputs[i]->super.super.parent);
335+
validate(bundle->outputs[i]->super.super.payload_pool->size < SERIALIZATION_MAX_PAYLOAD_SIZE);
329336
}
330337
}

src/serialization.c

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,17 @@ int deserialize_from_protobuf(FederateMessage *message, const unsigned char *buf
3131
}
3232

3333
lf_ret_t deserialize_payload_default(void *user_struct, const unsigned char *msg_buf, size_t msg_size) {
34-
memcpy(user_struct, msg_buf, MIN(msg_size, 832)); // TODO: 832 is a magic number
34+
if (msg_size > SERIALIZATION_MAX_PAYLOAD_SIZE) {
35+
return LF_ERR;
36+
}
37+
memcpy(user_struct, msg_buf, msg_size);
3538
return LF_OK;
3639
}
3740

38-
size_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf) {
39-
memcpy(msg_buf, user_struct, MIN(user_struct_size, 832)); // TODO: 832 is a magic number
40-
return MIN(user_struct_size, 832); // TODO: 832 is a magic number
41+
ssize_t serialize_payload_default(const void *user_struct, size_t user_struct_size, unsigned char *msg_buf) {
42+
if (user_struct_size > SERIALIZATION_MAX_PAYLOAD_SIZE) {
43+
return -1;
44+
}
45+
memcpy(msg_buf, user_struct, user_struct_size);
46+
return user_struct_size;
4147
}

0 commit comments

Comments
 (0)