git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@8620 35acf78f-673a-0410-8e92-d51de3d6d3f4

This commit is contained in:
Giovanni Di Sirio 2015-12-20 10:25:41 +00:00
parent ddcc89f8d1
commit a952f3cfaf
2 changed files with 80 additions and 6 deletions

View File

@ -94,8 +94,13 @@ struct io_buffers_queue {
uint8_t *buffers; uint8_t *buffers;
/** /**
* @brief Pointer for R/W sequential access. * @brief Pointer for R/W sequential access.
* @note It is @p NULL if a new buffer must be fetched from the queue.
*/ */
uint8_t *ptr; uint8_t *ptr;
/**
* @brief Boundary for R/W sequential access.
*/
uint8_t *top;
/** /**
* @brief Data notification callback. * @brief Data notification callback.
*/ */
@ -156,7 +161,7 @@ typedef io_buffers_queue_t output_buffers_queue_t;
* *
* @iclass * @iclass
*/ */
#define iqbIsEmptyI(ibqp) ((bool)(bqSpaceI(ibqp) == 0U)) #define ibqIsEmptyI(ibqp) ((bool)(bqSpaceI(ibqp) == 0U))
/** /**
* @brief Evaluates to @p TRUE if the specified input buffered queue is full. * @brief Evaluates to @p TRUE if the specified input buffered queue is full.

View File

@ -71,12 +71,13 @@ void ibqObjectInit(input_buffers_queue_t *ibqp, uint8_t *bp,
ibqp->bn = n; ibqp->bn = n;
ibqp->buffers = bp; ibqp->buffers = bp;
ibqp->ptr = NULL; ibqp->ptr = NULL;
ibqp->top = NULL;
ibqp->notify = infy; ibqp->notify = infy;
ibqp->link = link; ibqp->link = link;
} }
/** /**
* @brief Gets a buffer for posting in the queue. * @brief Gets the next empty buffer from the queue.
* @note The function always returns the same buffer if called repeatedly. * @note The function always returns the same buffer if called repeatedly.
* *
* @param[out] ibqp pointer to the @p input_buffers_queue_t object * @param[out] ibqp pointer to the @p input_buffers_queue_t object
@ -85,7 +86,7 @@ void ibqObjectInit(input_buffers_queue_t *ibqp, uint8_t *bp,
* *
* @iclass * @iclass
*/ */
uint8_t *ibqGetNextBufferI(input_buffers_queue_t *ibqp) { uint8_t *ibqGetEmptyBufferI(input_buffers_queue_t *ibqp) {
osalDbgCheckClassI(); osalDbgCheckClassI();
@ -97,7 +98,7 @@ uint8_t *ibqGetNextBufferI(input_buffers_queue_t *ibqp) {
} }
/** /**
* @brief Posts a buffer in the queue. * @brief Posts a new filled buffer in the queue.
* *
* @param[out] ibqp pointer to the @p input_buffers_queue_t object * @param[out] ibqp pointer to the @p input_buffers_queue_t object
* @param[in] size used size of the buffer * @param[in] size used size of the buffer
@ -107,7 +108,7 @@ uint8_t *ibqGetNextBufferI(input_buffers_queue_t *ibqp) {
void ibqPostBufferI(io_buffers_queue_t *ibqp, size_t size) { void ibqPostBufferI(io_buffers_queue_t *ibqp, size_t size) {
osalDbgCheckClassI(); osalDbgCheckClassI();
osalDbgAssert(!ibqIsFullI(ibqp), "buffered queue full"); osalDbgAssert(!ibqIsFullI(ibqp), "buffers queue full");
/* Writing size field in the buffer.*/ /* Writing size field in the buffer.*/
*((size_t *)ibqp->bwrptr) = size; *((size_t *)ibqp->bwrptr) = size;
@ -123,6 +124,52 @@ void ibqPostBufferI(io_buffers_queue_t *ibqp, size_t size) {
osalThreadDequeueNextI(&ibqp->waiting, MSG_OK); osalThreadDequeueNextI(&ibqp->waiting, MSG_OK);
} }
/**
* @brief Gets the next filled buffer from the queue.
* @note The function always returns the same buffer if called repeatedly.
*
* @param[out] ibqp pointer to the @p input_buffers_queue_t object
* @return A pointer to the next buffer to be filled.
* @retval NULL if the queue is empty.
*
* @iclass
*/
uint8_t *ibqGetFullBufferI(input_buffers_queue_t *ibqp) {
osalDbgCheckClassI();
if (ibqIsEmptyI(ibqp)) {
return NULL;
}
return ibqp->brdptr + sizeof (size_t);
}
/**
* @brief Releases the next filled buffer back in the queue.
*
* @param[out] ibqp pointer to the @p input_buffers_queue_t object
*
* @iclass
*/
void ibqReleaseBufferI(io_buffers_queue_t *ibqp) {
osalDbgCheckClassI();
osalDbgAssert(!ibqIsEmptyI(ibqp), "buffers queue empty");
/* Freeing a buffer slot in the queue.*/
ibqp->bcounter--;
ibqp->brdptr += ibqp->bsize;
if (ibqp->brdptr >= ibqp->btop) {
ibqp->brdptr = ibqp->buffers;
}
/* Notifying the buffer release.*/
if (ibqp->notify != NULL) {
ibqp->notify(ibqp);
}
}
/** /**
* @brief Input queue read with timeout. * @brief Input queue read with timeout.
* @details This function reads a byte value from an input queue. If * @details This function reads a byte value from an input queue. If
@ -144,7 +191,29 @@ void ibqPostBufferI(io_buffers_queue_t *ibqp, size_t size) {
* @api * @api
*/ */
msg_t ibqGetTimeout(input_buffers_queue_t *ibqp, systime_t timeout) { msg_t ibqGetTimeout(input_buffers_queue_t *ibqp, systime_t timeout) {
msg_t msg;
/* This condition indicates that a new buffer must be acquired.*/
while (ibqp->ptr == NULL) {
msg = osalThreadEnqueueTimeoutS(&ibqp->waiting, timeout);
if (msg < MSG_OK) {
return msg;
}
ibqp->ptr = ibqGetFullBufferI(ibqp);
}
/* Next byte from the buffer.*/
msg = *ibqp->ptr;
ibqp->ptr++;
/* If the current buffer has been fully read then it is returned as
empty in the queue.*/
if (ibqp->ptr == ibqp->top) {
ibqReleaseBufferI(ibqp);
ibqp->ptr = NULL;
}
return msg;
} }
/** /**