This is an automated email from the ASF dual-hosted git repository.

astitcher pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/qpid-proton.git


The following commit(s) were added to refs/heads/main by this push:
     new 67b545544 PROTON-2913: pn_message_encode could generate an illegal 
message
67b545544 is described below

commit 67b5455445de6c97fb656f83b2af3331a9d899ab
Author: Andrew Stitcher <[email protected]>
AuthorDate: Wed Dec 10 19:00:48 2025 -0500

    PROTON-2913: pn_message_encode could generate an illegal message
    
    If given a message with no message body, pn_message_encode would
    generate a message with no body which is illegal in AMQP.
    
    Would have preferred to generate an error in this case, but this would
    be a change to a very long standing behaviour.
---
 c/src/core/message.c      | 16 +++++++++++++++-
 python/proton/_message.py |  5 +++--
 2 files changed, 18 insertions(+), 3 deletions(-)

diff --git a/c/src/core/message.c b/c/src/core/message.c
index b3b1973ea..98f0d9864 100644
--- a/c/src/core/message.c
+++ b/c/src/core/message.c
@@ -730,7 +730,11 @@ int pn_message_set_reply_to_group_id(pn_message_t *msg, 
const char *reply_to_gro
 
 int pn_message_decode(pn_message_t *msg, const char *bytes, size_t size)
 {
-  assert(msg && bytes && size);
+  assert(msg);
+
+  if (!bytes || !size) {
+    return pn_error_format(msg->error, PN_ARG_ERR, "invalid message bytes");
+  }
 
   pn_bytes_t msg_bytes = {.size=size, .start=bytes};
   pn_bytes_t instructions_bytes = {0, 0};
@@ -852,6 +856,7 @@ int pn_message_encode(pn_message_t *msg, char *bytes, 
size_t *isize)
   if (!pni_switch_to_raw_bytes(scratch, &msg->body_deprecated, 
&msg->body_raw)) {
     return PN_OVERFLOW;
   }
+
   size_t remaining = *isize;
   size_t total = 0;
 
@@ -942,6 +947,15 @@ int pn_message_encode(pn_message_t *msg, char *bytes, 
size_t *isize)
     last_size = pn_amqp_encode_bytes_described_type_raw(bytes, remaining, 
descriptor, msg->body_raw);
     if (last_size > remaining) return PN_OVERFLOW;
 
+    remaining -= last_size;
+    bytes += last_size;
+    total += last_size;
+  } else {
+    // AMQP requires a body, so encode a null body if none present
+    static const char null_byte = PNE_NULL;
+    last_size = pn_amqp_encode_bytes_described_type_raw(bytes, remaining, 
AMQP_DESC_AMQP_VALUE, (pn_bytes_t){.size=1, .start=&null_byte});
+    if (last_size > remaining) return PN_OVERFLOW;
+
     remaining -= last_size;
     bytes += last_size;
     total += last_size;
diff --git a/python/proton/_message.py b/python/proton/_message.py
index f5f37e161..56e985c02 100644
--- a/python/proton/_message.py
+++ b/python/proton/_message.py
@@ -135,8 +135,9 @@ class Message:
             self._check_property_keys()
             props.put_object(self.properties)
         body.clear()
-        if self.body is not None:
-            body.put_object(self.body)
+        # Message body must be present for a valid AMQP message
+        # If it is None, encode as an explicit null
+        body.put_object(self.body)
 
     def _post_decode(self) -> None:
         inst = Data(pn_message_instructions(self._msg))


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to