Add Stream Batching Buffer (#916)

The difference between a stream buffer and a stream batching buffer is when
a task performs read on a non-empty buffer:
- The task reading from a non-empty stream buffer returns immediately
   regardless of the amount of data in the buffer.
- The task reading from a non-empty steam batching buffer blocks until the
   amount of data in the buffer exceeds the trigger level or the block time
   expires.
pull/1031/head^2
Caleb Perkinson 10 months ago committed by GitHub
parent 5a72344c9a
commit f69b1db45c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -982,15 +982,15 @@
#endif #endif
#ifndef traceSTREAM_BUFFER_CREATE_FAILED #ifndef traceSTREAM_BUFFER_CREATE_FAILED
#define traceSTREAM_BUFFER_CREATE_FAILED( xIsMessageBuffer ) #define traceSTREAM_BUFFER_CREATE_FAILED( xStreamBufferType )
#endif #endif
#ifndef traceSTREAM_BUFFER_CREATE_STATIC_FAILED #ifndef traceSTREAM_BUFFER_CREATE_STATIC_FAILED
#define traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xIsMessageBuffer ) #define traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xStreamBufferType )
#endif #endif
#ifndef traceSTREAM_BUFFER_CREATE #ifndef traceSTREAM_BUFFER_CREATE
#define traceSTREAM_BUFFER_CREATE( pxStreamBuffer, xIsMessageBuffer ) #define traceSTREAM_BUFFER_CREATE( pxStreamBuffer, xStreamBufferType )
#endif #endif
#ifndef traceSTREAM_BUFFER_DELETE #ifndef traceSTREAM_BUFFER_DELETE
@ -2402,7 +2402,7 @@
#endif #endif
#ifndef traceENTER_xStreamBufferGenericCreate #ifndef traceENTER_xStreamBufferGenericCreate
#define traceENTER_xStreamBufferGenericCreate( xBufferSizeBytes, xTriggerLevelBytes, xIsMessageBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) #define traceENTER_xStreamBufferGenericCreate( xBufferSizeBytes, xTriggerLevelBytes, xStreamBufferType, pxSendCompletedCallback, pxReceiveCompletedCallback )
#endif #endif
#ifndef traceRETURN_xStreamBufferGenericCreate #ifndef traceRETURN_xStreamBufferGenericCreate
@ -2410,7 +2410,7 @@
#endif #endif
#ifndef traceENTER_xStreamBufferGenericCreateStatic #ifndef traceENTER_xStreamBufferGenericCreateStatic
#define traceENTER_xStreamBufferGenericCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, xIsMessageBuffer, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) #define traceENTER_xStreamBufferGenericCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, xStreamBufferType, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback )
#endif #endif
#ifndef traceRETURN_xStreamBufferGenericCreateStatic #ifndef traceRETURN_xStreamBufferGenericCreateStatic

@ -158,11 +158,11 @@ typedef StreamBufferHandle_t MessageBufferHandle_t;
* \ingroup MessageBufferManagement * \ingroup MessageBufferManagement
*/ */
#define xMessageBufferCreate( xBufferSizeBytes ) \ #define xMessageBufferCreate( xBufferSizeBytes ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( size_t ) 0, pdTRUE, NULL, NULL ) xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( size_t ) 0, sbTYPE_MESSAGE_BUFFER, NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 ) #if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xMessageBufferCreateWithCallback( xBufferSizeBytes, pxSendCompletedCallback, pxReceiveCompletedCallback ) \ #define xMessageBufferCreateWithCallback( xBufferSizeBytes, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( size_t ) 0, pdTRUE, ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) ) xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( size_t ) 0, sbTYPE_MESSAGE_BUFFER, ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif #endif
/** /**
@ -243,11 +243,11 @@ typedef StreamBufferHandle_t MessageBufferHandle_t;
* \ingroup MessageBufferManagement * \ingroup MessageBufferManagement
*/ */
#define xMessageBufferCreateStatic( xBufferSizeBytes, pucMessageBufferStorageArea, pxStaticMessageBuffer ) \ #define xMessageBufferCreateStatic( xBufferSizeBytes, pucMessageBufferStorageArea, pxStaticMessageBuffer ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), 0, pdTRUE, ( pucMessageBufferStorageArea ), ( pxStaticMessageBuffer ), NULL, NULL ) xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), 0, sbTYPE_MESSAGE_BUFFER, ( pucMessageBufferStorageArea ), ( pxStaticMessageBuffer ), NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 ) #if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xMessageBufferCreateStaticWithCallback( xBufferSizeBytes, pucMessageBufferStorageArea, pxStaticMessageBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) \ #define xMessageBufferCreateStaticWithCallback( xBufferSizeBytes, pucMessageBufferStorageArea, pxStaticMessageBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), 0, pdTRUE, ( pucMessageBufferStorageArea ), ( pxStaticMessageBuffer ), ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) ) xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), 0, sbTYPE_MESSAGE_BUFFER, ( pucMessageBufferStorageArea ), ( pxStaticMessageBuffer ), ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif #endif
/** /**

@ -357,12 +357,12 @@ size_t MPU_xStreamBufferNextMessageLengthBytes( StreamBufferHandle_t xStreamBuff
* with all the APIs. */ * with all the APIs. */
StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) PRIVILEGED_FUNCTION; StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) PRIVILEGED_FUNCTION;
StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
uint8_t * const pucStreamBufferStorageArea, uint8_t * const pucStreamBufferStorageArea,
StaticStreamBuffer_t * const pxStaticStreamBuffer, StaticStreamBuffer_t * const pxStaticStreamBuffer,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,

@ -62,6 +62,13 @@
#endif #endif
/* *INDENT-ON* */ /* *INDENT-ON* */
/**
* Type of stream buffer. For internal use only.
*/
#define sbTYPE_STREAM_BUFFER ( ( BaseType_t ) 0 )
#define sbTYPE_MESSAGE_BUFFER ( ( BaseType_t ) 1 )
#define sbTYPE_STREAM_BATCHING_BUFFER ( ( BaseType_t ) 2 )
/** /**
* Type by which stream buffers are referenced. For example, a call to * Type by which stream buffers are referenced. For example, a call to
* xStreamBufferCreate() returns an StreamBufferHandle_t variable that can * xStreamBufferCreate() returns an StreamBufferHandle_t variable that can
@ -157,11 +164,11 @@ typedef void (* StreamBufferCallbackFunction_t)( StreamBufferHandle_t xStreamBuf
*/ */
#define xStreamBufferCreate( xBufferSizeBytes, xTriggerLevelBytes ) \ #define xStreamBufferCreate( xBufferSizeBytes, xTriggerLevelBytes ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), pdFALSE, NULL, NULL ) xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BUFFER, NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 ) #if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xStreamBufferCreateWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pxSendCompletedCallback, pxReceiveCompletedCallback ) \ #define xStreamBufferCreateWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), pdFALSE, ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) ) xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BUFFER, ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif #endif
/** /**
@ -257,11 +264,199 @@ typedef void (* StreamBufferCallbackFunction_t)( StreamBufferHandle_t xStreamBuf
*/ */
#define xStreamBufferCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer ) \ #define xStreamBufferCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), pdFALSE, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), NULL, NULL ) xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BUFFER, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 ) #if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xStreamBufferCreateStaticWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) \ #define xStreamBufferCreateStaticWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), pdFALSE, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) ) xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BUFFER, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif
/**
* stream_buffer.h
*
* @code{c}
* StreamBufferHandle_t xStreamBatchingBufferCreate( size_t xBufferSizeBytes, size_t xTriggerLevelBytes );
* @endcode
*
* Creates a new stream batching buffer using dynamically allocated memory. See
* xStreamBatchingBufferCreateStatic() for a version that uses statically
* allocated memory (memory that is allocated at compile time).
*
* configSUPPORT_DYNAMIC_ALLOCATION must be set to 1 or left undefined in
* FreeRTOSConfig.h for xStreamBatchingBufferCreate() to be available.
* configUSE_STREAM_BUFFERS must be set to 1 in for FreeRTOSConfig.h for
* xStreamBatchingBufferCreate() to be available.
*
* The difference between a stream buffer and a stream batching buffer is when
* a task performs read on a non-empty buffer:
* - The task reading from a non-empty stream buffer returns immediately
* regardless of the amount of data in the buffer.
* - The task reading from a non-empty steam batching buffer blocks until the
* amount of data in the buffer exceeds the trigger level or the block time
* expires.
*
* @param xBufferSizeBytes The total number of bytes the stream batching buffer
* will be able to hold at any one time.
*
* @param xTriggerLevelBytes The number of bytes that must be in the stream
* batching buffer to unblock a task calling xStreamBufferReceive before the
* block time expires.
*
* @param pxSendCompletedCallback Callback invoked when number of bytes at least
* equal to trigger level is sent to the stream batching buffer. If the
* parameter is NULL, it will use the default implementation provided by
* sbSEND_COMPLETED macro. To enable the callback, configUSE_SB_COMPLETED_CALLBACK
* must be set to 1 in FreeRTOSConfig.h.
*
* @param pxReceiveCompletedCallback Callback invoked when more than zero bytes
* are read from a stream batching buffer. If the parameter is NULL, it will use
* the default implementation provided by sbRECEIVE_COMPLETED macro. To enable
* the callback, configUSE_SB_COMPLETED_CALLBACK must be set to 1 in
* FreeRTOSConfig.h.
*
* @return If NULL is returned, then the stream batching buffer cannot be created
* because there is insufficient heap memory available for FreeRTOS to allocate
* the stream batching buffer data structures and storage area. A non-NULL value
* being returned indicates that the stream batching buffer has been created
* successfully - the returned value should be stored as the handle to the
* created stream batching buffer.
*
* Example use:
* @code{c}
*
* void vAFunction( void )
* {
* StreamBufferHandle_t xStreamBatchingBuffer;
* const size_t xStreamBufferSizeBytes = 100, xTriggerLevel = 10;
*
* // Create a stream batching buffer that can hold 100 bytes. The memory used
* // to hold both the stream batching buffer structure and the data in the stream
* // batching buffer is allocated dynamically.
* xStreamBatchingBuffer = xStreamBatchingBufferCreate( xStreamBufferSizeBytes, xTriggerLevel );
*
* if( xStreamBatchingBuffer == NULL )
* {
* // There was not enough heap memory space available to create the
* // stream batching buffer.
* }
* else
* {
* // The stream batching buffer was created successfully and can now be used.
* }
* }
* @endcode
* \defgroup xStreamBatchingBufferCreate xStreamBatchingBufferCreate
* \ingroup StreamBatchingBufferManagement
*/
#define xStreamBatchingBufferCreate( xBufferSizeBytes, xTriggerLevelBytes ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BATCHING_BUFFER, NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xStreamBatchingBufferCreateWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreate( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BATCHING_BUFFER, ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif
/**
* stream_buffer.h
*
* @code{c}
* StreamBufferHandle_t xStreamBatchingBufferCreateStatic( size_t xBufferSizeBytes,
* size_t xTriggerLevelBytes,
* uint8_t *pucStreamBufferStorageArea,
* StaticStreamBuffer_t *pxStaticStreamBuffer );
* @endcode
* Creates a new stream batching buffer using statically allocated memory. See
* xStreamBatchingBufferCreate() for a version that uses dynamically allocated
* memory.
*
* configSUPPORT_STATIC_ALLOCATION must be set to 1 in FreeRTOSConfig.h for
* xStreamBatchingBufferCreateStatic() to be available. configUSE_STREAM_BUFFERS
* must be set to 1 in for FreeRTOSConfig.h for xStreamBatchingBufferCreateStatic()
* to be available.
*
* The difference between a stream buffer and a stream batching buffer is when
* a task performs read on a non-empty buffer:
* - The task reading from a non-empty stream buffer returns immediately
* regardless of the amount of data in the buffer.
* - The task reading from a non-empty steam batching buffer blocks until the
* amount of data in the buffer exceeds the trigger level or the block time
* expires.
*
* @param xBufferSizeBytes The size, in bytes, of the buffer pointed to by the
* pucStreamBufferStorageArea parameter.
*
* @param xTriggerLevelBytes The number of bytes that must be in the stream
* batching buffer to unblock a task calling xStreamBufferReceive before the
* block time expires.
*
* @param pucStreamBufferStorageArea Must point to a uint8_t array that is at
* least xBufferSizeBytes big. This is the array to which streams are
* copied when they are written to the stream batching buffer.
*
* @param pxStaticStreamBuffer Must point to a variable of type
* StaticStreamBuffer_t, which will be used to hold the stream batching buffer's
* data structure.
*
* @param pxSendCompletedCallback Callback invoked when number of bytes at least
* equal to trigger level is sent to the stream batching buffer. If the parameter
* is NULL, it will use the default implementation provided by sbSEND_COMPLETED
* macro. To enable the callback, configUSE_SB_COMPLETED_CALLBACK must be set to
* 1 in FreeRTOSConfig.h.
*
* @param pxReceiveCompletedCallback Callback invoked when more than zero bytes
* are read from a stream batching buffer. If the parameter is NULL, it will use
* the default implementation provided by sbRECEIVE_COMPLETED macro. To enable
* the callback, configUSE_SB_COMPLETED_CALLBACK must be set to 1 in
* FreeRTOSConfig.h.
*
* @return If the stream batching buffer is created successfully then a handle
* to the created stream batching buffer is returned. If either pucStreamBufferStorageArea
* or pxStaticstreamBuffer are NULL then NULL is returned.
*
* Example use:
* @code{c}
*
* // Used to dimension the array used to hold the streams. The available space
* // will actually be one less than this, so 999.
* #define STORAGE_SIZE_BYTES 1000
*
* // Defines the memory that will actually hold the streams within the stream
* // batching buffer.
* static uint8_t ucStorageBuffer[ STORAGE_SIZE_BYTES ];
*
* // The variable used to hold the stream batching buffer structure.
* StaticStreamBuffer_t xStreamBufferStruct;
*
* void MyFunction( void )
* {
* StreamBufferHandle_t xStreamBatchingBuffer;
* const size_t xTriggerLevel = 1;
*
* xStreamBatchingBuffer = xStreamBatchingBufferCreateStatic( sizeof( ucStorageBuffer ),
* xTriggerLevel,
* ucStorageBuffer,
* &xStreamBufferStruct );
*
* // As neither the pucStreamBufferStorageArea or pxStaticStreamBuffer
* // parameters were NULL, xStreamBatchingBuffer will not be NULL, and can be
* // used to reference the created stream batching buffer in other stream
* // buffer API calls.
*
* // Other code that uses the stream batching buffer can go here.
* }
*
* @endcode
* \defgroup xStreamBatchingBufferCreateStatic xStreamBatchingBufferCreateStatic
* \ingroup StreamBatchingBufferManagement
*/
#define xStreamBatchingBufferCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BATCHING_BUFFER, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), NULL, NULL )
#if ( configUSE_SB_COMPLETED_CALLBACK == 1 )
#define xStreamBatchingBufferCreateStaticWithCallback( xBufferSizeBytes, xTriggerLevelBytes, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ) \
xStreamBufferGenericCreateStatic( ( xBufferSizeBytes ), ( xTriggerLevelBytes ), sbTYPE_STREAM_BATCHING_BUFFER, ( pucStreamBufferStorageArea ), ( pxStaticStreamBuffer ), ( pxSendCompletedCallback ), ( pxReceiveCompletedCallback ) )
#endif #endif
/** /**
@ -1053,14 +1248,14 @@ void vStreamBufferSetStreamBufferNotificationIndex( StreamBufferHandle_t xStream
/* Functions below here are not part of the public API. */ /* Functions below here are not part of the public API. */
StreamBufferHandle_t xStreamBufferGenericCreate( size_t xBufferSizeBytes, StreamBufferHandle_t xStreamBufferGenericCreate( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) PRIVILEGED_FUNCTION; StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) PRIVILEGED_FUNCTION;
#if ( configSUPPORT_STATIC_ALLOCATION == 1 ) #if ( configSUPPORT_STATIC_ALLOCATION == 1 )
StreamBufferHandle_t xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, StreamBufferHandle_t xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
uint8_t * const pucStreamBufferStorageArea, uint8_t * const pucStreamBufferStorageArea,
StaticStreamBuffer_t * const pxStaticStreamBuffer, StaticStreamBuffer_t * const pxStaticStreamBuffer,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,

@ -2404,14 +2404,14 @@
#if ( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configUSE_STREAM_BUFFERS == 1 ) ) #if ( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configUSE_STREAM_BUFFERS == 1 ) )
StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) /* FREERTOS_SYSTEM_CALL */ StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) /* FREERTOS_SYSTEM_CALL */
{ {
StreamBufferHandle_t xReturn; StreamBufferHandle_t xReturn;
/** /**
* Streambuffer application level callback functionality is disabled for MPU * Stream buffer application level callback functionality is disabled for MPU
* enabled ports. * enabled ports.
*/ */
configASSERT( ( pxSendCompletedCallback == NULL ) && configASSERT( ( pxSendCompletedCallback == NULL ) &&
@ -2427,7 +2427,7 @@
xReturn = xStreamBufferGenericCreate( xBufferSizeBytes, xReturn = xStreamBufferGenericCreate( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
NULL, NULL,
NULL ); NULL );
portMEMORY_BARRIER(); portMEMORY_BARRIER();
@ -2439,14 +2439,14 @@
{ {
xReturn = xStreamBufferGenericCreate( xBufferSizeBytes, xReturn = xStreamBufferGenericCreate( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
NULL, NULL,
NULL ); NULL );
} }
} }
else else
{ {
traceSTREAM_BUFFER_CREATE_FAILED( xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_FAILED( xStreamBufferType );
xReturn = NULL; xReturn = NULL;
} }
@ -2458,7 +2458,7 @@
#if ( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configUSE_STREAM_BUFFERS == 1 ) ) #if ( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configUSE_STREAM_BUFFERS == 1 ) )
StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
uint8_t * const pucStreamBufferStorageArea, uint8_t * const pucStreamBufferStorageArea,
StaticStreamBuffer_t * const pxStaticStreamBuffer, StaticStreamBuffer_t * const pxStaticStreamBuffer,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
@ -2467,7 +2467,7 @@
StreamBufferHandle_t xReturn; StreamBufferHandle_t xReturn;
/** /**
* Streambuffer application level callback functionality is disabled for MPU * Stream buffer application level callback functionality is disabled for MPU
* enabled ports. * enabled ports.
*/ */
configASSERT( ( pxSendCompletedCallback == NULL ) && configASSERT( ( pxSendCompletedCallback == NULL ) &&
@ -2483,7 +2483,7 @@
xReturn = xStreamBufferGenericCreateStatic( xBufferSizeBytes, xReturn = xStreamBufferGenericCreateStatic( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
pucStreamBufferStorageArea, pucStreamBufferStorageArea,
pxStaticStreamBuffer, pxStaticStreamBuffer,
NULL, NULL,
@ -2497,7 +2497,7 @@
{ {
xReturn = xStreamBufferGenericCreateStatic( xBufferSizeBytes, xReturn = xStreamBufferGenericCreateStatic( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
pucStreamBufferStorageArea, pucStreamBufferStorageArea,
pxStaticStreamBuffer, pxStaticStreamBuffer,
NULL, NULL,
@ -2506,7 +2506,7 @@
} }
else else
{ {
traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xStreamBufferType );
xReturn = NULL; xReturn = NULL;
} }

@ -4662,7 +4662,7 @@
StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) /* PRIVILEGED_FUNCTION */ StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) /* PRIVILEGED_FUNCTION */
{ {
@ -4686,7 +4686,7 @@
{ {
xInternalStreamBufferHandle = xStreamBufferGenericCreate( xBufferSizeBytes, xInternalStreamBufferHandle = xStreamBufferGenericCreate( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
NULL, NULL,
NULL ); NULL );
@ -4703,7 +4703,7 @@
} }
else else
{ {
traceSTREAM_BUFFER_CREATE_FAILED( xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_FAILED( xStreamBufferType );
xExternalStreamBufferHandle = NULL; xExternalStreamBufferHandle = NULL;
} }
@ -4717,7 +4717,7 @@
StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
uint8_t * const pucStreamBufferStorageArea, uint8_t * const pucStreamBufferStorageArea,
StaticStreamBuffer_t * const pxStaticStreamBuffer, StaticStreamBuffer_t * const pxStaticStreamBuffer,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
@ -4743,7 +4743,7 @@
{ {
xInternalStreamBufferHandle = xStreamBufferGenericCreateStatic( xBufferSizeBytes, xInternalStreamBufferHandle = xStreamBufferGenericCreateStatic( xBufferSizeBytes,
xTriggerLevelBytes, xTriggerLevelBytes,
xIsMessageBuffer, xStreamBufferType,
pucStreamBufferStorageArea, pucStreamBufferStorageArea,
pxStaticStreamBuffer, pxStaticStreamBuffer,
NULL, NULL,
@ -4762,7 +4762,7 @@
} }
else else
{ {
traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xStreamBufferType );
xExternalStreamBufferHandle = NULL; xExternalStreamBufferHandle = NULL;
} }

@ -224,6 +224,7 @@
/* Bits stored in the ucFlags field of the stream buffer. */ /* Bits stored in the ucFlags field of the stream buffer. */
#define sbFLAGS_IS_MESSAGE_BUFFER ( ( uint8_t ) 1 ) /* Set if the stream buffer was created as a message buffer, in which case it holds discrete messages rather than a stream. */ #define sbFLAGS_IS_MESSAGE_BUFFER ( ( uint8_t ) 1 ) /* Set if the stream buffer was created as a message buffer, in which case it holds discrete messages rather than a stream. */
#define sbFLAGS_IS_STATICALLY_ALLOCATED ( ( uint8_t ) 2 ) /* Set if the stream buffer was created using statically allocated memory. */ #define sbFLAGS_IS_STATICALLY_ALLOCATED ( ( uint8_t ) 2 ) /* Set if the stream buffer was created using statically allocated memory. */
#define sbFLAGS_IS_BATCHING_BUFFER ( ( uint8_t ) 4 ) /* Set if the stream buffer was created as a batching buffer, meaning the receiver task will only unblock when the trigger level exceededs. */
/*-----------------------------------------------------------*/ /*-----------------------------------------------------------*/
@ -329,25 +330,31 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
#if ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) #if ( configSUPPORT_DYNAMIC_ALLOCATION == 1 )
StreamBufferHandle_t xStreamBufferGenericCreate( size_t xBufferSizeBytes, StreamBufferHandle_t xStreamBufferGenericCreate( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
StreamBufferCallbackFunction_t pxReceiveCompletedCallback ) StreamBufferCallbackFunction_t pxReceiveCompletedCallback )
{ {
void * pvAllocatedMemory; void * pvAllocatedMemory;
uint8_t ucFlags; uint8_t ucFlags;
traceENTER_xStreamBufferGenericCreate( xBufferSizeBytes, xTriggerLevelBytes, xIsMessageBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ); traceENTER_xStreamBufferGenericCreate( xBufferSizeBytes, xTriggerLevelBytes, xStreamBufferType, pxSendCompletedCallback, pxReceiveCompletedCallback );
/* In case the stream buffer is going to be used as a message buffer /* In case the stream buffer is going to be used as a message buffer
* (that is, it will hold discrete messages with a little meta data that * (that is, it will hold discrete messages with a little meta data that
* says how big the next message is) check the buffer will be large enough * says how big the next message is) check the buffer will be large enough
* to hold at least one message. */ * to hold at least one message. */
if( xIsMessageBuffer == pdTRUE ) if( xStreamBufferType == sbTYPE_MESSAGE_BUFFER )
{ {
/* Is a message buffer but not statically allocated. */ /* Is a message buffer but not statically allocated. */
ucFlags = sbFLAGS_IS_MESSAGE_BUFFER; ucFlags = sbFLAGS_IS_MESSAGE_BUFFER;
configASSERT( xBufferSizeBytes > sbBYTES_TO_STORE_MESSAGE_LENGTH ); configASSERT( xBufferSizeBytes > sbBYTES_TO_STORE_MESSAGE_LENGTH );
} }
else if( xStreamBufferType == sbTYPE_STREAM_BATCHING_BUFFER )
{
/* Is a batching buffer but not statically allocated. */
ucFlags = sbFLAGS_IS_BATCHING_BUFFER;
configASSERT( xBufferSizeBytes > 0 );
}
else else
{ {
/* Not a message buffer and not statically allocated. */ /* Not a message buffer and not statically allocated. */
@ -398,11 +405,11 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
pxSendCompletedCallback, pxSendCompletedCallback,
pxReceiveCompletedCallback ); pxReceiveCompletedCallback );
traceSTREAM_BUFFER_CREATE( ( ( StreamBuffer_t * ) pvAllocatedMemory ), xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE( ( ( StreamBuffer_t * ) pvAllocatedMemory ), xStreamBufferType );
} }
else else
{ {
traceSTREAM_BUFFER_CREATE_FAILED( xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_FAILED( xStreamBufferType );
} }
traceRETURN_xStreamBufferGenericCreate( pvAllocatedMemory ); traceRETURN_xStreamBufferGenericCreate( pvAllocatedMemory );
@ -419,7 +426,7 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
StreamBufferHandle_t xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, StreamBufferHandle_t xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes,
size_t xTriggerLevelBytes, size_t xTriggerLevelBytes,
BaseType_t xIsMessageBuffer, BaseType_t xStreamBufferType,
uint8_t * const pucStreamBufferStorageArea, uint8_t * const pucStreamBufferStorageArea,
StaticStreamBuffer_t * const pxStaticStreamBuffer, StaticStreamBuffer_t * const pxStaticStreamBuffer,
StreamBufferCallbackFunction_t pxSendCompletedCallback, StreamBufferCallbackFunction_t pxSendCompletedCallback,
@ -432,7 +439,7 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
StreamBufferHandle_t xReturn; StreamBufferHandle_t xReturn;
uint8_t ucFlags; uint8_t ucFlags;
traceENTER_xStreamBufferGenericCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, xIsMessageBuffer, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback ); traceENTER_xStreamBufferGenericCreateStatic( xBufferSizeBytes, xTriggerLevelBytes, xStreamBufferType, pucStreamBufferStorageArea, pxStaticStreamBuffer, pxSendCompletedCallback, pxReceiveCompletedCallback );
configASSERT( pucStreamBufferStorageArea ); configASSERT( pucStreamBufferStorageArea );
configASSERT( pxStaticStreamBuffer ); configASSERT( pxStaticStreamBuffer );
@ -450,12 +457,18 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
* says how big the next message is) check the buffer will be large enough * says how big the next message is) check the buffer will be large enough
* to hold at least one message. */ * to hold at least one message. */
if( xIsMessageBuffer != pdFALSE ) if( xStreamBufferType == sbTYPE_MESSAGE_BUFFER )
{ {
/* Statically allocated message buffer. */ /* Statically allocated message buffer. */
ucFlags = sbFLAGS_IS_MESSAGE_BUFFER | sbFLAGS_IS_STATICALLY_ALLOCATED; ucFlags = sbFLAGS_IS_MESSAGE_BUFFER | sbFLAGS_IS_STATICALLY_ALLOCATED;
configASSERT( xBufferSizeBytes > sbBYTES_TO_STORE_MESSAGE_LENGTH ); configASSERT( xBufferSizeBytes > sbBYTES_TO_STORE_MESSAGE_LENGTH );
} }
else if( xStreamBufferType == sbTYPE_STREAM_BATCHING_BUFFER )
{
/* Statically allocated batching buffer. */
ucFlags = sbFLAGS_IS_BATCHING_BUFFER | sbFLAGS_IS_STATICALLY_ALLOCATED;
configASSERT( xBufferSizeBytes > 0 );
}
else else
{ {
/* Statically allocated stream buffer. */ /* Statically allocated stream buffer. */
@ -486,7 +499,7 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
* again. */ * again. */
pxStreamBuffer->ucFlags |= sbFLAGS_IS_STATICALLY_ALLOCATED; pxStreamBuffer->ucFlags |= sbFLAGS_IS_STATICALLY_ALLOCATED;
traceSTREAM_BUFFER_CREATE( pxStreamBuffer, xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE( pxStreamBuffer, xStreamBufferType );
/* MISRA Ref 11.3.1 [Misaligned access] */ /* MISRA Ref 11.3.1 [Misaligned access] */
/* More details at: https://github.com/FreeRTOS/FreeRTOS-Kernel/blob/main/MISRA.md#rule-113 */ /* More details at: https://github.com/FreeRTOS/FreeRTOS-Kernel/blob/main/MISRA.md#rule-113 */
@ -496,7 +509,7 @@ static void prvInitialiseNewStreamBuffer( StreamBuffer_t * const pxStreamBuffer,
else else
{ {
xReturn = NULL; xReturn = NULL;
traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xIsMessageBuffer ); traceSTREAM_BUFFER_CREATE_STATIC_FAILED( xReturn, xStreamBufferType );
} }
traceRETURN_xStreamBufferGenericCreateStatic( xReturn ); traceRETURN_xStreamBufferGenericCreateStatic( xReturn );
@ -1053,6 +1066,12 @@ size_t xStreamBufferReceive( StreamBufferHandle_t xStreamBuffer,
{ {
xBytesToStoreMessageLength = sbBYTES_TO_STORE_MESSAGE_LENGTH; xBytesToStoreMessageLength = sbBYTES_TO_STORE_MESSAGE_LENGTH;
} }
else if( ( pxStreamBuffer->ucFlags & sbFLAGS_IS_BATCHING_BUFFER ) != ( uint8_t ) 0 )
{
/* Force task to block if the batching buffer contains less bytes than
* the trigger level. */
xBytesToStoreMessageLength = pxStreamBuffer->xTriggerLevelBytes;
}
else else
{ {
xBytesToStoreMessageLength = 0; xBytesToStoreMessageLength = 0;
@ -1070,7 +1089,9 @@ size_t xStreamBufferReceive( StreamBufferHandle_t xStreamBuffer,
* xBytesToStoreMessageLength holds the number of bytes used to hold * xBytesToStoreMessageLength holds the number of bytes used to hold
* the length of the next discrete message. If this function was * the length of the next discrete message. If this function was
* invoked by a stream buffer read then xBytesToStoreMessageLength will * invoked by a stream buffer read then xBytesToStoreMessageLength will
* be 0. */ * be 0. If this function was invoked by a stream batch buffer read
* then xBytesToStoreMessageLength will be xTriggerLevelBytes value
* for the buffer.*/
if( xBytesAvailable <= xBytesToStoreMessageLength ) if( xBytesAvailable <= xBytesToStoreMessageLength )
{ {
/* Clear notification state as going to wait for data. */ /* Clear notification state as going to wait for data. */

Loading…
Cancel
Save