Refactor audio code out of bootanimation_main.
So it can be shared with the iot/ variant I refactored it into the
audioplay.h file. This keeps all of the audio code local, we could hide
the functions and only expose the callback but that would make testing
harder.
Test: Ran a bootanimation.zip with audio.wav on Marlin, works as expected.
Bug: 67051984
Change-Id: Ie31dc5f2cfaad5bb23134ef81be712afa6b3cd6f
diff --git a/cmds/bootanimation/bootanimation_main.cpp b/cmds/bootanimation/bootanimation_main.cpp
index 8501982..a52a5e9 100644
--- a/cmds/bootanimation/bootanimation_main.cpp
+++ b/cmds/bootanimation/bootanimation_main.cpp
@@ -26,8 +26,6 @@
#include <sys/resource.h>
#include <utils/Log.h>
#include <utils/SystemClock.h>
-#include <utils/threads.h>
-#include <android-base/properties.h>
#include "BootAnimation.h"
#include "BootAnimationUtil.h"
@@ -35,113 +33,6 @@
using namespace android;
-// ---------------------------------------------------------------------------
-
-namespace {
-
-// Create a typedef for readability.
-typedef android::BootAnimation::Animation Animation;
-
-static const char PLAY_SOUND_PROP_NAME[] = "persist.sys.bootanim.play_sound";
-static const char BOOT_COMPLETED_PROP_NAME[] = "sys.boot_completed";
-static const char POWER_CTL_PROP_NAME[] = "sys.powerctl";
-static const char BOOTREASON_PROP_NAME[] = "ro.boot.bootreason";
-static const std::vector<std::string> PLAY_SOUND_BOOTREASON_BLACKLIST {
- "kernel_panic",
- "Panic",
- "Watchdog",
-};
-
-class InitAudioThread : public Thread {
-public:
- InitAudioThread(uint8_t* exampleAudioData, int exampleAudioLength)
- : Thread(false),
- mExampleAudioData(exampleAudioData),
- mExampleAudioLength(exampleAudioLength) {}
-private:
- virtual bool threadLoop() {
- audioplay::create(mExampleAudioData, mExampleAudioLength);
- // Exit immediately
- return false;
- }
-
- uint8_t* mExampleAudioData;
- int mExampleAudioLength;
-};
-
-bool playSoundsAllowed() {
- // Only play sounds for system boots, not runtime restarts.
- if (android::base::GetBoolProperty(BOOT_COMPLETED_PROP_NAME, false)) {
- return false;
- }
- // no audio while shutting down
- if (!android::base::GetProperty(POWER_CTL_PROP_NAME, "").empty()) {
- return false;
- }
- // Read the system property to see if we should play the sound.
- // If it's not present, default to allowed.
- if (!property_get_bool(PLAY_SOUND_PROP_NAME, 1)) {
- return false;
- }
-
- // Don't play sounds if this is a reboot due to an error.
- char bootreason[PROPERTY_VALUE_MAX];
- if (property_get(BOOTREASON_PROP_NAME, bootreason, nullptr) > 0) {
- for (const auto& str : PLAY_SOUND_BOOTREASON_BLACKLIST) {
- if (strcasecmp(str.c_str(), bootreason) == 0) {
- return false;
- }
- }
- }
- return true;
-}
-
-class AudioAnimationCallbacks : public android::BootAnimation::Callbacks {
-public:
- void init(const Vector<Animation::Part>& parts) override {
- const Animation::Part* partWithAudio = nullptr;
- for (const Animation::Part& part : parts) {
- if (part.audioData != nullptr) {
- partWithAudio = ∂
- }
- }
-
- if (partWithAudio == nullptr) {
- return;
- }
-
- ALOGD("found audio.wav, creating playback engine");
- initAudioThread = new InitAudioThread(partWithAudio->audioData,
- partWithAudio->audioLength);
- initAudioThread->run("BootAnimation::InitAudioThread", PRIORITY_NORMAL);
- };
-
- void playPart(int partNumber, const Animation::Part& part, int playNumber) override {
- // only play audio file the first time we animate the part
- if (playNumber == 0 && part.audioData && playSoundsAllowed()) {
- ALOGD("playing clip for part%d, size=%d",
- partNumber, part.audioLength);
- // Block until the audio engine is finished initializing.
- if (initAudioThread != nullptr) {
- initAudioThread->join();
- }
- audioplay::playClip(part.audioData, part.audioLength);
- }
- };
-
- void shutdown() override {
- // we've finally played everything we're going to play
- audioplay::setPlaying(false);
- audioplay::destroy();
- };
-
-private:
- sp<InitAudioThread> initAudioThread = nullptr;
-};
-
-} // namespace
-
-
int main()
{
setpriority(PRIO_PROCESS, 0, ANDROID_PRIORITY_DISPLAY);
@@ -156,7 +47,7 @@
waitForSurfaceFlinger();
// create the boot animation object
- sp<BootAnimation> boot = new BootAnimation(new AudioAnimationCallbacks());
+ sp<BootAnimation> boot = new BootAnimation(audioplay::createAnimationCallbacks());
ALOGV("Boot animation set up. Joining pool.");
IPCThreadState::self()->joinThreadPool();