cleanup: Make group packet entry creation less error-prone

We always assumed that create_array_entry() would only be called
with an empty array entry and wouldn't modify entries on error.
We now explicitly require both conditions, and also give an
error in the case of a non-null data pointer with a zero
length field, as this indicates a logic error.

Checks for an empty array entry that precede a call to
create_array_entry() are now redundant. It should be noted that
a non-empty entry doesn't necessarily indicate an error. This
condition can be triggered if packets are being sent or
received faster than they can be processed/acknowledged,
which is common when spamming messages on poor connections.
This commit is contained in:
jfreegman 2024-01-11 10:55:10 -05:00
parent 5b9c420ce1
commit 6b6718e4d2
No known key found for this signature in database
GPG Key ID: 3627F3144076AE63
2 changed files with 20 additions and 22 deletions

View File

@ -1 +1 @@
423687bc6adc323174a2ab4e2ee8443e6c21c4d6509942af469b4bc16db6bfa4 /usr/local/bin/tox-bootstrapd c98b35f18f351c9a3a05137e69a43e634ab5963d364b9337e89ad89469ebd8c2 /usr/local/bin/tox-bootstrapd

View File

@ -85,18 +85,32 @@ void gcc_set_recv_message_id(GC_Connection *gconn, uint64_t id)
} }
/** @brief Puts packet data in array_entry. /** @brief Puts packet data in array_entry.
*
* Requires an empty array entry to be passed, and must not modify the passed
* array entry on error.
* *
* Return true on success. * Return true on success.
*/ */
non_null(1, 2) nullable(3) non_null(1, 2, 3) nullable(4)
static bool create_array_entry(const Mono_Time *mono_time, GC_Message_Array_Entry *array_entry, const uint8_t *data, static bool create_array_entry(const Logger *log, const Mono_Time *mono_time, GC_Message_Array_Entry *array_entry,
uint16_t length, uint8_t packet_type, uint64_t message_id) const uint8_t *data, uint16_t length, uint8_t packet_type, uint64_t message_id)
{ {
if (!array_entry_is_empty(array_entry)) {
LOGGER_WARNING(log, "Failed to create array entry; entry is not empty.");
return false;
}
if (length == 0) { if (length == 0) {
if (data != nullptr) {
LOGGER_FATAL(log, "Got non-null data with zero length (type %d)", packet_type); // should never happen
return false;
}
array_entry->data = nullptr; array_entry->data = nullptr;
array_entry->data_length = 0; array_entry->data_length = 0;
} else { } else {
if (data == nullptr) { if (data == nullptr) {
LOGGER_FATAL(log, "Got null data with non-zero length (type %u)", packet_type); // should never happen
return false; return false;
} }
@ -138,13 +152,7 @@ static bool add_to_send_array(const Logger *log, const Mono_Time *mono_time, GC_
const uint16_t idx = gcc_get_array_index(gconn->send_message_id); const uint16_t idx = gcc_get_array_index(gconn->send_message_id);
GC_Message_Array_Entry *array_entry = &gconn->send_array[idx]; GC_Message_Array_Entry *array_entry = &gconn->send_array[idx];
if (!array_entry_is_empty(array_entry)) { if (!create_array_entry(log, mono_time, array_entry, data, length, packet_type, gconn->send_message_id)) {
LOGGER_DEBUG(log, "Send array entry isn't empty");
return false;
}
if (!create_array_entry(mono_time, array_entry, data, length, packet_type, gconn->send_message_id)) {
LOGGER_WARNING(log, "Failed to create array entry");
return false; return false;
} }
@ -335,17 +343,7 @@ static bool store_in_recv_array(const Logger *log, const Mono_Time *mono_time, G
const uint16_t idx = gcc_get_array_index(message_id); const uint16_t idx = gcc_get_array_index(message_id);
GC_Message_Array_Entry *ary_entry = &gconn->recv_array[idx]; GC_Message_Array_Entry *ary_entry = &gconn->recv_array[idx];
if (!array_entry_is_empty(ary_entry)) { return create_array_entry(log, mono_time, ary_entry, data, length, packet_type, message_id);
LOGGER_DEBUG(log, "Recv array is not empty");
return false;
}
if (!create_array_entry(mono_time, ary_entry, data, length, packet_type, message_id)) {
LOGGER_WARNING(log, "Failed to create array entry");
return false;
}
return true;
} }
/** /**