stream_buffer: require batching buffers to exceed trigger level

Batching stream buffers are documented to unblock receivers only after the buffered byte count exceeds the trigger level, but both xStreamBufferSend() paths currently notify as soon as the count reaches it.

That equality case wakes the blocked receiver too early, causing xStreamBufferReceive() to return 0 bytes while the buffer still holds exactly trigger-level data. Route both task and ISR send paths through a shared trigger helper so batching buffers require a strict greater-than check while existing stream and message buffer semantics remain unchanged.

Fixes #1375

Signed-off-by: Asish Kumar <officialasishkumar@gmail.com>
diff --git a/stream_buffer.c b/stream_buffer.c
index 287bd07..a4c6d26 100644
--- a/stream_buffer.c
+++ b/stream_buffer.c
@@ -257,6 +257,15 @@
 static size_t prvBytesInBuffer( const StreamBuffer_t * const pxStreamBuffer ) PRIVILEGED_FUNCTION;
 
 /*
+ * Returns pdTRUE when the amount of buffered data should unblock a task that
+ * is waiting to receive data. Stream batching buffers require the buffered
+ * data to exceed the trigger level, whereas stream and message buffers unblock
+ * when the trigger level is reached.
+ */
+static BaseType_t prvBytesInBufferMeetTriggerLevel( const StreamBuffer_t * const pxStreamBuffer,
+                                                    size_t xBytesInBuffer ) PRIVILEGED_FUNCTION;
+
+/*
  * Add xCount bytes from pucData into the pxStreamBuffer's data storage area.
  * This function does not update the buffer's xHead pointer, so multiple writes
  * may be chained together "atomically". This is useful for Message Buffers where
@@ -919,7 +928,7 @@
         traceSTREAM_BUFFER_SEND( xStreamBuffer, xReturn );
 
         /* Was a task waiting for the data? */
-        if( prvBytesInBuffer( pxStreamBuffer ) >= pxStreamBuffer->xTriggerLevelBytes )
+        if( prvBytesInBufferMeetTriggerLevel( pxStreamBuffer, prvBytesInBuffer( pxStreamBuffer ) ) != pdFALSE )
         {
             prvSEND_COMPLETED( pxStreamBuffer );
         }
@@ -976,7 +985,7 @@
     if( xReturn > ( size_t ) 0 )
     {
         /* Was a task waiting for the data? */
-        if( prvBytesInBuffer( pxStreamBuffer ) >= pxStreamBuffer->xTriggerLevelBytes )
+        if( prvBytesInBufferMeetTriggerLevel( pxStreamBuffer, prvBytesInBuffer( pxStreamBuffer ) ) != pdFALSE )
         {
             /* MISRA Ref 4.7.1 [Return value shall be checked] */
             /* More details at: https://github.com/FreeRTOS/FreeRTOS-Kernel/blob/main/MISRA.md#dir-47 */
@@ -1587,6 +1596,35 @@
 }
 /*-----------------------------------------------------------*/
 
+static BaseType_t prvBytesInBufferMeetTriggerLevel( const StreamBuffer_t * const pxStreamBuffer,
+                                                    size_t xBytesInBuffer )
+{
+    BaseType_t xReturn = pdFALSE;
+
+    if( ( pxStreamBuffer->ucFlags & sbFLAGS_IS_BATCHING_BUFFER ) != ( uint8_t ) 0 )
+    {
+        if( xBytesInBuffer > pxStreamBuffer->xTriggerLevelBytes )
+        {
+            xReturn = pdTRUE;
+        }
+        else
+        {
+            mtCOVERAGE_TEST_MARKER();
+        }
+    }
+    else if( xBytesInBuffer >= pxStreamBuffer->xTriggerLevelBytes )
+    {
+        xReturn = pdTRUE;
+    }
+    else
+    {
+        mtCOVERAGE_TEST_MARKER();
+    }
+
+    return xReturn;
+}
+/*-----------------------------------------------------------*/
+
 static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
                                           uint8_t * const pucBuffer,
                                           size_t xBufferSizeBytes,