Audio Statistics
During the development of your audio function, you may be interested in knowing what is happening during stream communication. The audio class offers a few statistics per AudioStreaming interface. The configuration constant USBD_AUDIO_CFG_STAT_EN
allows you to activate the audio stream statistics. You need to set it to DEF_ENABLED
.
You will have to use the structure USBD_AUDIO_STAT
in your audio application to get statistics. This structure collects long-term statistics for a given AudioStreaming interface, that is each time the corresponding stream is opened and used by the host. The statistics are not reset when the stream is closed. Audio Statistics#Listing - Getting Audio Statistics in the Application shows how to retrieve audio statistics from your application.
#if (USBD_AUDIO_CFG_STAT_EN == DEF_ENABLED) (1) USBD_AUDIO_STAT *App_SpeakerStatPtr; (2) USBD_AUDIO_STAT *App_MicStatPtr; #endif (3) static void App_USBD_Audio_Conn (CPU_INT08U dev_nbr, CPU_INT08U cfg_nbr, CPU_INT08U terminal_id, USBD_AUDIO_AS_HANDLE as_handle); const USBD_AUDIO_EVENT_FNCTS App_USBD_Audio_EventFncts = { App_USBD_Audio_Conn, App_USBD_Audio_Disconn }; CPU_BOOLEAN App_USBD_Audio_Init (CPU_INT08U dev_nbr, CPU_INT08U cfg_hs, CPU_INT08U cfg_fs) { ... audio_nbr = USBD_Audio_Add(APP_CFG_USBD_AUDIO_NBR_ENTITY, &USBD_Audio_DrvCommonAPI_Simulation, &App_USBD_Audio_EventFncts, (4) &err); if (err != USBD_ERR_NONE) { /* $$$$ Handle the error. */ } ... return (DEF_OK); } (5) static void App_USBD_Audio_Conn(CPU_INT08U dev_nbr, CPU_INT08U cfg_nbr, CPU_INT08U terminal_id, USBD_AUDIO_AS_HANDLE as_handle) { (void)&dev_nbr; (void)&cfg_nbr; #if (USBD_AUDIO_CFG_STAT_EN == DEF_ENABLED) if (terminal_id == Mic_OT_USB_IN_ID) { (6) App_MicStatPtr = USBD_Audio_AS_IF_StatGet(as_handle); } else if (terminal_id == Speaker_IT_USB_OUT_ID) { App_SpeakerStatPtr = USBD_Audio_AS_IF_StatGet(as_handle); } #else (void)&terminal_id; (void)&p_as_if_arg; #endif }
(1) Your debug code for audio statistics could be surrounded by some preprocessor directives testing USBD_AUDIO_CFG_STAT_EN
.
(2) Declare a pointer to an USBD_AUDIO_STAT
structure. You can have one pointer per stream you want to follow. In the example, the pointers App_SpeakerStatPtr
and App_MicStatPtr
allows respectively to monitor the speaker and record streams.
(3) Declare a connection event function that will be called by the audio class when the device configuration is selected by the host. In this example, the function named App_USBD_Audio_Conn()
will allow you to retrieve references to the speaker and record stream statistics structures. This function will initialize a function pointer from the audio event structure USBD_AUDIO_EVENT_FNCTS
.
(4) When creating an audio class instance with USBD_Audio_Add()
, the third argument will be a reference to the structure containing the connection event function.
(5) The audio class will call App_USBD_Audio_Conn()
for each AudioStreaming interface.
(6) Call the function USBD_Audio_AS_IF_StatGet()
to get statistics about the microphone in the example. The audio class will return a reference to the USBD_AUDIO_STAT
structure assigned to the microphone stream. This reference is kept by the pointer App_MicStatPtr
. You may have to check the terminal ID if you have several audio streams statistics to retrieve. For each stream, call again USBD_Audio_AS_IF_StatGet()
. The audio statistics structure can be consulted during debug operations in a watch window for instance.
Table - USBD_AUDIO_STAT Structure Fields Description gives more details about the fields of USBD_AUDIO_STAT
structure. The fields are basically counters that are incremented to follow a certain statistic. Counters are placed strategically inside the audio class to monitor the stream communication.The column "Description" will refer to the stream data flow. Refer to Audio Class Stream Data Flow as a complement to fully understand counters.
Field | Description | Description |
---|---|---|
Related to Playback | ||
AudioProc_Playback_NbrIsocRxSubmitSuccess | Total number of isochronous OUT transfers successfully submitted to the USB device driver. The sum of AudioProc_Playback_NbrIsocRxSubmitPlaybackTask with AudioProc_Playback_NbrIsocRxSubmitCoreTask should be equal to this counter when a stream is closed. | Total number of isochronous OUT transfers successfully submitted to the USB device driver. The sum of AudioProc_Playback_NbrIsocRxSubmitPlaybackTask with AudioProc_Playback_NbrIsocRxSubmitCoreTask should be equal to this counter when a stream is closed. |
AudioProc_Playback_NbrIsocRxSubmitErr | Number of isochronous OUT transfers submitted to the USB device driver with an error. | Number of isochronous OUT transfers submitted to the USB device driver with an error. |
AudioProc_Playback_NbrIsocRxSubmitPlaybackTask | Number of isochronous OUT transfers successfully submitted by the Playback task. | Number of isochronous OUT transfers successfully submitted by the Playback task. |
AudioProc_Playback_NbrIsocRxSubmitCoreTask | Number of isochronous OUT transfers successfully submitted by the Core task. | Number of isochronous OUT transfers successfully submitted by the Core task. |
AudioProc_Playback_NbrIsocRxCmpl | Number of isochronous OUT transfers completed with or without error. That is | Number of isochronous OUT transfers completed with or without error. That is |
AudioProc_Playback_NbrIsocRxCmplErrOther | Number of isochronous OUT transfers completed with an error different from | Number of isochronous OUT transfers completed with an error different from |
AudioProc_Playback_NbrIsocRxCmplErrAbort | Number of isochronous OUT transfers completed with the error code USBD_ERR_EP_ABORT . When a stream closes, a few isochronous transfers may be pending in the USB device driver, the Core task aborts all pending transfers by calling
USBD_Audio_
Playback
IsocCmpl()
with the error code
USBD_ERR_EP_ABORT
. This error code is a normal error. | Number of isochronous OUT transfers completed with the error code USBD_ERR_EP_ABORT . When a stream closes, a few isochronous transfers may be pending in the USB device driver, the Core task aborts all pending transfers by calling
USBD_Audio_
Playback
IsocCmpl()
with the error code
USBD_ERR_EP_ABORT
. This error code is a normal error. |
AudioProc_Playback_NbrIsocRxBufNotAvail | Number of times no buffer available for Playback and Core tasks while preparing a new isochronous transfer. | Number of times no buffer available for Playback and Core tasks while preparing a new isochronous transfer. |
AudioProc_Playback_NbrReqPostPlaybackTask | Number of requests submitted to the Playback task. A request is a stream handle sent when opening the playback stream and each time an audio transfer is finished. At the stream closing, this counter should be equal to AudioProc_Playback_NbrReqPendPlaybackTask . | Number of requests submitted to the Playback task. A request is a stream handle sent when opening the playback stream and each time an audio transfer is finished. At the stream closing, this counter should be equal to AudioProc_Playback_NbrReqPendPlaybackTask . |
AudioProc_Playback_NbrReqPendPlaybackTask | Number of requests retrieved by the Playback task. Each time the Playback task wakes up, this counter is incremented. | Number of requests retrieved by the Playback task. Each time the Playback task wakes up, this counter is incremented. |
AudioProc_Playback_NbrIsocRxOngoingCnt | Current number of isochronous OUT transfers in progress. That is transfers have been submitted to the USB device driver but are not yet finished. A transfer is being processed or transfers are waiting to be processed by the USB device controller. | Current number of isochronous OUT transfers in progress. That is transfers have been submitted to the USB device driver but are not yet finished. A transfer is being processed or transfers are waiting to be processed by the USB device controller. |
Related to Playback Feedback: all these counters are available only if USBD_AUDIO_CFG_PLAYBACK_FEEDBACK_EN is set to DEF_ENABLED . | ||
AudioProc_Playback_SynchNbrBufGet | Number of feedback buffers obtained each time a new feedback value must be sent to the host. There is one and unique feedback buffer per stream. If a new feedback value is to be sent and the single buffer is already in use, this feedback value is lost. The counter | Number of feedback buffers obtained each time a new feedback value must be sent to the host. There is one and unique feedback buffer per stream. If a new feedback value is to be sent and the single buffer is already in use, this feedback value is lost. The counter |
AudioProc_Playback_SynchNbrBufFree
| Number of feedback buffers made available again. The unique feedback buffer is made available each time an isochronous IN transfer completes or in case of error when submitting an isochronous transfer with the function USBD_IsocTxAsync() . | Number of feedback buffers made available again. The unique feedback buffer is made available each time an isochronous IN transfer completes or in case of error when submitting an isochronous transfer with the function USBD_IsocTxAsync() . |
AudioProc_Playback_SynchNbrBufNotAvail
| Number of times the unique feedback buffer is not available because already in use. In that case, the feedback value is lost. | Number of times the unique feedback buffer is not available because already in use. In that case, the feedback value is lost. |
AudioProc_Playback_SynchNbrSafeZone
| Number of normal situations without feedback correction. | Number of normal situations without feedback correction. |
AudioProc_Playback_SynchNbrOverrun
| Number of overrun situations requiring feedback correction. | Number of overrun situations requiring feedback correction. |
AudioProc_Playback_SynchNbrLightOverrun
| Number of light overrun situations. Refer to section Playback Feedback Correction for more details about a light overrun. | Number of light overrun situations. Refer to section Playback Feedback Correction for more details about a light overrun. |
AudioProc_Playback_SynchNbrHeavyOverrun
| Number of heavy overrun situations. Refer to section Playback Feedback Correction for more details about a heavy overrun. | Number of heavy overrun situations. Refer to section Playback Feedback Correction for more details about a heavy overrun. |
AudioProc_Playback_SynchNbrUnderrun
| Number of underrun situations requiring feedback correction. | Number of underrun situations requiring feedback correction. |
AudioProc_Playback_SynchNbrLightUnderrun
| Number of light underrun situations. Refer to section Playback Feedback Correction for more details about a light underrun. | Number of light underrun situations. Refer to section Playback Feedback Correction for more details about a light underrun. |
AudioProc_Playback_SynchNbrHeavyUnderrun
| Number of heavy underrun situations. Refer to section Playback Feedback Correction for more details about a heavy underrun. | Number of heavy underrun situations. Refer to section Playback Feedback Correction for more details about a heavy underrun. |
AudioProc_Playback_SynchNbrRefreshPeriodReached
| Number of times the refresh period has been reached, The audio device reports a feedback value every bRefresh period. This bRefresh period is defined in the feedback Endpoint descriptor retrieved by the host during the enumeration. The audio class evaluates the feedback correction each time a playback buffer is received from host. When the number of frames elapsed matches the bRefresh period, a feedback value is sent. Refer to section Playback Feedback Correction for more details. | Number of times the refresh period has been reached, The audio device reports a feedback value every bRefresh period. This bRefresh period is defined in the feedback Endpoint descriptor retrieved by the host during the enumeration. The audio class evaluates the feedback correction each time a playback buffer is received from host. When the number of frames elapsed matches the bRefresh period, a feedback value is sent. Refer to section Playback Feedback Correction for more details. |
AudioProc_Playback_SynchNbrIsocTxSubmitted
| Number of isochronous IN transfers successfully submitted to the USB device driver. | Number of isochronous IN transfers successfully submitted to the USB device driver. |
AudioProc_Playback_SynchNbrIsocTxCmpl
| Number of isochronous IN transfers completed with or without an error. That is USBD_Audio_IsocPlaybackSynchCmpl () has been called by the Core task. | Number of isochronous IN transfers completed with or without an error. That is USBD_Audio_IsocPlaybackSynchCmpl () has been called by the Core task. |
Related to Record | ||
AudioProc_Record_NbrIsocTxSubmitSuccess | Total number of isochronous IN transfers successfully submitted to the USB device driver. The sum of AudioProc_Record_NbrIsocTxSubmitRecordTask
with AudioProc_Record_NbrIsocTxSubmitCoreTask should be equal to this counter when a stream is closed. | Total number of isochronous IN transfers successfully submitted to the USB device driver. The sum of AudioProc_Record_NbrIsocTxSubmitRecordTask
with AudioProc_Record_NbrIsocTxSubmitCoreTask should be equal to this counter when a stream is closed. |
AudioProc_Record_NbrIsocTxSubmitErr | Number of isochronous IN transfers submitted to the USB device driver with an error. | Number of isochronous IN transfers submitted to the USB device driver with an error. |
AudioProc_Record_NbrIsocTxSubmitRecordTask | Number of isochronous IN transfers successfully submitted by the Record task. | Number of isochronous IN transfers successfully submitted by the Record task. |
AudioProc_Record_NbrIsocTxSubmitCoreTask | Number of isochronous IN transfers successfully submitted by the Core task. | Number of isochronous IN transfers successfully submitted by the Core task. |
AudioProc_Record_NbrIsocTxCmpl | Number of isochronous IN transfers completed with or without an error. That is
USBD_Audio_RecordIsocCmpl
() has been called by the Core task. | Number of isochronous IN transfers completed with or without an error. That is
USBD_Audio_RecordIsocCmpl
() has been called by the Core task. |
AudioProc_Record_NbrIsocTxCmplErrOther | Number of isochronous IN transfers completed with an error different from USBD_ERR_EP_ABORT . That is
USBD_Audio_RecordIsocCmpl() has been called by the Core task. | Number of isochronous IN transfers completed with an error different from USBD_ERR_EP_ABORT . That is
USBD_Audio_RecordIsocCmpl() has been called by the Core task. |
AudioProc_Record_NbrIsocTxCmplErrAbort | Number of isochronous IN transfers completed with the error code USBD_ERR_EP_ABORT . When a stream closes, a few isochronous transfers may be pending in the USB device driver, the Core task aborts all pending transfers by calling USBD_Audio_RecordIsocCmpl() with the error code USBD_ERR_EP_ABORT . This error code is a normal error. | Number of isochronous IN transfers completed with the error code USBD_ERR_EP_ABORT . When a stream closes, a few isochronous transfers may be pending in the USB device driver, the Core task aborts all pending transfers by calling USBD_Audio_RecordIsocCmpl() with the error code USBD_ERR_EP_ABORT . This error code is a normal error. |
AudioProc_Record_NbrIsocTxBufNotAvail | Number of times no buffer available for Record and Core tasks while preparing a new isochronous transfer. | Number of times no buffer available for Record and Core tasks while preparing a new isochronous transfer. |
AudioProc_Record_NbrReqPostRecordTask | Number of requests submitted to the Record task. A request is a stream handle sent each time a record buffer ready to be sent to the host is signaled to the Record task by the Audio Peripheral Driver. When the stream is closed, this counter should be equal to AudioProc_Record_NbrReqPendRecordTask. | Number of requests submitted to the Record task. A request is a stream handle sent each time a record buffer ready to be sent to the host is signaled to the Record task by the Audio Peripheral Driver. When the stream is closed, this counter should be equal to AudioProc_Record_NbrReqPendRecordTask. |
AudioProc_Record_NbrReqPendRecordTask | Number of requests retrieved by the Record task. Each time the Record task wakes up, this counter is incremented. | Number of requests retrieved by the Record task. Each time the Record task wakes up, this counter is incremented. |
Related to Playback and Record | ||
AudioProc_RingBufQ_NbrProducerStartIxCatchUp | Number of times the index ProducerStart has caught up the index ConsumerEnd and/or ProducerEnd . | Number of times the index ProducerStart has caught up the index ConsumerEnd and/or ProducerEnd . |
AudioProc_RingBufQ_NbrProducerEndIxCatchUp | Number of times the index ProducerEnd has caught up the index
ProducerStart and/or
ConsumerStart
. | Number of times the index ProducerEnd has caught up the index
ProducerStart and/or
ConsumerStart
. |
AudioProc_RingBufQ_NbrConsumerStartIxCatchUp | Number of times the index ConsumerStart has caught up the index ProducerEnd and/or ConsumerEnd . | Number of times the index ConsumerStart has caught up the index ProducerEnd and/or ConsumerEnd . |
AudioProc_RingBufQ_NbrConsumerEndIxCatchUp | Number of times the index ConsumerEnd has caught up the index ConsumerStart and/or ProducerStart . | Number of times the index ConsumerEnd has caught up the index ConsumerStart and/or ProducerStart . |
AudioProc_RingBufQ_NbrProducerStartIxWrapAround | Number of wrap-around for the index ProducerStart of the ring buffer queue. | Number of wrap-around for the index ProducerStart of the ring buffer queue. |
AudioProc_RingBufQ_NbrProducerEndIxWrapAround | Number of wrap-around for the index ProducerEnd of the ring buffer queue. | Number of wrap-around for the index ProducerEnd of the ring buffer queue. |
AudioProc_RingBufQ_NbrConsumerStartIxWrapAround | Number of wrap-around for the index Consumer Start of the ring buffer queue. | Number of wrap-around for the index Consumer Start of the ring buffer queue. |
AudioProc_RingBufQ_NbrConsumerEndIxWrapAround | Number of wrap-around for the index ConsumerEnd of the ring buffer queue. | Number of wrap-around for the index ConsumerEnd of the ring buffer queue. |
AudioProc_RingBufQ_NbrBufDescInUse | Number of buffer descriptors in use by playback or record streams. Buffer descriptors are used internally by the audio class, in particular to support multi-streaming. It allows the Playback or Record task to manage buffers from different AudioStreaming interfaces. | Number of buffer descriptors in use by playback or record streams. Buffer descriptors are used internally by the audio class, in particular to support multi-streaming. It allows the Playback or Record task to manage buffers from different AudioStreaming interfaces. |
AudioProc_RingBufQ_NbrErr | Number of times there was an error getting a buffer from the ring buffer queue. | Number of times there was an error getting a buffer from the ring buffer queue. |
AudioProc_NbrStreamOpen | Number of times the stream has been open by the host. This counter is incremented when the host sends a SET_INTERFACE request to the device with a non-null alternate setting. | Number of times the stream has been open by the host. This counter is incremented when the host sends a SET_INTERFACE request to the device with a non-null alternate setting. |
AudioProc_NbrStreamClosed | Number of times the stream has been closed. This counter is incremented when the host sends a SET_INTERFACE request to the device with a null alternate setting and when an internal error within the audio class occurs requiring to mark the stream as closed. When a stream is closed and no error occurs internally, this counter should be equal to
AudioProc_NbrStreamOpen. | Number of times the stream has been closed. This counter is incremented when the host sends a SET_INTERFACE request to the device with a null alternate setting and when an internal error within the audio class occurs requiring to mark the stream as closed. When a stream is closed and no error occurs internally, this counter should be equal to
AudioProc_NbrStreamOpen. |
AudioProc_CorrNbrUnderrun | Number of underrun situations requiring built-in playback or record correction. | Number of underrun situations requiring built-in playback or record correction. |
AudioProc_CorrNbrOverrun | Number of overrun situations requiring built-in playback or record correction. | Number of overrun situations requiring built-in playback or record correction. |
AudioProc_CorrNbrSafeZone | Number of normal situations without built-in playback or record correction. | Number of normal situations without built-in playback or record correction. |
Related to Playback and Record from Audio Peripheral Driver | ||
AudioDrv_Playback_DMA_NbrXferCmpl | Number of playback buffers consumed by the Audio Peripheral Driver. By default, audio statistics are not available in the Audio Peripheral Driver. Since the Audio Peripheral Driver is written by you, you can use the macro AUDIO_DRV_STAT_INC() to increment this counter. Refer to Statistics for more details about where to use this macro. | Number of playback buffers consumed by the Audio Peripheral Driver. By default, audio statistics are not available in the Audio Peripheral Driver. Since the Audio Peripheral Driver is written by you, you can use the macro AUDIO_DRV_STAT_INC() to increment this counter. Refer to Statistics for more details about where to use this macro. |
AudioDrv_Playback_DMA_NbrSilenceBuf | Number of silence buffers consumed by the Audio Peripheral Driver. If there are no playback buffers ready to play by the codec, the driver should simply send silence buffers. This counter can be incremented with the macro AUDIO_DRV_STAT_INC()
. | Number of silence buffers consumed by the Audio Peripheral Driver. If there are no playback buffers ready to play by the codec, the driver should simply send silence buffers. This counter can be incremented with the macro AUDIO_DRV_STAT_INC()
. |
AudioDrv_Record_DMA_NbrXferCmpl | Number of record buffers produced by the Audio Peripheral Driver. You can use the macro AUDIO_DRV_STAT_INC() to increment this counter. | Number of record buffers produced by the Audio Peripheral Driver. You can use the macro AUDIO_DRV_STAT_INC() to increment this counter. |
AudioDrv_Record_DMA_NbrDummyBuf | Number of dummy buffers used by the Audio Peripheral Driver because no empty record buffers are available. If there are no record buffers available, the driver may need to falsely consume some record data while waiting for some record buffers to be free. This counter can be incremented with the macro AUDIO_DRV_STAT_INC() . | Number of dummy buffers used by the Audio Peripheral Driver because no empty record buffers are available. If there are no record buffers available, the driver may need to falsely consume some record data while waiting for some record buffers to be free. This counter can be incremented with the macro AUDIO_DRV_STAT_INC() . |