Skip to content

Commit b852984

Browse files
committed
internal/oboe: update Oboe to 1.9.3
1 parent 7b86496 commit b852984

18 files changed

+189
-71
lines changed

internal/oboe/gen.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ import (
2929
"strings"
3030
)
3131

32-
const oboeVersion = "1.9.0"
32+
const oboeVersion = "1.9.3"
3333

3434
func main() {
3535
if err := run(); err != nil {

internal/oboe/oboe_aaudio_AudioStreamAAudio_android.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,8 +20,8 @@
2020

2121
#include "oboe_aaudio_AAudioLoader_android.h"
2222
#include "oboe_aaudio_AudioStreamAAudio_android.h"
23-
#include "oboe_common_AudioClock_android.h"
2423
#include "oboe_common_OboeDebug_android.h"
24+
#include "oboe_oboe_AudioClock_android.h"
2525
#include "oboe_oboe_Utilities_android.h"
2626
#include "oboe_aaudio_AAudioExtensions_android.h"
2727

internal/oboe/oboe_aaudio_AudioStreamAAudio_android.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,14 @@ class AudioStreamAAudio : public AudioStream {
100100
mAdpfOpenAttempted = false;
101101
}
102102

103+
oboe::Result reportWorkload(int32_t appWorkload) override {
104+
if (!isPerformanceHintEnabled()) {
105+
return oboe::Result::ErrorInvalidState;
106+
}
107+
mAdpfWrapper.reportWorkload(appWorkload);
108+
return oboe::Result::OK;
109+
}
110+
103111
protected:
104112
static void internalErrorCallback(
105113
AAudioStream *stream,

internal/oboe/oboe_common_AdpfWrapper_android.cpp

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,8 @@
1818
#include <stdint.h>
1919
#include <sys/types.h>
2020

21+
#include "oboe_oboe_AudioClock_android.h"
2122
#include "oboe_common_AdpfWrapper_android.h"
22-
#include "oboe_common_AudioClock_android.h"
2323
#include "oboe_common_OboeDebug_android.h"
2424

2525
typedef APerformanceHintManager* (*APH_getManager)();
@@ -120,5 +120,22 @@ void AdpfWrapper::onEndCallback(double durationScaler) {
120120
int64_t actualDurationNanos = endCallbackNanos - mBeginCallbackNanos;
121121
int64_t scaledDurationNanos = static_cast<int64_t>(actualDurationNanos * durationScaler);
122122
reportActualDuration(scaledDurationNanos);
123+
// When the workload is non-zero, update the conversion factor from workload
124+
// units to nanoseconds duration.
125+
if (mPreviousWorkload > 0) {
126+
mNanosPerWorkloadUnit = ((double) scaledDurationNanos) / mPreviousWorkload;
127+
}
128+
}
129+
}
130+
131+
void AdpfWrapper::reportWorkload(int32_t appWorkload) {
132+
if (isOpen()) {
133+
// Compare with previous workload. If we think we will need more
134+
// time to render the callback then warn ADPF as soon as possible.
135+
if (appWorkload > mPreviousWorkload && mNanosPerWorkloadUnit > 0.0) {
136+
int64_t predictedDuration = (int64_t) (appWorkload * mNanosPerWorkloadUnit);
137+
reportActualDuration(predictedDuration);
138+
}
139+
mPreviousWorkload = appWorkload;
123140
}
124141
}

internal/oboe/oboe_common_AdpfWrapper_android.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,11 +75,15 @@ class AdpfWrapper {
7575
*/
7676
void reportActualDuration(int64_t actualDurationNanos);
7777

78+
void reportWorkload(int32_t appWorkload);
79+
7880
private:
7981
std::mutex mLock;
8082
APerformanceHintSession* mHintSession = nullptr;
8183
int64_t mBeginCallbackNanos = 0;
8284
static bool sUseAlternativeHack;
85+
int32_t mPreviousWorkload = 0;
86+
double mNanosPerWorkloadUnit = 0.0;
8387
};
8488

8589
#endif //SYNTHMARK_ADPF_WRAPPER_H

internal/oboe/oboe_common_AudioStreamBuilder_android.cpp

Lines changed: 22 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -100,8 +100,10 @@ Result AudioStreamBuilder::openStreamInternal(AudioStream **streamPP) {
100100
return result;
101101
}
102102

103+
#ifndef OBOE_SUPPRESS_LOG_SPAM
103104
LOGI("%s() %s -------- %s --------",
104105
__func__, getDirection() == Direction::Input ? "INPUT" : "OUTPUT", getVersionText());
106+
#endif
105107

106108
if (streamPP == nullptr) {
107109
return Result::ErrorNull;
@@ -180,24 +182,26 @@ Result AudioStreamBuilder::openStreamInternal(AudioStream **streamPP) {
180182
AAudioExtensions::getInstance().setMMapEnabled(wasMMapOriginallyEnabled); // restore original
181183
}
182184
if (result == Result::OK) {
183-
184-
int32_t optimalBufferSize = -1;
185-
// Use a reasonable default buffer size.
186-
if (streamP->getDirection() == Direction::Input) {
187-
// For input, small size does not improve latency because the stream is usually
188-
// run close to empty. And a low size can result in XRuns so always use the maximum.
189-
optimalBufferSize = streamP->getBufferCapacityInFrames();
190-
} else if (streamP->getPerformanceMode() == PerformanceMode::LowLatency
191-
&& streamP->getDirection() == Direction::Output) { // Output check is redundant.
192-
optimalBufferSize = streamP->getFramesPerBurst() *
193-
kBufferSizeInBurstsForLowLatencyStreams;
194-
}
195-
if (optimalBufferSize >= 0) {
196-
auto setBufferResult = streamP->setBufferSizeInFrames(optimalBufferSize);
197-
if (!setBufferResult) {
198-
LOGW("Failed to setBufferSizeInFrames(%d). Error was %s",
199-
optimalBufferSize,
200-
convertToText(setBufferResult.error()));
185+
// AAudio supports setBufferSizeInFrames() so use it.
186+
if (streamP->getAudioApi() == AudioApi::AAudio) {
187+
int32_t optimalBufferSize = -1;
188+
// Use a reasonable default buffer size.
189+
if (streamP->getDirection() == Direction::Input) {
190+
// For input, small size does not improve latency because the stream is usually
191+
// run close to empty. And a low size can result in XRuns so always use the maximum.
192+
optimalBufferSize = streamP->getBufferCapacityInFrames();
193+
} else if (streamP->getPerformanceMode() == PerformanceMode::LowLatency
194+
&& streamP->getDirection() == Direction::Output) { // Output check is redundant.
195+
optimalBufferSize = streamP->getFramesPerBurst() *
196+
kBufferSizeInBurstsForLowLatencyStreams;
197+
}
198+
if (optimalBufferSize >= 0) {
199+
auto setBufferResult = streamP->setBufferSizeInFrames(optimalBufferSize);
200+
if (!setBufferResult) {
201+
LOGW("Failed to setBufferSizeInFrames(%d). Error was %s",
202+
optimalBufferSize,
203+
convertToText(setBufferResult.error()));
204+
}
201205
}
202206
}
203207

internal/oboe/oboe_common_AudioStream_android.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,10 @@
1818
#include <pthread.h>
1919
#include <thread>
2020

21+
#include "oboe_oboe_AudioClock_android.h"
2122
#include "oboe_oboe_AudioStream_android.h"
22-
#include "oboe_common_OboeDebug_android.h"
23-
#include "oboe_common_AudioClock_android.h"
2423
#include "oboe_oboe_Utilities_android.h"
24+
#include "oboe_common_OboeDebug_android.h"
2525

2626
namespace oboe {
2727

internal/oboe/oboe_common_StabilizedCallback_android.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,9 @@
1414
* limitations under the License.
1515
*/
1616

17-
#include "oboe_oboe_StabilizedCallback_android.h"
18-
#include "oboe_common_AudioClock_android.h"
1917
#include "oboe_common_Trace_android.h"
18+
#include "oboe_oboe_AudioClock_android.h"
19+
#include "oboe_oboe_StabilizedCallback_android.h"
2020

2121
constexpr int32_t kLoadGenerationStepSizeNanos = 20000;
2222
constexpr float kPercentageOfCallbackToUse = 0.8;

internal/oboe/oboe_common_AudioClock_android.h renamed to internal/oboe/oboe_oboe_AudioClock_android.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,6 @@
2323

2424
namespace oboe {
2525

26-
// TODO: Move this class into the public headers because it is useful when calculating stream latency
2726
class AudioClock {
2827
public:
2928
static int64_t getNanoseconds(clockid_t clockId = CLOCK_MONOTONIC) {

internal/oboe/oboe_oboe_AudioStream_android.h

Lines changed: 34 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,6 @@
2626
#include "oboe_oboe_AudioStreamBuilder_android.h"
2727
#include "oboe_oboe_AudioStreamBase_android.h"
2828

29-
/** WARNING - UNDER CONSTRUCTION - THIS API WILL CHANGE. */
30-
3129
namespace oboe {
3230

3331
/**
@@ -517,18 +515,18 @@ class AudioStream : public AudioStreamBase {
517515
*
518516
* The flag will be checked in the Oboe data callback. If it transitions from false to true
519517
* then the PerformanceHint feature will be started.
520-
* This only needs to be called once.
518+
* This only needs to be called once for each stream.
521519
*
522520
* You may want to enable this if you have a dynamically changing workload
523-
* and you notice that you are getting underruns and glitches when your workload increases.
521+
* and you notice that you are getting under-runs and glitches when your workload increases.
524522
* This might happen, for example, if you suddenly go from playing one note to
525523
* ten notes on a synthesizer.
526524
*
527-
* Try the CPU Load test in OboeTester if you would like to experiment with this interactively.
525+
* Try the "CPU Load" test in OboeTester if you would like to experiment with this interactively.
528526
*
529527
* On some devices, this may be implemented using the "ADPF" library.
530528
*
531-
* @param enabled true if you would like a performance boost
529+
* @param enabled true if you would like a performance boost, default is false
532530
*/
533531
void setPerformanceHintEnabled(bool enabled) {
534532
mPerformanceHintEnabled = enabled;
@@ -544,6 +542,36 @@ class AudioStream : public AudioStreamBase {
544542
return mPerformanceHintEnabled;
545543
}
546544

545+
/**
546+
* Use this to give the performance manager more information about your workload.
547+
* You can call this at the beginning of the callback when you figure
548+
* out what your workload will be.
549+
*
550+
* Call this if (1) you have called setPerformanceHintEnabled(true), and
551+
* (2) you have a varying workload, and
552+
* (3) you hear glitches when your workload suddenly increases.
553+
*
554+
* This might happen when you go from a single note to a big chord on a synthesizer.
555+
*
556+
* The workload can be in your own units. If you are synthesizing music
557+
* then the workload could be the number of active voices.
558+
* If your app is a game then it could be the number of sound effects.
559+
* The units are arbitrary. They just have to be proportional to
560+
* the estimated computational load. For example, if some of your voices take 20%
561+
* more computation than a basic voice then assign 6 units to the complex voice
562+
* and 5 units to the basic voice.
563+
*
564+
* The performance hint code can use this as an advance warning that the callback duration
565+
* will probably increase. Rather than wait for the long duration and possibly under-run,
566+
* we can boost the CPU immediately before we start doing the calculations.
567+
*
568+
* @param appWorkload workload in application units, such as number of voices
569+
* @return OK or an error such as ErrorInvalidState if the PerformanceHint was not enabled.
570+
*/
571+
virtual oboe::Result reportWorkload(int32_t appWorkload) {
572+
return oboe::Result::ErrorUnimplemented;
573+
}
574+
547575
protected:
548576

549577
/**

internal/oboe/oboe_oboe_FullDuplexStream_android.h

Lines changed: 46 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -53,39 +53,69 @@ class FullDuplexStream : public AudioStreamDataCallback {
5353
virtual ~FullDuplexStream() = default;
5454

5555
/**
56-
* Sets the input stream. Calling this is mandatory.
56+
* Sets the input stream.
5757
*
58+
* @deprecated Call setSharedInputStream(std::shared_ptr<AudioStream> &stream) instead.
5859
* @param stream the output stream
5960
*/
6061
void setInputStream(AudioStream *stream) {
61-
mInputStream = stream;
62+
mRawInputStream = stream;
63+
}
64+
65+
/**
66+
* Sets the input stream. Calling this is mandatory.
67+
*
68+
* @param stream the output stream
69+
*/
70+
void setSharedInputStream(std::shared_ptr<AudioStream> &stream) {
71+
mSharedInputStream = stream;
6272
}
6373

6474
/**
65-
* Gets the input stream
75+
* Gets the current input stream. This function tries to return the shared input stream if it
76+
* is set before the raw input stream.
6677
*
67-
* @return the input stream
78+
* @return pointer to an output stream or nullptr.
6879
*/
6980
AudioStream *getInputStream() {
70-
return mInputStream;
81+
if (mSharedInputStream) {
82+
return mSharedInputStream.get();
83+
} else {
84+
return mRawInputStream;
85+
}
7186
}
7287

7388
/**
74-
* Sets the output stream. Calling this is mandatory.
89+
* Sets the output stream.
7590
*
91+
* @deprecated Call setSharedOutputStream(std::shared_ptr<AudioStream> &stream) instead.
7692
* @param stream the output stream
7793
*/
7894
void setOutputStream(AudioStream *stream) {
79-
mOutputStream = stream;
95+
mRawOutputStream = stream;
96+
}
97+
98+
/**
99+
* Sets the output stream. Calling this is mandatory.
100+
*
101+
* @param stream the output stream
102+
*/
103+
void setSharedOutputStream(std::shared_ptr<AudioStream> &stream) {
104+
mSharedOutputStream = stream;
80105
}
81106

82107
/**
83-
* Gets the output stream
108+
* Gets the current output stream. This function tries to return the shared output stream if it
109+
* is set before the raw output stream.
84110
*
85-
* @return the output stream
111+
* @return pointer to an output stream or nullptr.
86112
*/
87113
AudioStream *getOutputStream() {
88-
return mOutputStream;
114+
if (mSharedOutputStream) {
115+
return mSharedOutputStream.get();
116+
} else {
117+
return mRawOutputStream;
118+
}
89119
}
90120

91121
/**
@@ -123,10 +153,10 @@ class FullDuplexStream : public AudioStreamDataCallback {
123153
Result outputResult = Result::OK;
124154
Result inputResult = Result::OK;
125155
if (getOutputStream()) {
126-
outputResult = mOutputStream->requestStop();
156+
outputResult = getOutputStream()->requestStop();
127157
}
128158
if (getInputStream()) {
129-
inputResult = mInputStream->requestStop();
159+
inputResult = getOutputStream()->requestStop();
130160
}
131161
if (outputResult != Result::OK) {
132162
return outputResult;
@@ -312,8 +342,10 @@ class FullDuplexStream : public AudioStreamDataCallback {
312342
// Discard some callbacks so the input and output reach equilibrium.
313343
int32_t mCountCallbacksToDiscard = kNumCallbacksToDiscard;
314344

315-
AudioStream *mInputStream = nullptr;
316-
AudioStream *mOutputStream = nullptr;
345+
AudioStream *mRawInputStream = nullptr;
346+
AudioStream *mRawOutputStream = nullptr;
347+
std::shared_ptr<AudioStream> mSharedInputStream;
348+
std::shared_ptr<AudioStream> mSharedOutputStream;
317349

318350
int32_t mBufferSize = 0;
319351
std::unique_ptr<float[]> mInputBuffer;

internal/oboe/oboe_oboe_Oboe_android.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,5 +36,6 @@
3636
#include "oboe_oboe_FifoBuffer_android.h"
3737
#include "oboe_oboe_OboeExtensions_android.h"
3838
#include "oboe_oboe_FullDuplexStream_android.h"
39+
#include "oboe_oboe_AudioClock_android.h"
3940

4041
#endif //OBOE_OBOE_H

internal/oboe/oboe_oboe_Version_android.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
#define OBOE_VERSION_MINOR 9
3838

3939
// Type: 16-bit unsigned int. Min value: 0 Max value: 65535. See below for description.
40-
#define OBOE_VERSION_PATCH 0
40+
#define OBOE_VERSION_PATCH 3
4141

4242
#define OBOE_STRINGIFY(x) #x
4343
#define OBOE_TOSTRING(x) OBOE_STRINGIFY(x)

internal/oboe/oboe_opensles_AudioInputStreamOpenSLES_android.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ Result AudioInputStreamOpenSLES::open() {
106106
SL_DATAFORMAT_PCM, // formatType
107107
static_cast<SLuint32>(mChannelCount), // numChannels
108108
static_cast<SLuint32>(mSampleRate * kMillisPerSecond), // milliSamplesPerSec
109-
bitsPerSample, // bitsPerSample
109+
bitsPerSample, // mBitsPerSample
110110
bitsPerSample, // containerSize;
111111
channelCountToChannelMask(mChannelCount), // channelMask
112112
getDefaultByteOrder(),
@@ -212,7 +212,7 @@ Result AudioInputStreamOpenSLES::close() {
212212
LOGD("AudioInputStreamOpenSLES::%s()", __func__);
213213
std::lock_guard<std::mutex> lock(mLock);
214214
Result result = Result::OK;
215-
if (getState() == StreamState::Closed){
215+
if (getState() == StreamState::Closed) {
216216
result = Result::ErrorClosed;
217217
} else {
218218
(void) requestStop_l();

0 commit comments

Comments
 (0)