summaryrefslogtreecommitdiffstats
path: root/services
diff options
context:
space:
mode:
authorGlenn Kasten <gkasten@google.com>2015-02-27 22:55:14 +0000
committerAndroid (Google) Code Review <android-gerrit@google.com>2015-02-27 22:55:15 +0000
commit9060199701c97b290aa4a4184d147e0311ab8897 (patch)
treeca4bdc0a66470f17929b4c77e43a9d1c6273d7e5 /services
parent7841f704fee0e5acd45fa6e47a336120c3cad42c (diff)
parentd2123e631834a887c2d8600c3ac43dda02d47cb9 (diff)
downloadframeworks_av-9060199701c97b290aa4a4184d147e0311ab8897.zip
frameworks_av-9060199701c97b290aa4a4184d147e0311ab8897.tar.gz
frameworks_av-9060199701c97b290aa4a4184d147e0311ab8897.tar.bz2
Merge "Warmup cycles must be in range and consecutive"
Diffstat (limited to 'services')
-rw-r--r--services/audioflinger/FastCapture.cpp6
-rw-r--r--services/audioflinger/FastMixer.cpp6
-rw-r--r--services/audioflinger/FastThread.cpp20
-rw-r--r--services/audioflinger/FastThread.h6
4 files changed, 28 insertions, 10 deletions
diff --git a/services/audioflinger/FastCapture.cpp b/services/audioflinger/FastCapture.cpp
index 1c4f670..255496e 100644
--- a/services/audioflinger/FastCapture.cpp
+++ b/services/audioflinger/FastCapture.cpp
@@ -138,13 +138,15 @@ void FastCapture::onStateChange()
underrunNs = (frameCount * 1750000000LL) / sampleRate; // 1.75
overrunNs = (frameCount * 500000000LL) / sampleRate; // 0.50
forceNs = (frameCount * 950000000LL) / sampleRate; // 0.95
- warmupNs = (frameCount * 500000000LL) / sampleRate; // 0.50
+ warmupNsMin = (frameCount * 750000000LL) / sampleRate; // 0.75
+ warmupNsMax = (frameCount * 1250000000LL) / sampleRate; // 1.25
} else {
periodNs = 0;
underrunNs = 0;
overrunNs = 0;
forceNs = 0;
- warmupNs = 0;
+ warmupNsMin = 0;
+ warmupNsMax = LONG_MAX;
}
readBufferState = -1;
dumpState->mFrameCount = frameCount;
diff --git a/services/audioflinger/FastMixer.cpp b/services/audioflinger/FastMixer.cpp
index 67e2e6e..8b12f28 100644
--- a/services/audioflinger/FastMixer.cpp
+++ b/services/audioflinger/FastMixer.cpp
@@ -195,13 +195,15 @@ void FastMixer::onStateChange()
underrunNs = (frameCount * 1750000000LL) / sampleRate; // 1.75
overrunNs = (frameCount * 500000000LL) / sampleRate; // 0.50
forceNs = (frameCount * 950000000LL) / sampleRate; // 0.95
- warmupNs = (frameCount * 500000000LL) / sampleRate; // 0.50
+ warmupNsMin = (frameCount * 750000000LL) / sampleRate; // 0.75
+ warmupNsMax = (frameCount * 1250000000LL) / sampleRate; // 1.25
} else {
periodNs = 0;
underrunNs = 0;
overrunNs = 0;
forceNs = 0;
- warmupNs = 0;
+ warmupNsMin = 0;
+ warmupNsMax = LONG_MAX;
}
mMixerBufferState = UNDEFINED;
#if !LOG_NDEBUG
diff --git a/services/audioflinger/FastThread.cpp b/services/audioflinger/FastThread.cpp
index 3e12cca..b69cc85 100644
--- a/services/audioflinger/FastThread.cpp
+++ b/services/audioflinger/FastThread.cpp
@@ -29,7 +29,8 @@
#define FAST_DEFAULT_NS 999999999L // ~1 sec: default time to sleep
#define FAST_HOT_IDLE_NS 1000000L // 1 ms: time to sleep while hot idling
-#define MIN_WARMUP_CYCLES 2 // minimum number of loop cycles to wait for warmup
+#define MIN_WARMUP_CYCLES 2 // minimum number of consecutive in-range loop cycles
+ // to wait for warmup
#define MAX_WARMUP_CYCLES 10 // maximum number of loop cycles to wait for warmup
namespace android {
@@ -44,7 +45,8 @@ FastThread::FastThread() : Thread(false /*canCallJava*/),
underrunNs(0),
overrunNs(0),
forceNs(0),
- warmupNs(0),
+ warmupNsMin(0),
+ warmupNsMax(LONG_MAX),
// re-initialized to &dummyDumpState by subclass constructor
mDummyDumpState(NULL),
dumpState(NULL),
@@ -60,6 +62,7 @@ FastThread::FastThread() : Thread(false /*canCallJava*/),
isWarm(false),
/* measuredWarmupTs({0, 0}), */
warmupCycles(0),
+ warmupConsecutiveInRangeCycles(0),
// dummyLogWriter
logWriter(&dummyLogWriter),
timestampStatus(INVALID_OPERATION),
@@ -169,6 +172,7 @@ bool FastThread::threadLoop()
measuredWarmupTs.tv_sec = 0;
measuredWarmupTs.tv_nsec = 0;
warmupCycles = 0;
+ warmupConsecutiveInRangeCycles = 0;
sleepNs = -1;
coldGen = current->mColdGen;
#ifdef FAST_MIXER_STATISTICS
@@ -222,7 +226,8 @@ bool FastThread::threadLoop()
// To avoid an initial underrun on fast tracks after exiting standby,
// do not start pulling data from tracks and mixing until warmup is complete.
// Warmup is considered complete after the earlier of:
- // MIN_WARMUP_CYCLES write() attempts and last one blocks for at least warmupNs
+ // MIN_WARMUP_CYCLES consecutive in-range write() attempts,
+ // where "in-range" means warmupNsMin <= cycle time <= warmupNsMax
// MAX_WARMUP_CYCLES write() attempts.
// This is overly conservative, but to get better accuracy requires a new HAL API.
if (!isWarm && attemptedWrite) {
@@ -233,7 +238,14 @@ bool FastThread::threadLoop()
measuredWarmupTs.tv_nsec -= 1000000000;
}
++warmupCycles;
- if ((nsec > warmupNs && warmupCycles >= MIN_WARMUP_CYCLES) ||
+ if (warmupNsMin <= nsec && nsec <= warmupNsMax) {
+ ALOGV("warmup cycle %d in range: %.03f ms", warmupCycles, nsec * 1e-9);
+ ++warmupConsecutiveInRangeCycles;
+ } else {
+ ALOGV("warmup cycle %d out of range: %.03f ms", warmupCycles, nsec * 1e-9);
+ warmupConsecutiveInRangeCycles = 0;
+ }
+ if ((warmupConsecutiveInRangeCycles >= MIN_WARMUP_CYCLES) ||
(warmupCycles >= MAX_WARMUP_CYCLES)) {
isWarm = true;
dumpState->mMeasuredWarmupTs = measuredWarmupTs;
diff --git a/services/audioflinger/FastThread.h b/services/audioflinger/FastThread.h
index 1330334..cb32e9d 100644
--- a/services/audioflinger/FastThread.h
+++ b/services/audioflinger/FastThread.h
@@ -58,7 +58,8 @@ protected:
long underrunNs; // underrun likely when write cycle is greater than this value
long overrunNs; // overrun likely when write cycle is less than this value
long forceNs; // if overrun detected, force the write cycle to take this much time
- long warmupNs; // warmup complete when write cycle is greater than to this value
+ long warmupNsMin; // warmup complete when write cycle is greater than or equal to this value
+ long warmupNsMax; // and less than or equal to this value
FastThreadDumpState *mDummyDumpState;
FastThreadDumpState *dumpState;
bool ignoreNextOverrun; // used to ignore initial overrun and first after an underrun
@@ -74,7 +75,8 @@ protected:
unsigned coldGen; // last observed mColdGen
bool isWarm; // true means ready to mix, false means wait for warmup before mixing
struct timespec measuredWarmupTs; // how long did it take for warmup to complete
- uint32_t warmupCycles; // counter of number of loop cycles required to warmup
+ uint32_t warmupCycles; // counter of number of loop cycles during warmup phase
+ uint32_t warmupConsecutiveInRangeCycles; // number of consecutive cycles in range
NBLog::Writer dummyLogWriter;
NBLog::Writer *logWriter;
status_t timestampStatus;