2011-07-08 08:23:47 +04:00
|
|
|
/*
|
|
|
|
* Copyright © 2011 Mozilla Foundation
|
|
|
|
*
|
|
|
|
* This program is made available under an ISC-style license. See the
|
|
|
|
* accompanying file LICENSE for details.
|
|
|
|
*/
|
2016-11-11 06:09:49 +03:00
|
|
|
#include "gtest/gtest.h"
|
2016-11-11 04:50:16 +03:00
|
|
|
#if !defined(_XOPEN_SOURCE)
|
2015-12-01 02:55:42 +03:00
|
|
|
#define _XOPEN_SOURCE 600
|
2016-11-11 04:50:16 +03:00
|
|
|
#endif
|
2011-07-08 08:23:47 +04:00
|
|
|
#include "cubeb/cubeb.h"
|
2016-11-11 06:27:12 +03:00
|
|
|
#include <atomic>
|
2012-05-04 05:02:37 +04:00
|
|
|
#include <stdio.h>
|
2011-07-08 08:23:47 +04:00
|
|
|
#include <string.h>
|
2014-02-26 22:48:20 +04:00
|
|
|
#include <math.h>
|
2018-10-18 17:57:01 +03:00
|
|
|
|
|
|
|
//#define ENABLE_NORMAL_LOG
|
|
|
|
//#define ENABLE_VERBOSE_LOG
|
2013-09-02 22:50:58 +04:00
|
|
|
#include "common.h"
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
#define STREAM_RATE 44100
|
2016-06-29 16:04:08 +03:00
|
|
|
#define STREAM_LATENCY 100 * STREAM_RATE / 1000
|
2011-08-29 07:56:02 +04:00
|
|
|
#define STREAM_CHANNELS 1
|
2016-12-21 08:18:07 +03:00
|
|
|
#define STREAM_LAYOUT CUBEB_LAYOUT_MONO
|
2011-08-29 07:56:02 +04:00
|
|
|
#define STREAM_FORMAT CUBEB_SAMPLE_S16LE
|
|
|
|
|
2016-11-10 07:06:08 +03:00
|
|
|
int is_windows_7()
|
|
|
|
{
|
|
|
|
#ifdef __MINGW32__
|
2017-04-07 06:44:24 +03:00
|
|
|
fprintf(stderr, "Warning: this test was built with MinGW.\n"
|
2016-11-10 07:06:08 +03:00
|
|
|
"MinGW does not contain necessary version checking infrastructure. Claiming to be Windows 7, even if we're not.\n");
|
|
|
|
return 1;
|
|
|
|
#endif
|
|
|
|
#if (defined(_WIN32) || defined(__WIN32__)) && ( !defined(__MINGW32__))
|
|
|
|
OSVERSIONINFOEX osvi;
|
|
|
|
DWORDLONG condition_mask = 0;
|
|
|
|
|
|
|
|
ZeroMemory(&osvi, sizeof(OSVERSIONINFOEX));
|
|
|
|
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX);
|
|
|
|
|
|
|
|
// NT 6.1 is Windows 7
|
|
|
|
osvi.dwMajorVersion = 6;
|
|
|
|
osvi.dwMinorVersion = 1;
|
|
|
|
|
|
|
|
VER_SET_CONDITION(condition_mask, VER_MAJORVERSION, VER_EQUAL);
|
|
|
|
VER_SET_CONDITION(condition_mask, VER_MINORVERSION, VER_GREATER_EQUAL);
|
|
|
|
|
|
|
|
return VerifyVersionInfo(&osvi, VER_MAJORVERSION | VER_MINORVERSION, condition_mask);
|
|
|
|
#else
|
|
|
|
return 0;
|
|
|
|
#endif
|
|
|
|
}
|
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
static int dummy;
|
2016-11-11 06:27:12 +03:00
|
|
|
static std::atomic<uint64_t> total_frames_written;
|
2012-05-02 08:53:57 +04:00
|
|
|
static int delay_callback;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
static long
|
2016-08-23 04:20:54 +03:00
|
|
|
test_data_callback(cubeb_stream * stm, void * user_ptr, const void * /*inputbuffer*/, void * outputbuffer, long nframes)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2016-11-10 05:48:17 +03:00
|
|
|
EXPECT_TRUE(stm && user_ptr == &dummy && outputbuffer && nframes > 0);
|
2016-11-15 06:25:27 +03:00
|
|
|
assert(outputbuffer);
|
Preparatory work for the input and duplex code
This is changing all the signatures of the `cubeb_stream_init` implementations,
the signature of the `data_callback` type, so that cubeb can support audio
input.
`cubeb_stream_init` now has two `cubeb_stream_params` pointers, one for input,
one for output. If two pointers are passed, a "duplex" stream is opened. If only
one pointer is passed, an input-only or output-only stream is created.
Duplex streams have the same sample rate, and sample type. They don't have to
have the same number of channels.
`data_callback` now has two pointers to audio buffers: an input buffer (`NULL`
if this is an output-only stream) containing input data (e.g. a microphone), and
an output buffer, to be filled, as usual, with the audio frames to play. The
two buffers always have the exact same number of audio frames, and are
temporally correlated in a way that ensures the minimal loop-back latency on
the system if one directly copies the input buffer to the output buffer.
No functionnal changes are present in this patch, just signature changes.
Asserts have been added to prevent users to try to use the input code path for
now.
Actual implementations with the input code for different platforms will follow.
Green `mozilla-central` push:
<https://treeherder.mozilla.org/#/jobs?repo=try&revision=15b4dd3cbbe8>
2016-01-13 19:16:50 +03:00
|
|
|
memset(outputbuffer, 0, nframes * sizeof(short));
|
2015-11-26 00:57:04 +03:00
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
total_frames_written += nframes;
|
2012-05-02 08:53:57 +04:00
|
|
|
if (delay_callback) {
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(10);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
return nframes;
|
|
|
|
}
|
|
|
|
|
2012-06-06 07:33:12 +04:00
|
|
|
void
|
2016-08-23 04:20:54 +03:00
|
|
|
test_state_callback(cubeb_stream * /*stm*/, void * /*user_ptr*/, cubeb_state /*state*/)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_destroy_context)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
2014-10-13 09:52:37 +04:00
|
|
|
char const* backend_id;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2014-10-13 09:52:37 +04:00
|
|
|
backend_id = cubeb_get_backend_id(ctx);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(backend_id);
|
2014-10-13 09:52:37 +04:00
|
|
|
|
|
|
|
fprintf(stderr, "Backend: %s\n", backend_id);
|
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_destroy_multiple_contexts)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t i;
|
2011-07-08 08:23:47 +04:00
|
|
|
int r;
|
|
|
|
cubeb * ctx[4];
|
2014-09-17 09:34:37 +04:00
|
|
|
int order[4] = {2, 0, 3, 1};
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(ARRAY_LENGTH(ctx), ARRAY_LENGTH(order));
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2015-11-26 00:57:04 +03:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(ctx); ++i) {
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx[i], NULL);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx[i], nullptr);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
/* destroy in a different order */
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(ctx); ++i) {
|
|
|
|
cubeb_destroy(ctx[order[i]]);
|
|
|
|
}
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, context_variables)
|
2014-10-12 22:51:37 +04:00
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
uint32_t value;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_context_variables");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2014-10-12 22:51:37 +04:00
|
|
|
|
2015-11-26 00:57:04 +03:00
|
|
|
params.channels = STREAM_CHANNELS;
|
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
|
|
|
|
2017-06-23 10:26:09 +03:00
|
|
|
r = cubeb_get_min_latency(ctx, ¶ms, &value);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(r == CUBEB_OK || r == CUBEB_ERROR_NOT_SUPPORTED);
|
2014-11-28 05:56:44 +03:00
|
|
|
if (r == CUBEB_OK) {
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(value > 0);
|
2014-11-28 05:56:44 +03:00
|
|
|
}
|
2014-10-12 22:51:37 +04:00
|
|
|
|
|
|
|
r = cubeb_get_preferred_sample_rate(ctx, &value);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(r == CUBEB_OK || r == CUBEB_ERROR_NOT_SUPPORTED);
|
2014-11-28 05:56:44 +03:00
|
|
|
if (r == CUBEB_OK) {
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(value > 0);
|
2014-11-28 05:56:44 +03:00
|
|
|
}
|
2014-10-12 22:51:37 +04:00
|
|
|
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2014-10-12 22:51:37 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_destroy_stream)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_destroy_multiple_streams)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t i;
|
2011-07-08 08:23:47 +04:00
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
2014-09-17 09:22:06 +04:00
|
|
|
cubeb_stream * stream[8];
|
2011-07-08 08:23:47 +04:00
|
|
|
cubeb_stream_params params;
|
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream[i], "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream[i], nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2011-07-08 08:23:47 +04:00
|
|
|
cubeb_stream_destroy(stream[i]);
|
|
|
|
}
|
|
|
|
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, configure_stream)
|
2014-10-14 09:21:49 +04:00
|
|
|
{
|
2014-11-28 05:56:44 +03:00
|
|
|
int r;
|
2014-10-14 09:21:49 +04:00
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2014-10-14 09:21:49 +04:00
|
|
|
|
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
2019-08-21 18:34:40 +03:00
|
|
|
params.channels = 2;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = CUBEB_LAYOUT_STEREO;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2014-10-14 09:21:49 +04:00
|
|
|
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2014-10-14 09:21:49 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
2014-10-14 09:21:49 +04:00
|
|
|
|
2014-11-28 05:56:44 +03:00
|
|
|
r = cubeb_stream_set_volume(stream, 1.0f);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(r == 0 || r == CUBEB_ERROR_NOT_SUPPORTED);
|
2014-10-14 09:21:49 +04:00
|
|
|
|
2020-09-29 00:55:10 +03:00
|
|
|
r = cubeb_stream_set_name(stream, "test 2");
|
|
|
|
ASSERT_TRUE(r == 0 || r == CUBEB_ERROR_NOT_SUPPORTED);
|
|
|
|
|
2014-10-14 09:21:49 +04:00
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2014-10-14 09:21:49 +04:00
|
|
|
|
2017-07-06 12:35:47 +03:00
|
|
|
TEST(cubeb, configure_stream_undefined_layout)
|
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
|
|
|
|
r = common_init(&ctx, "test_sanity");
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
|
|
|
|
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
2019-08-21 18:34:40 +03:00
|
|
|
params.channels = 2;
|
2017-07-06 12:35:47 +03:00
|
|
|
params.layout = CUBEB_LAYOUT_UNDEFINED;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2017-07-06 12:35:47 +03:00
|
|
|
|
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
|
|
|
test_data_callback, test_state_callback, &dummy);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
|
|
|
|
|
|
|
r = cubeb_stream_start(stream);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
|
|
|
delay(100);
|
|
|
|
|
|
|
|
r = cubeb_stream_stop(stream);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
|
|
|
}
|
|
|
|
|
2012-05-02 08:53:57 +04:00
|
|
|
static void
|
2012-12-05 06:55:34 +04:00
|
|
|
test_init_start_stop_destroy_multiple_streams(int early, int delay_ms)
|
2012-05-02 08:53:57 +04:00
|
|
|
{
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t i;
|
2012-05-02 08:53:57 +04:00
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
2014-09-17 09:22:06 +04:00
|
|
|
cubeb_stream * stream[8];
|
2012-05-02 08:53:57 +04:00
|
|
|
cubeb_stream_params params;
|
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2012-05-02 08:53:57 +04:00
|
|
|
|
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2012-05-02 08:53:57 +04:00
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream[i], "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2012-05-02 08:53:57 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream[i], nullptr);
|
2012-05-02 08:53:57 +04:00
|
|
|
if (early) {
|
|
|
|
r = cubeb_stream_start(stream[i]);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (!early) {
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2012-05-02 08:53:57 +04:00
|
|
|
r = cubeb_stream_start(stream[i]);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-12-05 06:55:34 +04:00
|
|
|
if (delay_ms) {
|
|
|
|
delay(delay_ms);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
|
|
|
|
|
|
|
if (!early) {
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2012-05-02 08:53:57 +04:00
|
|
|
r = cubeb_stream_stop(stream[i]);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(stream); ++i) {
|
2012-05-02 08:53:57 +04:00
|
|
|
if (early) {
|
|
|
|
r = cubeb_stream_stop(stream[i]);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2012-05-02 08:53:57 +04:00
|
|
|
}
|
|
|
|
cubeb_stream_destroy(stream[i]);
|
|
|
|
}
|
|
|
|
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2012-05-02 08:53:57 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_start_stop_destroy_multiple_streams)
|
2016-11-10 07:06:08 +03:00
|
|
|
{
|
|
|
|
/* Sometimes, when using WASAPI on windows 7 (vista and 8 are okay), and
|
|
|
|
* calling Activate a lot on an AudioClient, 0x800700b7 is returned. This is
|
|
|
|
* the HRESULT value for "Cannot create a file when that file already exists",
|
|
|
|
* and is not documented as a possible return value for this call. Hence, we
|
|
|
|
* try to limit the number of streams we create in this test. */
|
|
|
|
if (!is_windows_7()) {
|
|
|
|
delay_callback = 0;
|
|
|
|
test_init_start_stop_destroy_multiple_streams(0, 0);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(1, 0);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(0, 150);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(1, 150);
|
|
|
|
delay_callback = 1;
|
|
|
|
test_init_start_stop_destroy_multiple_streams(0, 0);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(1, 0);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(0, 150);
|
|
|
|
test_init_start_stop_destroy_multiple_streams(1, 150);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, init_destroy_multiple_contexts_and_streams)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t i, j;
|
2011-07-08 08:23:47 +04:00
|
|
|
int r;
|
2014-09-17 09:22:06 +04:00
|
|
|
cubeb * ctx[2];
|
|
|
|
cubeb_stream * stream[8];
|
2011-07-08 08:23:47 +04:00
|
|
|
cubeb_stream_params params;
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t streams_per_ctx = ARRAY_LENGTH(stream) / ARRAY_LENGTH(ctx);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(ARRAY_LENGTH(ctx) * streams_per_ctx, ARRAY_LENGTH(stream));
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-10 07:06:08 +03:00
|
|
|
/* Sometimes, when using WASAPI on windows 7 (vista and 8 are okay), and
|
|
|
|
* calling Activate a lot on an AudioClient, 0x800700b7 is returned. This is
|
|
|
|
* the HRESULT value for "Cannot create a file when that file already exists",
|
|
|
|
* and is not documented as a possible return value for this call. Hence, we
|
|
|
|
* try to limit the number of streams we create in this test. */
|
|
|
|
if (is_windows_7())
|
|
|
|
return;
|
|
|
|
|
2015-11-26 00:57:04 +03:00
|
|
|
params.format = STREAM_FORMAT;
|
2011-08-29 07:56:02 +04:00
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(ctx); ++i) {
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx[i], "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx[i], nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (j = 0; j < streams_per_ctx; ++j) {
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx[i], &stream[i * streams_per_ctx + j], "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream[i * streams_per_ctx + j], nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-09-17 09:34:37 +04:00
|
|
|
for (i = 0; i < ARRAY_LENGTH(ctx); ++i) {
|
|
|
|
for (j = 0; j < streams_per_ctx; ++j) {
|
|
|
|
cubeb_stream_destroy(stream[i * streams_per_ctx + j]);
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
|
|
|
cubeb_destroy(ctx[i]);
|
|
|
|
}
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, basic_stream_operations)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
uint64_t position;
|
2018-12-17 21:59:21 +03:00
|
|
|
uint32_t latency;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
/* position and latency before stream has started */
|
2011-07-08 08:23:47 +04:00
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_EQ(position, 0u);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
r = cubeb_stream_get_latency(stream, &latency);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
r = cubeb_stream_start(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
/* position and latency after while stream running */
|
2011-07-08 08:23:47 +04:00
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
r = cubeb_stream_get_latency(stream, &latency);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
r = cubeb_stream_stop(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
/* position and latency after stream has stopped */
|
2011-07-08 08:23:47 +04:00
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2018-12-17 21:59:21 +03:00
|
|
|
r = cubeb_stream_get_latency(stream, &latency);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, stream_position)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2014-09-29 05:04:25 +04:00
|
|
|
size_t i;
|
2011-07-08 08:23:47 +04:00
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
uint64_t position, last_position;
|
|
|
|
|
2015-11-26 00:57:04 +03:00
|
|
|
total_frames_written = 0;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_data_callback, test_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
/* stream position should not advance before starting playback */
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_EQ(position, 0u);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_EQ(position, 0u);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
/* stream position should advance during playback */
|
|
|
|
r = cubeb_stream_start(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-03 08:45:29 +04:00
|
|
|
/* XXX let start happen */
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-08-03 08:45:29 +04:00
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
/* stream should have prefilled */
|
2016-11-11 06:27:12 +03:00
|
|
|
ASSERT_TRUE(total_frames_written.load() > 0);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
last_position = position;
|
|
|
|
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_GE(position, last_position);
|
2011-07-08 08:23:47 +04:00
|
|
|
last_position = position;
|
|
|
|
|
|
|
|
/* stream position should not exceed total frames written */
|
|
|
|
for (i = 0; i < 5; ++i) {
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_GE(position, last_position);
|
2016-11-11 06:27:12 +03:00
|
|
|
ASSERT_LE(position, total_frames_written.load());
|
2011-07-08 08:23:47 +04:00
|
|
|
last_position = position;
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
|
|
|
|
2016-10-21 16:28:17 +03:00
|
|
|
/* test that the position is valid even when starting and
|
|
|
|
* stopping the stream. */
|
|
|
|
for (i = 0; i < 5; ++i) {
|
|
|
|
r = cubeb_stream_stop(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2016-10-21 16:28:17 +03:00
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(last_position < position);
|
2016-10-21 16:28:17 +03:00
|
|
|
last_position = position;
|
|
|
|
delay(500);
|
|
|
|
r = cubeb_stream_start(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2016-10-21 16:28:17 +03:00
|
|
|
delay(500);
|
|
|
|
}
|
|
|
|
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_NE(last_position, 0u);
|
2011-08-03 08:45:29 +04:00
|
|
|
|
2011-07-08 08:23:47 +04:00
|
|
|
/* stream position should not advance after stopping playback */
|
|
|
|
r = cubeb_stream_stop(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
/* XXX allow stream to settle */
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
last_position = position;
|
|
|
|
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_EQ(position, last_position);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 06:27:12 +03:00
|
|
|
static std::atomic<int> do_drain;
|
|
|
|
static std::atomic<int> got_drain;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
static long
|
2016-08-23 04:20:54 +03:00
|
|
|
test_drain_data_callback(cubeb_stream * stm, void * user_ptr, const void * /*inputbuffer*/, void * outputbuffer, long nframes)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2016-11-10 05:48:17 +03:00
|
|
|
EXPECT_TRUE(stm && user_ptr == &dummy && outputbuffer && nframes > 0);
|
2016-11-15 06:25:27 +03:00
|
|
|
assert(outputbuffer);
|
2011-07-08 08:23:47 +04:00
|
|
|
if (do_drain == 1) {
|
|
|
|
do_drain = 2;
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
/* once drain has started, callback must never be called again */
|
2016-11-10 05:48:17 +03:00
|
|
|
EXPECT_TRUE(do_drain != 2);
|
Preparatory work for the input and duplex code
This is changing all the signatures of the `cubeb_stream_init` implementations,
the signature of the `data_callback` type, so that cubeb can support audio
input.
`cubeb_stream_init` now has two `cubeb_stream_params` pointers, one for input,
one for output. If two pointers are passed, a "duplex" stream is opened. If only
one pointer is passed, an input-only or output-only stream is created.
Duplex streams have the same sample rate, and sample type. They don't have to
have the same number of channels.
`data_callback` now has two pointers to audio buffers: an input buffer (`NULL`
if this is an output-only stream) containing input data (e.g. a microphone), and
an output buffer, to be filled, as usual, with the audio frames to play. The
two buffers always have the exact same number of audio frames, and are
temporally correlated in a way that ensures the minimal loop-back latency on
the system if one directly copies the input buffer to the output buffer.
No functionnal changes are present in this patch, just signature changes.
Asserts have been added to prevent users to try to use the input code path for
now.
Actual implementations with the input code for different platforms will follow.
Green `mozilla-central` push:
<https://treeherder.mozilla.org/#/jobs?repo=try&revision=15b4dd3cbbe8>
2016-01-13 19:16:50 +03:00
|
|
|
memset(outputbuffer, 0, nframes * sizeof(short));
|
2011-07-08 08:23:47 +04:00
|
|
|
total_frames_written += nframes;
|
|
|
|
return nframes;
|
|
|
|
}
|
|
|
|
|
2012-06-06 07:33:12 +04:00
|
|
|
void
|
2016-08-23 04:20:54 +03:00
|
|
|
test_drain_state_callback(cubeb_stream * /*stm*/, void * /*user_ptr*/, cubeb_state state)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
if (state == CUBEB_STATE_DRAINED) {
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(!got_drain);
|
2011-07-08 08:23:47 +04:00
|
|
|
got_drain = 1;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, drain)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_stream * stream;
|
|
|
|
cubeb_stream_params params;
|
|
|
|
uint64_t position;
|
|
|
|
|
2016-11-10 07:06:08 +03:00
|
|
|
delay_callback = 0;
|
2015-11-26 00:57:04 +03:00
|
|
|
total_frames_written = 0;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2017-05-23 05:35:29 +03:00
|
|
|
r = common_init(&ctx, "test_sanity");
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2011-08-29 07:56:02 +04:00
|
|
|
params.format = STREAM_FORMAT;
|
|
|
|
params.rate = STREAM_RATE;
|
|
|
|
params.channels = STREAM_CHANNELS;
|
2016-12-21 08:18:07 +03:00
|
|
|
params.layout = STREAM_LAYOUT;
|
2018-01-22 19:13:00 +03:00
|
|
|
params.prefs = CUBEB_STREAM_PREF_NONE;
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-01-20 21:17:11 +03:00
|
|
|
r = cubeb_stream_init(ctx, &stream, "test", NULL, NULL, NULL, ¶ms, STREAM_LATENCY,
|
2011-07-08 08:23:47 +04:00
|
|
|
test_drain_data_callback, test_drain_state_callback, &dummy);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(stream, nullptr);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
r = cubeb_stream_start(stream);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2021-07-27 17:36:15 +03:00
|
|
|
delay(5000);
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
do_drain = 1;
|
|
|
|
|
|
|
|
for (;;) {
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2011-07-08 08:23:47 +04:00
|
|
|
if (got_drain) {
|
|
|
|
break;
|
2014-02-26 22:48:20 +04:00
|
|
|
} else {
|
2016-11-11 06:27:12 +03:00
|
|
|
ASSERT_LE(position, total_frames_written.load());
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
2012-12-05 06:55:34 +04:00
|
|
|
delay(500);
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
|
|
|
|
|
|
|
r = cubeb_stream_get_position(stream, &position);
|
2016-11-10 06:17:30 +03:00
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
2016-11-10 05:48:17 +03:00
|
|
|
ASSERT_TRUE(got_drain);
|
2013-09-02 23:16:49 +04:00
|
|
|
|
2014-09-29 04:01:36 +04:00
|
|
|
// Really, we should be able to rely on position reaching our final written frame, but
|
|
|
|
// for now let's make sure it doesn't continue beyond that point.
|
2016-11-11 06:27:12 +03:00
|
|
|
//ASSERT_LE(position, total_frames_written.load());
|
2011-07-08 08:23:47 +04:00
|
|
|
|
|
|
|
cubeb_stream_destroy(stream);
|
|
|
|
cubeb_destroy(ctx);
|
2016-11-18 08:03:27 +03:00
|
|
|
|
|
|
|
got_drain = 0;
|
|
|
|
do_drain = 0;
|
2015-11-26 00:57:04 +03:00
|
|
|
}
|
2011-07-08 08:23:47 +04:00
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, DISABLED_eos_during_prefill)
|
2012-05-04 05:02:37 +04:00
|
|
|
{
|
2016-11-10 07:06:08 +03:00
|
|
|
// This test needs to be implemented.
|
2012-05-04 05:02:37 +04:00
|
|
|
}
|
|
|
|
|
2016-11-11 05:00:23 +03:00
|
|
|
TEST(cubeb, DISABLED_stream_destroy_pending_drain)
|
2011-07-08 08:23:47 +04:00
|
|
|
{
|
2016-11-10 07:06:08 +03:00
|
|
|
// This test needs to be implemented.
|
2011-07-08 08:23:47 +04:00
|
|
|
}
|
2017-05-24 04:06:09 +03:00
|
|
|
|
|
|
|
TEST(cubeb, stable_devid)
|
|
|
|
{
|
|
|
|
/* Test that the devid field of cubeb_device_info is stable
|
|
|
|
* (ie. compares equal) over two invocations of
|
|
|
|
* cubeb_enumerate_devices(). */
|
|
|
|
|
|
|
|
int r;
|
|
|
|
cubeb * ctx;
|
|
|
|
cubeb_device_collection first;
|
|
|
|
cubeb_device_collection second;
|
|
|
|
cubeb_device_type all_devices =
|
|
|
|
(cubeb_device_type) (CUBEB_DEVICE_TYPE_INPUT | CUBEB_DEVICE_TYPE_OUTPUT);
|
|
|
|
size_t n;
|
|
|
|
|
|
|
|
r = common_init(&ctx, "test_sanity");
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
ASSERT_NE(ctx, nullptr);
|
|
|
|
|
|
|
|
r = cubeb_enumerate_devices(ctx, all_devices, &first);
|
|
|
|
if (r == CUBEB_ERROR_NOT_SUPPORTED)
|
|
|
|
return;
|
|
|
|
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
|
|
|
r = cubeb_enumerate_devices(ctx, all_devices, &second);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
|
|
|
|
ASSERT_EQ(first.count, second.count);
|
|
|
|
for (n = 0; n < first.count; n++) {
|
|
|
|
ASSERT_EQ(first.device[n].devid, second.device[n].devid);
|
|
|
|
}
|
|
|
|
|
|
|
|
r = cubeb_device_collection_destroy(ctx, &first);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
r = cubeb_device_collection_destroy(ctx, &second);
|
|
|
|
ASSERT_EQ(r, CUBEB_OK);
|
|
|
|
cubeb_destroy(ctx);
|
|
|
|
}
|