aaudio: reduce glitching by improving sleep timing
ALways sleep a minimum time to avoid busy wait in real-time thread.
Account for wakeup jitter in threads on the other side of a FIFO.
Avoid race condition that caused a longer sleep than necessary.
Fix calculation of mFreeRunning for capture mode.
Also added systrace logging, which was used to debug this.
Bug: 63814792
Test: Run GStomper on Walleye with MMAP on, see bug
Change-Id: I7b20098580ff454365425bd21e43c17ade532a0a
diff --git a/media/libaaudio/src/client/AudioEndpoint.cpp b/media/libaaudio/src/client/AudioEndpoint.cpp
index 0684ed6..6ec285f 100644
--- a/media/libaaudio/src/client/AudioEndpoint.cpp
+++ b/media/libaaudio/src/client/AudioEndpoint.cpp
@@ -113,7 +113,8 @@
return result;
}
-aaudio_result_t AudioEndpoint::configure(const EndpointDescriptor *pEndpointDescriptor)
+aaudio_result_t AudioEndpoint::configure(const EndpointDescriptor *pEndpointDescriptor,
+ aaudio_direction_t direction)
{
aaudio_result_t result = AudioEndpoint_validateDescriptor(pEndpointDescriptor);
if (result != AAUDIO_OK) {
@@ -143,12 +144,20 @@
descriptor->dataAddress
);
- // ============================ down data queue =============================
+ // ============================ data queue =============================
descriptor = &pEndpointDescriptor->dataQueueDescriptor;
ALOGV("AudioEndpoint::configure() data framesPerBurst = %d", descriptor->framesPerBurst);
- ALOGV("AudioEndpoint::configure() data readCounterAddress = %p", descriptor->readCounterAddress);
- mFreeRunning = descriptor->readCounterAddress == nullptr;
+ ALOGV("AudioEndpoint::configure() data readCounterAddress = %p",
+ descriptor->readCounterAddress);
+
+ // An example of free running is when the other side is read or written by hardware DMA
+ // or a DSP. It does not update its counter so we have to update it.
+ int64_t *remoteCounter = (direction == AAUDIO_DIRECTION_OUTPUT)
+ ? descriptor->readCounterAddress // read by other side
+ : descriptor->writeCounterAddress; // written by other side
+ mFreeRunning = (remoteCounter == nullptr);
ALOGV("AudioEndpoint::configure() mFreeRunning = %d", mFreeRunning ? 1 : 0);
+
int64_t *readCounterAddress = (descriptor->readCounterAddress == nullptr)
? &mDataReadCounter
: descriptor->readCounterAddress;
@@ -173,13 +182,8 @@
return mUpCommandQueue->read(commandPtr, 1);
}
-aaudio_result_t AudioEndpoint::writeDataNow(const void *buffer, int32_t numFrames)
-{
- return mDataQueue->write(buffer, numFrames);
-}
-
-void AudioEndpoint::getEmptyFramesAvailable(WrappingBuffer *wrappingBuffer) {
- mDataQueue->getEmptyRoomAvailable(wrappingBuffer);
+int32_t AudioEndpoint::getEmptyFramesAvailable(WrappingBuffer *wrappingBuffer) {
+ return mDataQueue->getEmptyRoomAvailable(wrappingBuffer);
}
int32_t AudioEndpoint::getEmptyFramesAvailable()
@@ -187,7 +191,7 @@
return mDataQueue->getFifoControllerBase()->getEmptyFramesAvailable();
}
-void AudioEndpoint::getFullFramesAvailable(WrappingBuffer *wrappingBuffer)
+int32_t AudioEndpoint::getFullFramesAvailable(WrappingBuffer *wrappingBuffer)
{
return mDataQueue->getFullDataAvailable(wrappingBuffer);
}