blob: df20c9edce14cbbfd94c961ce71124e95356ea0e [file] [log] [blame]
// Copyright 2019 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SRC_MEDIA_AUDIO_LIB_TEST_HERMETIC_AUDIO_TEST_H_
#define SRC_MEDIA_AUDIO_LIB_TEST_HERMETIC_AUDIO_TEST_H_
#include <lib/syslog/cpp/macros.h>
#include <zircon/device/audio.h>
#include <unordered_map>
#include <unordered_set>
#include "src/media/audio/lib/format/audio_buffer.h"
#include "src/media/audio/lib/test/capturer_shim.h"
#include "src/media/audio/lib/test/constants.h"
#include "src/media/audio/lib/test/hermetic_audio_environment.h"
#include "src/media/audio/lib/test/inspect.h"
#include "src/media/audio/lib/test/renderer_shim.h"
#include "src/media/audio/lib/test/test_fixture.h"
#include "src/media/audio/lib/test/virtual_device.h"
#include "zircon/system/ulib/inspect/include/lib/inspect/cpp/hierarchy.h"
namespace media::audio::test {
// Restrictions on usage:
//
// 1. This class is thread hostile: none of its methods can be called concurrently.
// 2. It is illegal for two or more instances to be alive at any time. (This restriction
// is satisfied by ordinary usage of gtest.)
//
class HermeticAudioTest : public TestFixture {
protected:
static void SetUpTestSuite();
static void SetUpTestSuiteWithOptions(HermeticAudioEnvironment::Options options);
static void TearDownTestSuite();
static HermeticAudioEnvironment* environment() {
auto ptr = HermeticAudioTest::environment_.get();
FX_CHECK(ptr) << "No Environment; Did you forget to call SetUpTestSuite?";
return ptr;
}
void SetUp() override;
void TearDown() override;
// Register that the test expects no audio underflows. This expectation will be checked by
// TearDown().
void FailUponUnderflows() { disallow_underflows_ = true; }
// The returned pointers are owned by this class.
template <fuchsia::media::AudioSampleFormat SampleFormat>
VirtualOutput<SampleFormat>* CreateOutput(const audio_stream_unique_id_t& device_id,
TypedFormat<SampleFormat> format, size_t frame_count);
template <fuchsia::media::AudioSampleFormat SampleFormat>
VirtualInput<SampleFormat>* CreateInput(const audio_stream_unique_id_t& device_id,
TypedFormat<SampleFormat> format, size_t frame_count);
template <fuchsia::media::AudioSampleFormat SampleFormat>
AudioRendererShim<SampleFormat>* CreateAudioRenderer(
TypedFormat<SampleFormat> format, size_t frame_count,
fuchsia::media::AudioRenderUsage usage = fuchsia::media::AudioRenderUsage::MEDIA);
template <fuchsia::media::AudioSampleFormat SampleFormat>
AudioCapturerShim<SampleFormat>* CreateAudioCapturer(
TypedFormat<SampleFormat> format, size_t frame_count,
fuchsia::media::AudioCapturerConfiguration config);
template <fuchsia::media::AudioSampleFormat SampleFormat>
UltrasoundRendererShim<SampleFormat>* CreateUltrasoundRenderer(TypedFormat<SampleFormat> format,
size_t frame_count,
bool wait_for_creation = true);
template <fuchsia::media::AudioSampleFormat SampleFormat>
UltrasoundCapturerShim<SampleFormat>* CreateUltrasoundCapturer(TypedFormat<SampleFormat> format,
size_t frame_count,
bool wait_for_creation = true);
// Takes ownership of the AudioDeviceEnumerator. This is useful when tests need to watch for
// low-level device enumeration events. This is incompatible with CreateInput and CreateOutput.
fuchsia::media::AudioDeviceEnumeratorPtr TakeOwnershipOfAudioDeviceEnumerator();
// TODO(49807): make this private; this is currently used by fidl tests
fuchsia::media::AudioCorePtr audio_core_;
private:
static std::unique_ptr<HermeticAudioEnvironment> environment_;
static fuchsia::virtualaudio::ControlSyncPtr virtual_audio_control_sync_;
void WatchForDeviceArrivals();
void WaitForDeviceDepartures();
void OnDefaultDeviceChanged(uint64_t old_default_token, uint64_t new_default_token);
void CheckInspectHierarchy(const inspect::Hierarchy& root, const std::vector<std::string>& path,
const ExpectedInspectProperties& expected);
struct DeviceInfo {
std::unique_ptr<VirtualDevice<fuchsia::virtualaudio::Output>> output;
std::unique_ptr<VirtualDevice<fuchsia::virtualaudio::Input>> input;
std::optional<fuchsia::media::AudioDeviceInfo> info;
bool is_removed = false;
bool is_default = false;
};
std::unordered_map<uint64_t, std::string> token_to_unique_id_;
std::unordered_map<std::string, DeviceInfo> devices_;
std::vector<std::unique_ptr<CapturerShimImpl>> capturers_;
std::vector<std::unique_ptr<RendererShimImpl>> renderers_;
fuchsia::media::AudioDeviceEnumeratorPtr audio_dev_enum_;
fuchsia::ultrasound::FactoryPtr ultrasound_factory_;
bool disallow_underflows_ = false;
};
} // namespace media::audio::test
#endif // SRC_MEDIA_AUDIO_LIB_TEST_HERMETIC_AUDIO_TEST_H_