cubeb_opensl.cpp (62711B)
1 /* 2 * Copyright © 2012 Mozilla Foundation 3 * 4 * This program is made available under an ISC-style license. See the 5 * accompanying file LICENSE for details. 6 */ 7 #undef NDEBUG 8 #include <SLES/OpenSLES.h> 9 #include <dlfcn.h> 10 #include <errno.h> 11 #include <math.h> 12 #include <memory> 13 #include <pthread.h> 14 #include <stdlib.h> 15 #include <time.h> 16 #include <vector> 17 #if defined(__ANDROID__) 18 #include "android/sles_definitions.h" 19 #include <SLES/OpenSLES_Android.h> 20 #include <android/api-level.h> 21 #include <android/log.h> 22 #include <dlfcn.h> 23 #include <sys/system_properties.h> 24 #endif 25 #include "android/cubeb-output-latency.h" 26 #include "cubeb-internal.h" 27 #include "cubeb/cubeb.h" 28 #include "cubeb_android.h" 29 #include "cubeb_array_queue.h" 30 #include "cubeb_resampler.h" 31 32 #define ANDROID_VERSION_GINGERBREAD_MR1 10 33 #define ANDROID_VERSION_JELLY_BEAN 18 34 #define ANDROID_VERSION_LOLLIPOP 21 35 #define ANDROID_VERSION_MARSHMALLOW 23 36 #define ANDROID_VERSION_N_MR1 25 37 38 #define DEFAULT_SAMPLE_RATE 48000 39 #define DEFAULT_NUM_OF_FRAMES 480 40 41 extern cubeb_ops const opensl_ops; 42 43 struct cubeb { 44 struct cubeb_ops const * ops; 45 void * lib; 46 SLInterfaceID SL_IID_BUFFERQUEUE; 47 SLInterfaceID SL_IID_PLAY; 48 #if defined(__ANDROID__) 49 SLInterfaceID SL_IID_ANDROIDCONFIGURATION; 50 SLInterfaceID SL_IID_ANDROIDSIMPLEBUFFERQUEUE; 51 #endif 52 SLInterfaceID SL_IID_VOLUME; 53 SLInterfaceID SL_IID_RECORD; 54 SLObjectItf engObj; 55 SLEngineItf eng; 56 SLObjectItf outmixObj; 57 output_latency_function * p_output_latency_function; 58 }; 59 60 #define NELEMS(A) (sizeof(A) / sizeof(A)[0]) 61 #define NBUFS 2 62 63 struct cubeb_stream { 64 /* Note: Must match cubeb_stream layout in cubeb.c. */ 65 cubeb * context; 66 void * user_ptr; 67 /**/ 68 pthread_mutex_t mutex; 69 SLObjectItf playerObj; 70 SLPlayItf play; 71 SLBufferQueueItf bufq; 72 SLVolumeItf volume; 73 void ** queuebuf; 74 uint32_t queuebuf_capacity; 75 uint32_t queuebuf_idx; 76 long queuebuf_len; 77 long bytespersec; 78 uint32_t framesize; 79 /* Total number of played frames. 80 * Synchronized by stream::mutex lock. */ 81 long written; 82 /* Flag indicating draining. Synchronized 83 * by stream::mutex lock. */ 84 int draining; 85 /* Flags to determine in/out.*/ 86 uint32_t input_enabled; 87 uint32_t output_enabled; 88 /* Recorder abstract object. */ 89 SLObjectItf recorderObj; 90 /* Recorder Itf for input capture. */ 91 SLRecordItf recorderItf; 92 /* Buffer queue for input capture. */ 93 SLAndroidSimpleBufferQueueItf recorderBufferQueueItf; 94 /* Store input buffers. */ 95 void ** input_buffer_array; 96 /* The capacity of the array. 97 * On capture only can be small (4). 98 * On full duplex is calculated to 99 * store 1 sec of data buffers. */ 100 uint32_t input_array_capacity; 101 /* Current filled index of input buffer array. 102 * It is initiated to -1 indicating buffering 103 * have not started yet. */ 104 int input_buffer_index; 105 /* Length of input buffer.*/ 106 uint32_t input_buffer_length; 107 /* Input frame size */ 108 uint32_t input_frame_size; 109 /* Device sampling rate. If user rate is not 110 * accepted an compatible rate is set. If it is 111 * accepted this is equal to params.rate. */ 112 uint32_t input_device_rate; 113 /* Exchange input buffers between input 114 * and full duplex threads. */ 115 array_queue * input_queue; 116 /* Silent input buffer used on full duplex. */ 117 void * input_silent_buffer; 118 /* Number of input frames from the start of the stream*/ 119 uint32_t input_total_frames; 120 /* Flag to stop the execution of user callback and 121 * close all working threads. Synchronized by 122 * stream::mutex lock. */ 123 uint32_t shutdown; 124 /* Store user callback. */ 125 cubeb_data_callback data_callback; 126 /* Store state callback. */ 127 cubeb_state_callback state_callback; 128 129 cubeb_resampler * resampler; 130 unsigned int user_output_rate; 131 unsigned int output_configured_rate; 132 unsigned int buffer_size_frames; 133 // Audio output latency used in cubeb_stream_get_position(). 134 unsigned int output_latency_ms; 135 int64_t lastPosition; 136 int64_t lastPositionTimeStamp; 137 int64_t lastCompensativePosition; 138 int voice_input; 139 int voice_output; 140 std::unique_ptr<cubeb_stream_params> input_params; 141 std::unique_ptr<cubeb_stream_params> output_params; 142 // A non-empty buffer means that f32 -> int16 conversion need to happen 143 std::vector<float> conversion_buffer_output; 144 std::vector<float> conversion_buffer_input; 145 }; 146 147 /* Forward declaration. */ 148 static int 149 opensl_stop_player(cubeb_stream * stm); 150 static int 151 opensl_stop_recorder(cubeb_stream * stm); 152 153 static int 154 opensl_get_draining(cubeb_stream * stm) 155 { 156 #ifdef DEBUG 157 int r = pthread_mutex_trylock(&stm->mutex); 158 XASSERT((r == EDEADLK || r == EBUSY) && 159 "get_draining: mutex should be locked but it's not."); 160 #endif 161 return stm->draining; 162 } 163 164 static void 165 opensl_set_draining(cubeb_stream * stm, int value) 166 { 167 #ifdef DEBUG 168 int r = pthread_mutex_trylock(&stm->mutex); 169 LOG("set draining try r = %d", r); 170 XASSERT((r == EDEADLK || r == EBUSY) && 171 "set_draining: mutex should be locked but it's not."); 172 #endif 173 XASSERT(value == 0 || value == 1); 174 stm->draining = value; 175 } 176 177 static void 178 opensl_notify_drained(cubeb_stream * stm) 179 { 180 XASSERT(stm); 181 int r = pthread_mutex_lock(&stm->mutex); 182 XASSERT(r == 0); 183 int draining = opensl_get_draining(stm); 184 r = pthread_mutex_unlock(&stm->mutex); 185 XASSERT(r == 0); 186 if (draining) { 187 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_DRAINED); 188 if (stm->play) { 189 LOG("stop player in play_callback"); 190 r = opensl_stop_player(stm); 191 XASSERT(r == CUBEB_OK); 192 } 193 if (stm->recorderItf) { 194 r = opensl_stop_recorder(stm); 195 XASSERT(r == CUBEB_OK); 196 } 197 } 198 } 199 200 static uint32_t 201 opensl_get_shutdown(cubeb_stream * stm) 202 { 203 #ifdef DEBUG 204 int r = pthread_mutex_trylock(&stm->mutex); 205 XASSERT((r == EDEADLK || r == EBUSY) && 206 "get_shutdown: mutex should be locked but it's not."); 207 #endif 208 return stm->shutdown; 209 } 210 211 static void 212 opensl_set_shutdown(cubeb_stream * stm, uint32_t value) 213 { 214 #ifdef DEBUG 215 int r = pthread_mutex_trylock(&stm->mutex); 216 LOG("set shutdown try r = %d", r); 217 XASSERT((r == EDEADLK || r == EBUSY) && 218 "set_shutdown: mutex should be locked but it's not."); 219 #endif 220 XASSERT(value == 0 || value == 1); 221 stm->shutdown = value; 222 } 223 224 static void 225 play_callback(SLPlayItf caller, void * user_ptr, SLuint32 event) 226 { 227 cubeb_stream * stm = static_cast<cubeb_stream *>(user_ptr); 228 XASSERT(stm); 229 switch (event) { 230 case SL_PLAYEVENT_HEADATMARKER: 231 opensl_notify_drained(stm); 232 break; 233 default: 234 break; 235 } 236 } 237 238 static void 239 recorder_marker_callback(SLRecordItf caller, void * pContext, SLuint32 event) 240 { 241 cubeb_stream * stm = static_cast<cubeb_stream *>(pContext); 242 XASSERT(stm); 243 244 if (event == SL_RECORDEVENT_HEADATMARKER) { 245 int r = pthread_mutex_lock(&stm->mutex); 246 XASSERT(r == 0); 247 int draining = opensl_get_draining(stm); 248 r = pthread_mutex_unlock(&stm->mutex); 249 XASSERT(r == 0); 250 if (draining) { 251 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_DRAINED); 252 if (stm->recorderItf) { 253 r = opensl_stop_recorder(stm); 254 XASSERT(r == CUBEB_OK); 255 } 256 if (stm->play) { 257 r = opensl_stop_player(stm); 258 XASSERT(r == CUBEB_OK); 259 } 260 } 261 } 262 } 263 264 // Returns a buffer suitable to write output data to. 265 void * 266 get_output_buffer(cubeb_stream * stm, void * output_buffer, 267 uint32_t sample_count) 268 { 269 if (stm->conversion_buffer_output.empty()) { 270 return output_buffer; 271 } 272 if (stm->conversion_buffer_output.size() < sample_count) { 273 stm->conversion_buffer_output.resize(sample_count); 274 } 275 return stm->conversion_buffer_output.data(); 276 } 277 278 void * 279 release_output_buffer(cubeb_stream * stm, void * original_output_buffer, 280 uint32_t sample_count) 281 { 282 if (stm->conversion_buffer_output.empty()) { 283 return original_output_buffer; 284 } 285 int16_t * int16_buf = reinterpret_cast<int16_t *>(original_output_buffer); 286 for (uint32_t i = 0; i < sample_count; i++) { 287 float v = stm->conversion_buffer_output[i] * 32768.0f; 288 float clamped = std::max(-32768.0f, std::min(32767.0f, v)); 289 int16_buf[i] = static_cast<int16_t>(clamped); 290 } 291 return original_output_buffer; 292 } 293 294 static void 295 bufferqueue_callback(SLBufferQueueItf caller, void * user_ptr) 296 { 297 cubeb_stream * stm = static_cast<cubeb_stream *>(user_ptr); 298 XASSERT(stm); 299 SLBufferQueueState state; 300 SLresult res; 301 long written = 0; 302 303 res = (*stm->bufq)->GetState(stm->bufq, &state); 304 XASSERT(res == SL_RESULT_SUCCESS); 305 306 if (state.count > 1) { 307 return; 308 } 309 310 void * buf = stm->queuebuf[stm->queuebuf_idx]; 311 void * buf_original_ptr = buf; 312 uint32_t sample_count = 313 stm->output_params->channels * stm->queuebuf_len / stm->framesize; 314 written = 0; 315 int r = pthread_mutex_lock(&stm->mutex); 316 XASSERT(r == 0); 317 int draining = opensl_get_draining(stm); 318 uint32_t shutdown = opensl_get_shutdown(stm); 319 r = pthread_mutex_unlock(&stm->mutex); 320 XASSERT(r == 0); 321 if (!draining && !shutdown) { 322 323 buf = get_output_buffer(stm, buf, sample_count); 324 325 written = cubeb_resampler_fill(stm->resampler, nullptr, nullptr, buf, 326 stm->queuebuf_len / stm->framesize); 327 328 buf = release_output_buffer(stm, buf_original_ptr, sample_count); 329 330 ALOGV("bufferqueue_callback: resampler fill returned %ld frames", written); 331 if (written < 0 || 332 written * stm->framesize > static_cast<uint32_t>(stm->queuebuf_len)) { 333 ALOGV("bufferqueue_callback: error, shutting down"); 334 r = pthread_mutex_lock(&stm->mutex); 335 XASSERT(r == 0); 336 opensl_set_shutdown(stm, 1); 337 r = pthread_mutex_unlock(&stm->mutex); 338 XASSERT(r == 0); 339 opensl_stop_player(stm); 340 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR); 341 return; 342 } 343 } 344 345 // Keep sending silent data even in draining mode to prevent the audio 346 // back-end from being stopped automatically by OpenSL/ES. 347 XASSERT(static_cast<uint32_t>(stm->queuebuf_len) >= written * stm->framesize); 348 memset(reinterpret_cast<uint8_t *>(buf) + written * stm->framesize, 0, 349 stm->queuebuf_len - written * stm->framesize); 350 res = (*stm->bufq)->Enqueue(stm->bufq, buf, stm->queuebuf_len); 351 XASSERT(res == SL_RESULT_SUCCESS); 352 stm->queuebuf_idx = (stm->queuebuf_idx + 1) % stm->queuebuf_capacity; 353 354 if (written > 0) { 355 pthread_mutex_lock(&stm->mutex); 356 stm->written += written; 357 pthread_mutex_unlock(&stm->mutex); 358 } 359 360 if (!draining && 361 written * stm->framesize < static_cast<uint32_t>(stm->queuebuf_len)) { 362 LOG("bufferqueue_callback draining"); 363 r = pthread_mutex_lock(&stm->mutex); 364 XASSERT(r == 0); 365 int64_t written_duration = 366 INT64_C(1000) * stm->written * stm->framesize / stm->bytespersec; 367 opensl_set_draining(stm, 1); 368 r = pthread_mutex_unlock(&stm->mutex); 369 XASSERT(r == 0); 370 371 if (written_duration == 0) { 372 // since we didn't write any sample, it's not possible to reach the marker 373 // time and trigger the callback. We should initiative notify drained. 374 opensl_notify_drained(stm); 375 } else { 376 // Use SL_PLAYEVENT_HEADATMARKER event from slPlayCallback of SLPlayItf 377 // to make sure all the data has been processed. 378 (*stm->play) 379 ->SetMarkerPosition(stm->play, (SLmillisecond)written_duration); 380 } 381 return; 382 } 383 } 384 385 static int 386 opensl_enqueue_recorder(cubeb_stream * stm, void ** last_filled_buffer) 387 { 388 XASSERT(stm); 389 390 int current_index = stm->input_buffer_index; 391 void * last_buffer = nullptr; 392 393 if (current_index < 0) { 394 // This is the first enqueue 395 current_index = 0; 396 } else { 397 // The current index hold the last filled buffer get it before advance 398 // index. 399 last_buffer = stm->input_buffer_array[current_index]; 400 // Advance to get next available buffer 401 current_index = 402 static_cast<int>((current_index + 1) % stm->input_array_capacity); 403 } 404 // enqueue next empty buffer to be filled by the recorder 405 SLresult res = (*stm->recorderBufferQueueItf) 406 ->Enqueue(stm->recorderBufferQueueItf, 407 stm->input_buffer_array[current_index], 408 stm->input_buffer_length); 409 if (res != SL_RESULT_SUCCESS) { 410 LOG("Enqueue recorder failed. Error code: %u", res); 411 return CUBEB_ERROR; 412 } 413 // All good, update buffer and index. 414 stm->input_buffer_index = current_index; 415 if (last_filled_buffer) { 416 *last_filled_buffer = last_buffer; 417 } 418 return CUBEB_OK; 419 } 420 421 // If necessary, convert and returns an input buffer. 422 // Otherwise, just returns the pointer that has been passed in. 423 void * 424 convert_input_buffer_if_needed(cubeb_stream * stm, void * input_buffer, 425 uint32_t sample_count) 426 { 427 // Perform conversion if needed 428 if (stm->conversion_buffer_input.empty()) { 429 return input_buffer; 430 } 431 if (stm->conversion_buffer_input.size() < sample_count) { 432 stm->conversion_buffer_input.resize(sample_count); 433 } 434 int16_t * int16_buf = reinterpret_cast<int16_t *>(input_buffer); 435 for (uint32_t i = 0; i < sample_count; i++) { 436 stm->conversion_buffer_input[i] = 437 static_cast<float>(int16_buf[i]) / 32768.f; 438 } 439 return stm->conversion_buffer_input.data(); 440 } 441 442 // input data callback 443 void 444 recorder_callback(SLAndroidSimpleBufferQueueItf bq, void * context) 445 { 446 XASSERT(context); 447 cubeb_stream * stm = static_cast<cubeb_stream *>(context); 448 XASSERT(stm->recorderBufferQueueItf); 449 450 int r = pthread_mutex_lock(&stm->mutex); 451 XASSERT(r == 0); 452 uint32_t shutdown = opensl_get_shutdown(stm); 453 int draining = opensl_get_draining(stm); 454 r = pthread_mutex_unlock(&stm->mutex); 455 XASSERT(r == 0); 456 457 if (shutdown || draining) { 458 // According to the OpenSL ES 1.1 Specification, 8.14 SLBufferQueueItf 459 // page 184, on transition to the SL_RECORDSTATE_STOPPED state, 460 // the application should continue to enqueue buffers onto the queue 461 // to retrieve the residual recorded data in the system. 462 r = opensl_enqueue_recorder(stm, nullptr); 463 XASSERT(r == CUBEB_OK); 464 return; 465 } 466 467 // Enqueue next available buffer and get the last filled buffer. 468 void * input_buffer = nullptr; 469 r = opensl_enqueue_recorder(stm, &input_buffer); 470 XASSERT(r == CUBEB_OK); 471 XASSERT(input_buffer); 472 473 long input_frame_count = stm->input_buffer_length / stm->input_frame_size; 474 uint32_t sample_count = input_frame_count * stm->input_params->channels; 475 476 input_buffer = 477 convert_input_buffer_if_needed(stm, input_buffer, sample_count); 478 479 // Fill resampler with last input 480 long got = cubeb_resampler_fill(stm->resampler, input_buffer, 481 &input_frame_count, nullptr, 0); 482 // Error case 483 if (got < 0 || got > input_frame_count) { 484 r = pthread_mutex_lock(&stm->mutex); 485 XASSERT(r == 0); 486 opensl_set_shutdown(stm, 1); 487 r = pthread_mutex_unlock(&stm->mutex); 488 XASSERT(r == 0); 489 r = opensl_stop_recorder(stm); 490 XASSERT(r == CUBEB_OK); 491 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR); 492 } 493 494 // Advance total stream frames 495 stm->input_total_frames += got; 496 497 if (got < input_frame_count) { 498 r = pthread_mutex_lock(&stm->mutex); 499 XASSERT(r == 0); 500 opensl_set_draining(stm, 1); 501 r = pthread_mutex_unlock(&stm->mutex); 502 XASSERT(r == 0); 503 int64_t duration = 504 INT64_C(1000) * stm->input_total_frames / stm->input_device_rate; 505 (*stm->recorderItf) 506 ->SetMarkerPosition(stm->recorderItf, (SLmillisecond)duration); 507 return; 508 } 509 } 510 511 void 512 recorder_fullduplex_callback(SLAndroidSimpleBufferQueueItf bq, void * context) 513 { 514 XASSERT(context); 515 cubeb_stream * stm = static_cast<cubeb_stream *>(context); 516 XASSERT(stm->recorderBufferQueueItf); 517 518 int r = pthread_mutex_lock(&stm->mutex); 519 XASSERT(r == 0); 520 int draining = opensl_get_draining(stm); 521 uint32_t shutdown = opensl_get_shutdown(stm); 522 r = pthread_mutex_unlock(&stm->mutex); 523 XASSERT(r == 0); 524 525 if (shutdown || draining) { 526 /* On draining and shutdown the recorder should have been stoped from 527 * the one set the flags. Accordint to the doc, on transition to 528 * the SL_RECORDSTATE_STOPPED state, the application should 529 * continue to enqueue buffers onto the queue to retrieve the residual 530 * recorded data in the system. */ 531 LOG("Input shutdown %d or drain %d", shutdown, draining); 532 int r = opensl_enqueue_recorder(stm, nullptr); 533 XASSERT(r == CUBEB_OK); 534 return; 535 } 536 537 // Enqueue next available buffer and get the last filled buffer. 538 void * input_buffer = nullptr; 539 r = opensl_enqueue_recorder(stm, &input_buffer); 540 XASSERT(r == CUBEB_OK); 541 XASSERT(input_buffer); 542 543 XASSERT(stm->input_queue); 544 r = array_queue_push(stm->input_queue, input_buffer); 545 if (r == -1) { 546 LOG("Input queue is full, drop input ..."); 547 return; 548 } 549 550 LOG("Input pushed in the queue, input array %zu", 551 array_queue_get_size(stm->input_queue)); 552 } 553 554 static void 555 player_fullduplex_callback(SLBufferQueueItf caller, void * user_ptr) 556 { 557 cubeb_stream * stm = static_cast<cubeb_stream *>(user_ptr); 558 XASSERT(stm); 559 SLresult res; 560 561 int r = pthread_mutex_lock(&stm->mutex); 562 XASSERT(r == 0); 563 int draining = opensl_get_draining(stm); 564 uint32_t shutdown = opensl_get_shutdown(stm); 565 r = pthread_mutex_unlock(&stm->mutex); 566 XASSERT(r == 0); 567 568 // Get output 569 void * output_buffer = nullptr; 570 r = pthread_mutex_lock(&stm->mutex); 571 XASSERT(r == 0); 572 output_buffer = stm->queuebuf[stm->queuebuf_idx]; 573 void * output_buffer_original_ptr = output_buffer; 574 // Advance the output buffer queue index 575 stm->queuebuf_idx = (stm->queuebuf_idx + 1) % stm->queuebuf_capacity; 576 r = pthread_mutex_unlock(&stm->mutex); 577 XASSERT(r == 0); 578 579 if (shutdown || draining) { 580 LOG("Shutdown/draining, send silent"); 581 // Set silent on buffer 582 memset(output_buffer, 0, stm->queuebuf_len); 583 584 // Enqueue data in player buffer queue 585 res = (*stm->bufq)->Enqueue(stm->bufq, output_buffer, stm->queuebuf_len); 586 XASSERT(res == SL_RESULT_SUCCESS); 587 return; 588 } 589 590 // Get input. 591 void * input_buffer = array_queue_pop(stm->input_queue); 592 long input_frame_count = stm->input_buffer_length / stm->input_frame_size; 593 long sample_count = input_frame_count * stm->input_params->channels; 594 long frames_needed = stm->queuebuf_len / stm->framesize; 595 uint32_t output_sample_count = 596 stm->output_params->channels * stm->queuebuf_len / stm->framesize; 597 598 if (!input_buffer) { 599 LOG("Input hole set silent input buffer"); 600 input_buffer = stm->input_silent_buffer; 601 } 602 603 input_buffer = 604 convert_input_buffer_if_needed(stm, input_buffer, sample_count); 605 606 output_buffer = get_output_buffer(stm, output_buffer, output_sample_count); 607 608 long written = 0; 609 // Trigger user callback through resampler 610 written = 611 cubeb_resampler_fill(stm->resampler, input_buffer, &input_frame_count, 612 output_buffer, frames_needed); 613 614 output_buffer = 615 release_output_buffer(stm, output_buffer_original_ptr, sample_count); 616 617 LOG("Fill: written %ld, frames_needed %ld, input array size %zu", written, 618 frames_needed, array_queue_get_size(stm->input_queue)); 619 620 if (written < 0 || written > frames_needed) { 621 // Error case 622 r = pthread_mutex_lock(&stm->mutex); 623 XASSERT(r == 0); 624 opensl_set_shutdown(stm, 1); 625 r = pthread_mutex_unlock(&stm->mutex); 626 XASSERT(r == 0); 627 opensl_stop_player(stm); 628 opensl_stop_recorder(stm); 629 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR); 630 memset(output_buffer, 0, stm->queuebuf_len); 631 632 // Enqueue data in player buffer queue 633 res = (*stm->bufq)->Enqueue(stm->bufq, output_buffer, stm->queuebuf_len); 634 XASSERT(res == SL_RESULT_SUCCESS); 635 return; 636 } 637 638 // Advance total out written frames counter 639 r = pthread_mutex_lock(&stm->mutex); 640 XASSERT(r == 0); 641 stm->written += written; 642 r = pthread_mutex_unlock(&stm->mutex); 643 XASSERT(r == 0); 644 645 if (written < frames_needed) { 646 r = pthread_mutex_lock(&stm->mutex); 647 XASSERT(r == 0); 648 int64_t written_duration = 649 INT64_C(1000) * stm->written * stm->framesize / stm->bytespersec; 650 opensl_set_draining(stm, 1); 651 r = pthread_mutex_unlock(&stm->mutex); 652 XASSERT(r == 0); 653 654 // Use SL_PLAYEVENT_HEADATMARKER event from slPlayCallback of SLPlayItf 655 // to make sure all the data has been processed. 656 (*stm->play)->SetMarkerPosition(stm->play, (SLmillisecond)written_duration); 657 } 658 659 // Keep sending silent data even in draining mode to prevent the audio 660 // back-end from being stopped automatically by OpenSL/ES. 661 memset((uint8_t *)output_buffer + written * stm->framesize, 0, 662 stm->queuebuf_len - written * stm->framesize); 663 664 // Enqueue data in player buffer queue 665 res = (*stm->bufq)->Enqueue(stm->bufq, output_buffer, stm->queuebuf_len); 666 XASSERT(res == SL_RESULT_SUCCESS); 667 } 668 669 static void 670 opensl_destroy(cubeb * ctx); 671 672 #if defined(__ANDROID__) 673 #if (__ANDROID_API__ >= ANDROID_VERSION_LOLLIPOP) 674 using system_property_get = int(const char *, char *); 675 676 static int 677 wrap_system_property_get(const char * name, char * value) 678 { 679 void * libc = dlopen("libc.so", RTLD_LAZY); 680 if (!libc) { 681 LOG("Failed to open libc.so"); 682 return -1; 683 } 684 system_property_get * func = 685 (system_property_get *)dlsym(libc, "__system_property_get"); 686 int ret = -1; 687 if (func) { 688 ret = func(name, value); 689 } 690 dlclose(libc); 691 return ret; 692 } 693 #endif 694 695 static int 696 get_android_version(void) 697 { 698 char version_string[PROP_VALUE_MAX]; 699 700 memset(version_string, 0, PROP_VALUE_MAX); 701 702 #if (__ANDROID_API__ >= ANDROID_VERSION_LOLLIPOP) 703 int len = wrap_system_property_get("ro.build.version.sdk", version_string); 704 #else 705 int len = __system_property_get("ro.build.version.sdk", version_string); 706 #endif 707 if (len <= 0) { 708 LOG("Failed to get Android version!\n"); 709 return len; 710 } 711 712 int version = (int)strtol(version_string, nullptr, 10); 713 LOG("Android version %d", version); 714 return version; 715 } 716 #endif 717 718 extern "C" { 719 int 720 opensl_init(cubeb ** context, char const * context_name) 721 { 722 cubeb * ctx; 723 724 #if defined(__ANDROID__) 725 int android_version = get_android_version(); 726 if (android_version > 0 && 727 android_version <= ANDROID_VERSION_GINGERBREAD_MR1) { 728 // Don't even attempt to run on Gingerbread and lower 729 LOG("Error: Android version too old, exiting."); 730 return CUBEB_ERROR; 731 } 732 #endif 733 734 *context = nullptr; 735 736 ctx = static_cast<cubeb *>(calloc(1, sizeof(*ctx))); 737 XASSERT(ctx); 738 739 ctx->ops = &opensl_ops; 740 741 ctx->lib = dlopen("libOpenSLES.so", RTLD_LAZY); 742 if (!ctx->lib) { 743 LOG("Error: Couldn't find libOpenSLES.so, exiting"); 744 free(ctx); 745 return CUBEB_ERROR; 746 } 747 748 typedef SLresult (*slCreateEngine_t)( 749 SLObjectItf *, SLuint32, const SLEngineOption *, SLuint32, 750 const SLInterfaceID *, const SLboolean *); 751 slCreateEngine_t f_slCreateEngine = 752 (slCreateEngine_t)dlsym(ctx->lib, "slCreateEngine"); 753 SLInterfaceID SL_IID_ENGINE = 754 *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_ENGINE"); 755 SLInterfaceID SL_IID_OUTPUTMIX = 756 *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_OUTPUTMIX"); 757 ctx->SL_IID_VOLUME = *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_VOLUME"); 758 ctx->SL_IID_BUFFERQUEUE = 759 *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_BUFFERQUEUE"); 760 #if defined(__ANDROID__) 761 ctx->SL_IID_ANDROIDCONFIGURATION = 762 *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_ANDROIDCONFIGURATION"); 763 ctx->SL_IID_ANDROIDSIMPLEBUFFERQUEUE = 764 *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_ANDROIDSIMPLEBUFFERQUEUE"); 765 #endif 766 ctx->SL_IID_PLAY = *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_PLAY"); 767 ctx->SL_IID_RECORD = *(SLInterfaceID *)dlsym(ctx->lib, "SL_IID_RECORD"); 768 769 if (!f_slCreateEngine || !SL_IID_ENGINE || !SL_IID_OUTPUTMIX || 770 !ctx->SL_IID_BUFFERQUEUE || 771 #if defined(__ANDROID__) 772 !ctx->SL_IID_ANDROIDCONFIGURATION || 773 !ctx->SL_IID_ANDROIDSIMPLEBUFFERQUEUE || 774 #endif 775 !ctx->SL_IID_PLAY || !ctx->SL_IID_RECORD) { 776 LOG("Error: didn't find required symbols, exiting."); 777 opensl_destroy(ctx); 778 return CUBEB_ERROR; 779 } 780 781 const SLEngineOption opt[] = {{SL_ENGINEOPTION_THREADSAFE, SL_BOOLEAN_TRUE}}; 782 783 SLresult res; 784 res = f_slCreateEngine(&ctx->engObj, 1, opt, 0, nullptr, nullptr); 785 786 if (res != SL_RESULT_SUCCESS) { 787 LOG("Error: slCreateEngine failure, exiting."); 788 opensl_destroy(ctx); 789 return CUBEB_ERROR; 790 } 791 792 res = (*ctx->engObj)->Realize(ctx->engObj, SL_BOOLEAN_FALSE); 793 if (res != SL_RESULT_SUCCESS) { 794 LOG("Error: engine realization failure, exiting."); 795 opensl_destroy(ctx); 796 return CUBEB_ERROR; 797 } 798 799 res = (*ctx->engObj)->GetInterface(ctx->engObj, SL_IID_ENGINE, &ctx->eng); 800 if (res != SL_RESULT_SUCCESS) { 801 LOG("Error: GetInterface(..., SL_IID_ENGINE, ...), exiting."); 802 opensl_destroy(ctx); 803 return CUBEB_ERROR; 804 } 805 806 const SLInterfaceID idsom[] = {SL_IID_OUTPUTMIX}; 807 const SLboolean reqom[] = {SL_BOOLEAN_TRUE}; 808 res = 809 (*ctx->eng)->CreateOutputMix(ctx->eng, &ctx->outmixObj, 1, idsom, reqom); 810 if (res != SL_RESULT_SUCCESS) { 811 LOG("Error: CreateOutputMix failure, exiting."); 812 opensl_destroy(ctx); 813 return CUBEB_ERROR; 814 } 815 816 res = (*ctx->outmixObj)->Realize(ctx->outmixObj, SL_BOOLEAN_FALSE); 817 if (res != SL_RESULT_SUCCESS) { 818 LOG("Error: Output mix object failure, exiting."); 819 opensl_destroy(ctx); 820 return CUBEB_ERROR; 821 } 822 823 ctx->p_output_latency_function = 824 cubeb_output_latency_load_method(android_version); 825 if (!cubeb_output_latency_method_is_loaded(ctx->p_output_latency_function)) { 826 LOG("Warning: output latency is not available, cubeb_stream_get_position() " 827 "is not supported"); 828 } 829 830 *context = ctx; 831 832 LOG("Cubeb init (%p) success", ctx); 833 return CUBEB_OK; 834 } 835 } 836 837 static char const * 838 opensl_get_backend_id(cubeb * ctx) 839 { 840 return "opensl"; 841 } 842 843 static int 844 opensl_get_max_channel_count(cubeb * ctx, uint32_t * max_channels) 845 { 846 XASSERT(ctx && max_channels); 847 /* The android mixer handles up to two channels, see 848 http://androidxref.com/4.2.2_r1/xref/frameworks/av/services/audioflinger/AudioFlinger.h#67 849 */ 850 *max_channels = 2; 851 852 return CUBEB_OK; 853 } 854 855 static void 856 opensl_destroy(cubeb * ctx) 857 { 858 if (ctx->outmixObj) { 859 (*ctx->outmixObj)->Destroy(ctx->outmixObj); 860 } 861 if (ctx->engObj) { 862 (*ctx->engObj)->Destroy(ctx->engObj); 863 } 864 dlclose(ctx->lib); 865 if (ctx->p_output_latency_function) { 866 cubeb_output_latency_unload_method(ctx->p_output_latency_function); 867 } 868 free(ctx); 869 } 870 871 static void 872 opensl_stream_destroy(cubeb_stream * stm); 873 874 #if defined(__ANDROID__) && (__ANDROID_API__ >= ANDROID_VERSION_LOLLIPOP) 875 static int 876 opensl_set_format_ext(SLAndroidDataFormat_PCM_EX * format, 877 cubeb_stream_params * params) 878 { 879 XASSERT(format); 880 XASSERT(params); 881 882 format->formatType = SL_ANDROID_DATAFORMAT_PCM_EX; 883 format->numChannels = params->channels; 884 // sampleRate is in milliHertz 885 format->sampleRate = params->rate * 1000; 886 format->channelMask = params->channels == 1 887 ? SL_SPEAKER_FRONT_CENTER 888 : SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT; 889 890 switch (params->format) { 891 case CUBEB_SAMPLE_S16LE: 892 format->bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_16; 893 format->containerSize = SL_PCMSAMPLEFORMAT_FIXED_16; 894 format->representation = SL_ANDROID_PCM_REPRESENTATION_SIGNED_INT; 895 format->endianness = SL_BYTEORDER_LITTLEENDIAN; 896 break; 897 case CUBEB_SAMPLE_S16BE: 898 format->bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_16; 899 format->containerSize = SL_PCMSAMPLEFORMAT_FIXED_16; 900 format->representation = SL_ANDROID_PCM_REPRESENTATION_SIGNED_INT; 901 format->endianness = SL_BYTEORDER_BIGENDIAN; 902 break; 903 case CUBEB_SAMPLE_FLOAT32LE: 904 format->bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_32; 905 format->containerSize = SL_PCMSAMPLEFORMAT_FIXED_32; 906 format->representation = SL_ANDROID_PCM_REPRESENTATION_FLOAT; 907 format->endianness = SL_BYTEORDER_LITTLEENDIAN; 908 break; 909 case CUBEB_SAMPLE_FLOAT32BE: 910 format->bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_32; 911 format->containerSize = SL_PCMSAMPLEFORMAT_FIXED_32; 912 format->representation = SL_ANDROID_PCM_REPRESENTATION_FLOAT; 913 format->endianness = SL_BYTEORDER_BIGENDIAN; 914 break; 915 default: 916 return CUBEB_ERROR_INVALID_FORMAT; 917 } 918 return CUBEB_OK; 919 } 920 #endif 921 922 static int 923 opensl_set_format(SLDataFormat_PCM * format, cubeb_stream_params * params) 924 { 925 XASSERT(format); 926 XASSERT(params); 927 928 // If this function is called, this backend has been compiled with an older 929 // version of Android, that doesn't support floating point audio IO. 930 // The stream is configured with int16 of the proper endianess, and conversion 931 // will happen during playback. 932 933 format->formatType = SL_DATAFORMAT_PCM; 934 format->numChannels = params->channels; 935 // samplesPerSec is in milliHertz 936 format->samplesPerSec = params->rate * 1000; 937 format->bitsPerSample = SL_PCMSAMPLEFORMAT_FIXED_16; 938 format->containerSize = SL_PCMSAMPLEFORMAT_FIXED_16; 939 format->channelMask = params->channels == 1 940 ? SL_SPEAKER_FRONT_CENTER 941 : SL_SPEAKER_FRONT_LEFT | SL_SPEAKER_FRONT_RIGHT; 942 943 switch (params->format) { 944 case CUBEB_SAMPLE_S16LE: 945 case CUBEB_SAMPLE_FLOAT32LE: 946 format->endianness = SL_BYTEORDER_LITTLEENDIAN; 947 break; 948 case CUBEB_SAMPLE_S16BE: 949 case CUBEB_SAMPLE_FLOAT32BE: 950 format->endianness = SL_BYTEORDER_BIGENDIAN; 951 break; 952 default: 953 XASSERT(false && "unhandled value"); 954 } 955 return CUBEB_OK; 956 } 957 958 template <typename Function> 959 int 960 initialize_with_format(cubeb_stream * stm, cubeb_stream_params * params, 961 Function func) 962 { 963 void * format = nullptr; 964 bool using_floats = false; 965 uint32_t * format_sample_rate; 966 #if defined(__ANDROID__) && (__ANDROID_API__ >= ANDROID_VERSION_LOLLIPOP) 967 SLAndroidDataFormat_PCM_EX pcm_ext_format; 968 if (get_android_version() >= ANDROID_VERSION_LOLLIPOP) { 969 if (opensl_set_format_ext(&pcm_ext_format, params) != CUBEB_OK) { 970 LOG("opensl_set_format_ext: error, exiting"); 971 return CUBEB_ERROR_INVALID_FORMAT; 972 } 973 format = &pcm_ext_format; 974 format_sample_rate = &pcm_ext_format.sampleRate; 975 using_floats = 976 pcm_ext_format.representation == SL_ANDROID_PCM_REPRESENTATION_FLOAT; 977 } 978 #endif 979 980 SLDataFormat_PCM pcm_format; 981 if (!format) { 982 if (opensl_set_format(&pcm_format, params) != CUBEB_OK) { 983 LOG("opensl_set_format: error, exiting"); 984 return CUBEB_ERROR_INVALID_FORMAT; 985 } 986 format = &pcm_format; 987 format_sample_rate = &pcm_format.samplesPerSec; 988 } 989 990 return func(format, format_sample_rate, using_floats); 991 } 992 993 static int 994 opensl_configure_capture(cubeb_stream * stm, cubeb_stream_params * params) 995 { 996 XASSERT(stm); 997 XASSERT(params); 998 999 /* For now set device rate to params rate. */ 1000 stm->input_device_rate = params->rate; 1001 1002 int rv = initialize_with_format( 1003 stm, params, 1004 [=](void * format, uint32_t * format_sample_rate, 1005 bool using_floats) -> int { 1006 SLDataLocator_AndroidSimpleBufferQueue lDataLocatorOut; 1007 lDataLocatorOut.locatorType = SL_DATALOCATOR_ANDROIDSIMPLEBUFFERQUEUE; 1008 lDataLocatorOut.numBuffers = NBUFS; 1009 1010 SLDataSink dataSink; 1011 dataSink.pLocator = &lDataLocatorOut; 1012 dataSink.pFormat = format; 1013 1014 SLDataLocator_IODevice dataLocatorIn; 1015 dataLocatorIn.locatorType = SL_DATALOCATOR_IODEVICE; 1016 dataLocatorIn.deviceType = SL_IODEVICE_AUDIOINPUT; 1017 dataLocatorIn.deviceID = SL_DEFAULTDEVICEID_AUDIOINPUT; 1018 dataLocatorIn.device = nullptr; 1019 1020 SLDataSource dataSource; 1021 dataSource.pLocator = &dataLocatorIn; 1022 dataSource.pFormat = nullptr; 1023 1024 const SLInterfaceID lSoundRecorderIIDs[] = { 1025 stm->context->SL_IID_RECORD, 1026 stm->context->SL_IID_ANDROIDSIMPLEBUFFERQUEUE, 1027 stm->context->SL_IID_ANDROIDCONFIGURATION}; 1028 1029 const SLboolean lSoundRecorderReqs[] = { 1030 SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE}; 1031 // create the audio recorder abstract object 1032 SLresult res = 1033 (*stm->context->eng) 1034 ->CreateAudioRecorder(stm->context->eng, &stm->recorderObj, 1035 &dataSource, &dataSink, 1036 NELEMS(lSoundRecorderIIDs), 1037 lSoundRecorderIIDs, lSoundRecorderReqs); 1038 // Sample rate not supported. Try again with default sample rate! 1039 if (res == SL_RESULT_CONTENT_UNSUPPORTED) { 1040 if (stm->output_enabled && stm->output_configured_rate != 0) { 1041 // Set the same with the player. Since there is no 1042 // api for input device this is a safe choice. 1043 stm->input_device_rate = stm->output_configured_rate; 1044 } else { 1045 // The output preferred rate is used for an input only scenario. 1046 // The default rate expected to be supported from all android 1047 // devices. 1048 stm->input_device_rate = DEFAULT_SAMPLE_RATE; 1049 } 1050 *format_sample_rate = stm->input_device_rate * 1000; 1051 res = (*stm->context->eng) 1052 ->CreateAudioRecorder( 1053 stm->context->eng, &stm->recorderObj, &dataSource, 1054 &dataSink, NELEMS(lSoundRecorderIIDs), 1055 lSoundRecorderIIDs, lSoundRecorderReqs); 1056 } 1057 if (res != SL_RESULT_SUCCESS) { 1058 LOG("Failed to create recorder, not trying other input" 1059 " rate. Error code: %u", 1060 res); 1061 return CUBEB_ERROR; 1062 } 1063 // It's always possible to use int16 regardless of the Android version. 1064 // However if compiling for older Android version, it's possible to 1065 // request f32 audio, but Android only supports int16, in which case a 1066 // conversion need to happen. 1067 if ((params->format == CUBEB_SAMPLE_FLOAT32NE || 1068 params->format == CUBEB_SAMPLE_FLOAT32BE) && 1069 !using_floats) { 1070 // setup conversion from f32 to int16 1071 LOG("Input stream configured for using float, but not supported: a " 1072 "conversion will be performed"); 1073 stm->conversion_buffer_input.resize(1); 1074 } 1075 return CUBEB_OK; 1076 }); 1077 1078 if (rv != CUBEB_OK) { 1079 LOG("Could not initialize recorder."); 1080 return rv; 1081 } 1082 1083 SLresult res; 1084 if (get_android_version() > ANDROID_VERSION_JELLY_BEAN) { 1085 SLAndroidConfigurationItf recorderConfig; 1086 res = (*stm->recorderObj) 1087 ->GetInterface(stm->recorderObj, 1088 stm->context->SL_IID_ANDROIDCONFIGURATION, 1089 &recorderConfig); 1090 1091 if (res != SL_RESULT_SUCCESS) { 1092 LOG("Failed to get the android configuration interface for recorder. " 1093 "Error " 1094 "code: %u", 1095 res); 1096 return CUBEB_ERROR; 1097 } 1098 1099 // Voice recognition is the lowest latency, according to the docs. Camcorder 1100 // uses a microphone that is in the same direction as the camera. 1101 SLint32 streamType = stm->voice_input 1102 ? SL_ANDROID_RECORDING_PRESET_VOICE_RECOGNITION 1103 : SL_ANDROID_RECORDING_PRESET_CAMCORDER; 1104 1105 res = 1106 (*recorderConfig) 1107 ->SetConfiguration(recorderConfig, SL_ANDROID_KEY_RECORDING_PRESET, 1108 &streamType, sizeof(SLint32)); 1109 1110 if (res != SL_RESULT_SUCCESS) { 1111 LOG("Failed to set the android configuration to VOICE for the recorder. " 1112 "Error code: %u", 1113 res); 1114 return CUBEB_ERROR; 1115 } 1116 } 1117 // realize the audio recorder 1118 res = (*stm->recorderObj)->Realize(stm->recorderObj, SL_BOOLEAN_FALSE); 1119 if (res != SL_RESULT_SUCCESS) { 1120 LOG("Failed to realize recorder. Error code: %u", res); 1121 return CUBEB_ERROR; 1122 } 1123 // get the record interface 1124 res = (*stm->recorderObj) 1125 ->GetInterface(stm->recorderObj, stm->context->SL_IID_RECORD, 1126 &stm->recorderItf); 1127 if (res != SL_RESULT_SUCCESS) { 1128 LOG("Failed to get recorder interface. Error code: %u", res); 1129 return CUBEB_ERROR; 1130 } 1131 1132 res = (*stm->recorderItf) 1133 ->RegisterCallback(stm->recorderItf, recorder_marker_callback, stm); 1134 if (res != SL_RESULT_SUCCESS) { 1135 LOG("Failed to register recorder marker callback. Error code: %u", res); 1136 return CUBEB_ERROR; 1137 } 1138 1139 (*stm->recorderItf)->SetMarkerPosition(stm->recorderItf, (SLmillisecond)0); 1140 1141 res = (*stm->recorderItf) 1142 ->SetCallbackEventsMask(stm->recorderItf, 1143 (SLuint32)SL_RECORDEVENT_HEADATMARKER); 1144 if (res != SL_RESULT_SUCCESS) { 1145 LOG("Failed to set headatmarker event mask. Error code: %u", res); 1146 return CUBEB_ERROR; 1147 } 1148 // get the simple android buffer queue interface 1149 res = (*stm->recorderObj) 1150 ->GetInterface(stm->recorderObj, 1151 stm->context->SL_IID_ANDROIDSIMPLEBUFFERQUEUE, 1152 &stm->recorderBufferQueueItf); 1153 if (res != SL_RESULT_SUCCESS) { 1154 LOG("Failed to get recorder (android) buffer queue interface. Error code: " 1155 "%u", 1156 res); 1157 return CUBEB_ERROR; 1158 } 1159 1160 // register callback on record (input) buffer queue 1161 slAndroidSimpleBufferQueueCallback rec_callback = recorder_callback; 1162 if (stm->output_enabled) { 1163 // Register full duplex callback instead. 1164 rec_callback = recorder_fullduplex_callback; 1165 } 1166 res = (*stm->recorderBufferQueueItf) 1167 ->RegisterCallback(stm->recorderBufferQueueItf, rec_callback, stm); 1168 if (res != SL_RESULT_SUCCESS) { 1169 LOG("Failed to register recorder buffer queue callback. Error code: %u", 1170 res); 1171 return CUBEB_ERROR; 1172 } 1173 1174 // Calculate length of input buffer according to requested latency 1175 uint32_t sample_size = 0; 1176 if (params->format == CUBEB_SAMPLE_FLOAT32BE || 1177 params->format == CUBEB_SAMPLE_FLOAT32NE) { 1178 sample_size = sizeof(float); 1179 } else { 1180 sample_size = sizeof(int16_t); 1181 } 1182 stm->input_frame_size = params->channels * sample_size; 1183 stm->input_buffer_length = (stm->input_frame_size * stm->buffer_size_frames); 1184 1185 // Calculate the capacity of input array 1186 stm->input_array_capacity = NBUFS; 1187 if (stm->output_enabled) { 1188 // Full duplex, update capacity to hold 1 sec of data 1189 stm->input_array_capacity = 1190 1 * stm->input_device_rate / stm->input_buffer_length; 1191 } 1192 // Allocate input array 1193 stm->input_buffer_array = 1194 (void **)calloc(1, sizeof(void *) * stm->input_array_capacity); 1195 // Buffering has not started yet. 1196 stm->input_buffer_index = -1; 1197 // Prepare input buffers 1198 for (uint32_t i = 0; i < stm->input_array_capacity; ++i) { 1199 stm->input_buffer_array[i] = calloc(1, stm->input_buffer_length); 1200 } 1201 1202 // On full duplex allocate input queue and silent buffer 1203 if (stm->output_enabled) { 1204 stm->input_queue = array_queue_create(stm->input_array_capacity); 1205 XASSERT(stm->input_queue); 1206 stm->input_silent_buffer = calloc(1, stm->input_buffer_length); 1207 XASSERT(stm->input_silent_buffer); 1208 } 1209 1210 // Enqueue buffer to start rolling once recorder started 1211 rv = opensl_enqueue_recorder(stm, nullptr); 1212 if (rv != CUBEB_OK) { 1213 return rv; 1214 } 1215 1216 LOG("Cubeb stream init recorder success"); 1217 1218 return CUBEB_OK; 1219 } 1220 1221 static int 1222 opensl_configure_playback(cubeb_stream * stm, cubeb_stream_params * params) 1223 { 1224 XASSERT(stm); 1225 XASSERT(params); 1226 1227 stm->user_output_rate = params->rate; 1228 stm->lastPosition = -1; 1229 stm->lastPositionTimeStamp = 0; 1230 stm->lastCompensativePosition = -1; 1231 1232 int rv = initialize_with_format( 1233 stm, params, 1234 [=](void * format, uint32_t * format_sample_rate, bool using_floats) { 1235 SLDataLocator_BufferQueue loc_bufq; 1236 loc_bufq.locatorType = SL_DATALOCATOR_BUFFERQUEUE; 1237 loc_bufq.numBuffers = NBUFS; 1238 SLDataSource source; 1239 source.pLocator = &loc_bufq; 1240 source.pFormat = format; 1241 SLDataLocator_OutputMix loc_outmix; 1242 loc_outmix.locatorType = SL_DATALOCATOR_OUTPUTMIX; 1243 loc_outmix.outputMix = stm->context->outmixObj; 1244 1245 SLDataSink sink; 1246 sink.pLocator = &loc_outmix; 1247 sink.pFormat = nullptr; 1248 1249 #if defined(__ANDROID__) 1250 const SLInterfaceID ids[] = {stm->context->SL_IID_BUFFERQUEUE, 1251 stm->context->SL_IID_VOLUME, 1252 stm->context->SL_IID_ANDROIDCONFIGURATION}; 1253 const SLboolean req[] = {SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE, 1254 SL_BOOLEAN_TRUE}; 1255 #else 1256 const SLInterfaceID ids[] = {ctx->SL_IID_BUFFERQUEUE, 1257 ctx->SL_IID_VOLUME}; 1258 const SLboolean req[] = {SL_BOOLEAN_TRUE, SL_BOOLEAN_TRUE}; 1259 #endif 1260 XASSERT(NELEMS(ids) == NELEMS(req)); 1261 1262 uint32_t preferred_sampling_rate = stm->user_output_rate; 1263 SLresult res = SL_RESULT_CONTENT_UNSUPPORTED; 1264 if (preferred_sampling_rate) { 1265 res = (*stm->context->eng) 1266 ->CreateAudioPlayer(stm->context->eng, &stm->playerObj, 1267 &source, &sink, NELEMS(ids), ids, req); 1268 } 1269 1270 // Sample rate not supported? Try again with primary sample rate! 1271 if (res == SL_RESULT_CONTENT_UNSUPPORTED && 1272 preferred_sampling_rate != DEFAULT_SAMPLE_RATE) { 1273 preferred_sampling_rate = DEFAULT_SAMPLE_RATE; 1274 *format_sample_rate = preferred_sampling_rate * 1000; 1275 res = (*stm->context->eng) 1276 ->CreateAudioPlayer(stm->context->eng, &stm->playerObj, 1277 &source, &sink, NELEMS(ids), ids, req); 1278 } 1279 1280 if (res != SL_RESULT_SUCCESS) { 1281 LOG("Failed to create audio player. Error code: %u", res); 1282 return CUBEB_ERROR; 1283 } 1284 stm->output_configured_rate = preferred_sampling_rate; 1285 1286 // It's always possible to use int16 regardless of the Android version. 1287 // However if compiling for older Android version, it's possible to 1288 // request f32 audio, but Android only supports int16, in which case a 1289 // conversion need to happen. 1290 if ((params->format == CUBEB_SAMPLE_FLOAT32NE || 1291 params->format == CUBEB_SAMPLE_FLOAT32BE) && 1292 !using_floats) { 1293 // setup conversion from f32 to int16 1294 LOG("Input stream configured for using float, but not supported: a " 1295 "conversion will be performed"); 1296 stm->conversion_buffer_output.resize(1); 1297 } 1298 1299 if (!using_floats) { 1300 stm->framesize = params->channels * sizeof(int16_t); 1301 } else { 1302 stm->framesize = params->channels * sizeof(float); 1303 } 1304 return CUBEB_OK; 1305 }); 1306 1307 if (rv != CUBEB_OK) { 1308 LOG("Couldn't set format on sink or source"); 1309 return rv; 1310 } 1311 1312 stm->bytespersec = stm->output_configured_rate * stm->framesize; 1313 stm->queuebuf_len = stm->framesize * stm->buffer_size_frames; 1314 1315 // Calculate the capacity of input array 1316 stm->queuebuf_capacity = NBUFS; 1317 // Allocate input arrays 1318 stm->queuebuf = (void **)calloc(1, sizeof(void *) * stm->queuebuf_capacity); 1319 for (uint32_t i = 0; i < stm->queuebuf_capacity; ++i) { 1320 stm->queuebuf[i] = calloc(1, stm->queuebuf_len); 1321 XASSERT(stm->queuebuf[i]); 1322 } 1323 1324 SLAndroidConfigurationItf playerConfig = nullptr; 1325 1326 SLresult res; 1327 if (get_android_version() >= ANDROID_VERSION_N_MR1) { 1328 res = (*stm->playerObj) 1329 ->GetInterface(stm->playerObj, 1330 stm->context->SL_IID_ANDROIDCONFIGURATION, 1331 &playerConfig); 1332 if (res != SL_RESULT_SUCCESS) { 1333 LOG("Failed to get Android configuration interface. Error code: %u", res); 1334 return CUBEB_ERROR; 1335 } 1336 1337 SLint32 streamType = SL_ANDROID_STREAM_MEDIA; 1338 if (stm->voice_output) { 1339 streamType = SL_ANDROID_STREAM_VOICE; 1340 } 1341 res = (*playerConfig) 1342 ->SetConfiguration(playerConfig, SL_ANDROID_KEY_STREAM_TYPE, 1343 &streamType, sizeof(streamType)); 1344 if (res != SL_RESULT_SUCCESS) { 1345 LOG("Failed to set Android configuration to %d Error code: %u", 1346 streamType, res); 1347 } 1348 1349 SLuint32 performanceMode = SL_ANDROID_PERFORMANCE_LATENCY; 1350 if (stm->buffer_size_frames > POWERSAVE_LATENCY_FRAMES_THRESHOLD) { 1351 LOG("Audio stream configured for power saving"); 1352 performanceMode = SL_ANDROID_PERFORMANCE_POWER_SAVING; 1353 } 1354 1355 res = (*playerConfig) 1356 ->SetConfiguration(playerConfig, SL_ANDROID_KEY_PERFORMANCE_MODE, 1357 &performanceMode, sizeof(performanceMode)); 1358 if (res != SL_RESULT_SUCCESS) { 1359 LOG("Failed to set Android performance mode to %d Error code: %u. This " 1360 "is not fatal.", 1361 performanceMode, res); 1362 } 1363 } 1364 1365 res = (*stm->playerObj)->Realize(stm->playerObj, SL_BOOLEAN_FALSE); 1366 if (res != SL_RESULT_SUCCESS) { 1367 LOG("Failed to realize player object. Error code: %u", res); 1368 return CUBEB_ERROR; 1369 } 1370 1371 // There are two ways of getting the audio output latency: 1372 // - a configuration value, only available on some devices (notably devices 1373 // running FireOS) 1374 // - A Java method, that we call using JNI. 1375 // 1376 // The first method is prefered, if available, because it can account for more 1377 // latency causes, and is more precise. 1378 1379 // Latency has to be queried after the realization of the interface, when 1380 // using SL_IID_ANDROIDCONFIGURATION. 1381 SLuint32 audioLatency = 0; 1382 SLuint32 paramSize = sizeof(SLuint32); 1383 // The reported latency is in milliseconds. 1384 if (playerConfig) { 1385 res = (*playerConfig) 1386 ->GetConfiguration(playerConfig, 1387 (const SLchar *)"androidGetAudioLatency", 1388 ¶mSize, &audioLatency); 1389 if (res == SL_RESULT_SUCCESS) { 1390 LOG("Got playback latency using android configuration extension"); 1391 stm->output_latency_ms = audioLatency; 1392 } 1393 } 1394 // `playerConfig` is available, but the above failed, or `playerConfig` is not 1395 // available. In both cases, we need to acquire the output latency by an other 1396 // mean. 1397 if ((playerConfig && res != SL_RESULT_SUCCESS) || !playerConfig) { 1398 if (cubeb_output_latency_method_is_loaded( 1399 stm->context->p_output_latency_function)) { 1400 LOG("Got playback latency using JNI"); 1401 stm->output_latency_ms = 1402 cubeb_get_output_latency(stm->context->p_output_latency_function); 1403 } else { 1404 LOG("No alternate latency querying method loaded, A/V sync will be off."); 1405 stm->output_latency_ms = 0; 1406 } 1407 } 1408 1409 LOG("Audio output latency: %dms", stm->output_latency_ms); 1410 1411 res = 1412 (*stm->playerObj) 1413 ->GetInterface(stm->playerObj, stm->context->SL_IID_PLAY, &stm->play); 1414 if (res != SL_RESULT_SUCCESS) { 1415 LOG("Failed to get play interface. Error code: %u", res); 1416 return CUBEB_ERROR; 1417 } 1418 1419 res = (*stm->playerObj) 1420 ->GetInterface(stm->playerObj, stm->context->SL_IID_BUFFERQUEUE, 1421 &stm->bufq); 1422 if (res != SL_RESULT_SUCCESS) { 1423 LOG("Failed to get bufferqueue interface. Error code: %u", res); 1424 return CUBEB_ERROR; 1425 } 1426 1427 res = (*stm->playerObj) 1428 ->GetInterface(stm->playerObj, stm->context->SL_IID_VOLUME, 1429 &stm->volume); 1430 if (res != SL_RESULT_SUCCESS) { 1431 LOG("Failed to get volume interface. Error code: %u", res); 1432 return CUBEB_ERROR; 1433 } 1434 1435 res = (*stm->play)->RegisterCallback(stm->play, play_callback, stm); 1436 if (res != SL_RESULT_SUCCESS) { 1437 LOG("Failed to register play callback. Error code: %u", res); 1438 return CUBEB_ERROR; 1439 } 1440 1441 // Work around wilhelm/AudioTrack badness, bug 1221228 1442 (*stm->play)->SetMarkerPosition(stm->play, (SLmillisecond)0); 1443 1444 res = (*stm->play) 1445 ->SetCallbackEventsMask(stm->play, 1446 (SLuint32)SL_PLAYEVENT_HEADATMARKER); 1447 if (res != SL_RESULT_SUCCESS) { 1448 LOG("Failed to set headatmarker event mask. Error code: %u", res); 1449 return CUBEB_ERROR; 1450 } 1451 1452 slBufferQueueCallback player_callback = bufferqueue_callback; 1453 if (stm->input_enabled) { 1454 player_callback = player_fullduplex_callback; 1455 } 1456 res = (*stm->bufq)->RegisterCallback(stm->bufq, player_callback, stm); 1457 if (res != SL_RESULT_SUCCESS) { 1458 LOG("Failed to register bufferqueue callback. Error code: %u", res); 1459 return CUBEB_ERROR; 1460 } 1461 1462 { 1463 // Enqueue a silent frame so once the player becomes playing, the frame 1464 // will be consumed and kick off the buffer queue callback. 1465 // Note the duration of a single frame is less than 1ms. We don't bother 1466 // adjusting the playback position. 1467 uint8_t * buf = 1468 reinterpret_cast<uint8_t *>(stm->queuebuf[stm->queuebuf_idx++]); 1469 memset(buf, 0, stm->framesize); 1470 res = (*stm->bufq)->Enqueue(stm->bufq, buf, stm->framesize); 1471 XASSERT(res == SL_RESULT_SUCCESS); 1472 } 1473 1474 LOG("Cubeb stream init playback success"); 1475 return CUBEB_OK; 1476 } 1477 1478 static int 1479 opensl_validate_stream_param(cubeb_stream_params * stream_params) 1480 { 1481 if ((stream_params && 1482 (stream_params->channels < 1 || stream_params->channels > 32))) { 1483 return CUBEB_ERROR_INVALID_FORMAT; 1484 } 1485 if ((stream_params && (stream_params->prefs & CUBEB_STREAM_PREF_LOOPBACK))) { 1486 LOG("Loopback is not supported"); 1487 return CUBEB_ERROR_NOT_SUPPORTED; 1488 } 1489 return CUBEB_OK; 1490 } 1491 1492 int 1493 has_pref_set(cubeb_stream_params * input_params, 1494 cubeb_stream_params * output_params, cubeb_stream_prefs pref) 1495 { 1496 return (input_params && input_params->prefs & pref) || 1497 (output_params && output_params->prefs & pref); 1498 } 1499 1500 static int 1501 opensl_stream_init(cubeb * ctx, cubeb_stream ** stream, 1502 char const * stream_name, cubeb_devid input_device, 1503 cubeb_stream_params * input_stream_params, 1504 cubeb_devid output_device, 1505 cubeb_stream_params * output_stream_params, 1506 unsigned int latency_frames, 1507 cubeb_data_callback data_callback, 1508 cubeb_state_callback state_callback, void * user_ptr) 1509 { 1510 cubeb_stream * stm = nullptr; 1511 cubeb_async_log_reset_threads(); 1512 1513 XASSERT(ctx); 1514 if (input_device || output_device) { 1515 LOG("Device selection is not supported in Android. The default will be " 1516 "used"); 1517 } 1518 1519 *stream = nullptr; 1520 1521 int r = opensl_validate_stream_param(output_stream_params); 1522 if (r != CUBEB_OK) { 1523 LOG("Output stream params not valid"); 1524 return r; 1525 } 1526 r = opensl_validate_stream_param(input_stream_params); 1527 if (r != CUBEB_OK) { 1528 LOG("Input stream params not valid"); 1529 return r; 1530 } 1531 1532 stm = reinterpret_cast<cubeb_stream *>(calloc(1, sizeof(*stm))); 1533 XASSERT(stm); 1534 1535 if (input_stream_params) { 1536 stm->input_params = 1537 std::make_unique<cubeb_stream_params>(*input_stream_params); 1538 } 1539 if (output_stream_params) { 1540 stm->output_params = 1541 std::make_unique<cubeb_stream_params>(*output_stream_params); 1542 } 1543 1544 stm->context = ctx; 1545 stm->data_callback = data_callback; 1546 stm->state_callback = state_callback; 1547 stm->user_ptr = user_ptr; 1548 stm->buffer_size_frames = 1549 latency_frames ? latency_frames : DEFAULT_NUM_OF_FRAMES; 1550 stm->input_enabled = (input_stream_params) ? 1 : 0; 1551 stm->output_enabled = (output_stream_params) ? 1 : 0; 1552 stm->shutdown = 1; 1553 stm->voice_input = 1554 has_pref_set(input_stream_params, nullptr, CUBEB_STREAM_PREF_VOICE); 1555 stm->voice_output = 1556 has_pref_set(nullptr, output_stream_params, CUBEB_STREAM_PREF_VOICE); 1557 1558 LOG("cubeb stream prefs: voice_input: %s voice_output: %s", 1559 stm->voice_input ? "true" : "false", 1560 stm->voice_output ? "true" : "false"); 1561 1562 #ifdef DEBUG 1563 pthread_mutexattr_t attr; 1564 pthread_mutexattr_init(&attr); 1565 pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK); 1566 r = pthread_mutex_init(&stm->mutex, &attr); 1567 #else 1568 r = pthread_mutex_init(&stm->mutex, nullptr); 1569 #endif 1570 XASSERT(r == 0); 1571 1572 if (output_stream_params) { 1573 LOG("Playback params: Rate %d, channels %d, format %d, latency in frames " 1574 "%d.", 1575 output_stream_params->rate, output_stream_params->channels, 1576 output_stream_params->format, stm->buffer_size_frames); 1577 r = opensl_configure_playback(stm, output_stream_params); 1578 if (r != CUBEB_OK) { 1579 LOG("Error: playback-side configuration error, exiting."); 1580 opensl_stream_destroy(stm); 1581 return r; 1582 } 1583 } 1584 1585 if (input_stream_params) { 1586 LOG("Capture params: Rate %d, channels %d, format %d, latency in frames " 1587 "%d.", 1588 input_stream_params->rate, input_stream_params->channels, 1589 input_stream_params->format, stm->buffer_size_frames); 1590 r = opensl_configure_capture(stm, input_stream_params); 1591 if (r != CUBEB_OK) { 1592 LOG("Error: record-side configuration error, exiting."); 1593 opensl_stream_destroy(stm); 1594 return r; 1595 } 1596 } 1597 1598 /* Configure resampler*/ 1599 uint32_t target_sample_rate; 1600 if (input_stream_params) { 1601 target_sample_rate = input_stream_params->rate; 1602 } else { 1603 XASSERT(output_stream_params); 1604 target_sample_rate = output_stream_params->rate; 1605 } 1606 1607 // Use the actual configured rates for input 1608 // and output. 1609 cubeb_stream_params input_params; 1610 if (input_stream_params) { 1611 input_params = *input_stream_params; 1612 input_params.rate = stm->input_device_rate; 1613 } 1614 cubeb_stream_params output_params; 1615 if (output_stream_params) { 1616 output_params = *output_stream_params; 1617 output_params.rate = stm->output_configured_rate; 1618 } 1619 1620 stm->resampler = cubeb_resampler_create( 1621 stm, input_stream_params ? &input_params : nullptr, 1622 output_stream_params ? &output_params : nullptr, target_sample_rate, 1623 data_callback, user_ptr, CUBEB_RESAMPLER_QUALITY_DEFAULT, 1624 CUBEB_RESAMPLER_RECLOCK_NONE); 1625 if (!stm->resampler) { 1626 LOG("Failed to create resampler"); 1627 opensl_stream_destroy(stm); 1628 return CUBEB_ERROR; 1629 } 1630 1631 *stream = stm; 1632 LOG("Cubeb stream (%p) init success", stm); 1633 return CUBEB_OK; 1634 } 1635 1636 static int 1637 opensl_start_player(cubeb_stream * stm) 1638 { 1639 XASSERT(stm->playerObj); 1640 SLuint32 playerState; 1641 (*stm->playerObj)->GetState(stm->playerObj, &playerState); 1642 if (playerState == SL_OBJECT_STATE_REALIZED) { 1643 SLresult res = (*stm->play)->SetPlayState(stm->play, SL_PLAYSTATE_PLAYING); 1644 if (res != SL_RESULT_SUCCESS) { 1645 LOG("Failed to start player. Error code: %u", res); 1646 return CUBEB_ERROR; 1647 } 1648 } 1649 return CUBEB_OK; 1650 } 1651 1652 static int 1653 opensl_start_recorder(cubeb_stream * stm) 1654 { 1655 XASSERT(stm->recorderObj); 1656 SLuint32 recorderState; 1657 (*stm->recorderObj)->GetState(stm->recorderObj, &recorderState); 1658 if (recorderState == SL_OBJECT_STATE_REALIZED) { 1659 SLresult res = 1660 (*stm->recorderItf) 1661 ->SetRecordState(stm->recorderItf, SL_RECORDSTATE_RECORDING); 1662 if (res != SL_RESULT_SUCCESS) { 1663 LOG("Failed to start recorder. Error code: %u", res); 1664 return CUBEB_ERROR; 1665 } 1666 } 1667 return CUBEB_OK; 1668 } 1669 1670 static int 1671 opensl_stream_start(cubeb_stream * stm) 1672 { 1673 XASSERT(stm); 1674 1675 int r = pthread_mutex_lock(&stm->mutex); 1676 XASSERT(r == 0); 1677 opensl_set_shutdown(stm, 0); 1678 opensl_set_draining(stm, 0); 1679 r = pthread_mutex_unlock(&stm->mutex); 1680 XASSERT(r == 0); 1681 1682 if (stm->playerObj) { 1683 r = opensl_start_player(stm); 1684 if (r != CUBEB_OK) { 1685 return r; 1686 } 1687 } 1688 1689 if (stm->recorderObj) { 1690 int r = opensl_start_recorder(stm); 1691 if (r != CUBEB_OK) { 1692 return r; 1693 } 1694 } 1695 1696 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_STARTED); 1697 LOG("Cubeb stream (%p) started", stm); 1698 return CUBEB_OK; 1699 } 1700 1701 static int 1702 opensl_stop_player(cubeb_stream * stm) 1703 { 1704 XASSERT(stm->playerObj); 1705 XASSERT(stm->shutdown || stm->draining); 1706 1707 SLresult res = (*stm->play)->SetPlayState(stm->play, SL_PLAYSTATE_PAUSED); 1708 if (res != SL_RESULT_SUCCESS) { 1709 LOG("Failed to stop player. Error code: %u", res); 1710 return CUBEB_ERROR; 1711 } 1712 1713 return CUBEB_OK; 1714 } 1715 1716 static int 1717 opensl_stop_recorder(cubeb_stream * stm) 1718 { 1719 XASSERT(stm->recorderObj); 1720 XASSERT(stm->shutdown || stm->draining); 1721 1722 SLresult res = (*stm->recorderItf) 1723 ->SetRecordState(stm->recorderItf, SL_RECORDSTATE_PAUSED); 1724 if (res != SL_RESULT_SUCCESS) { 1725 LOG("Failed to stop recorder. Error code: %u", res); 1726 return CUBEB_ERROR; 1727 } 1728 1729 return CUBEB_OK; 1730 } 1731 1732 static int 1733 opensl_stream_stop(cubeb_stream * stm) 1734 { 1735 XASSERT(stm); 1736 1737 int r = pthread_mutex_lock(&stm->mutex); 1738 XASSERT(r == 0); 1739 opensl_set_shutdown(stm, 1); 1740 r = pthread_mutex_unlock(&stm->mutex); 1741 XASSERT(r == 0); 1742 1743 if (stm->playerObj) { 1744 r = opensl_stop_player(stm); 1745 if (r != CUBEB_OK) { 1746 return r; 1747 } 1748 } 1749 1750 if (stm->recorderObj) { 1751 int r = opensl_stop_recorder(stm); 1752 if (r != CUBEB_OK) { 1753 return r; 1754 } 1755 } 1756 1757 stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_STOPPED); 1758 LOG("Cubeb stream (%p) stopped", stm); 1759 return CUBEB_OK; 1760 } 1761 1762 static int 1763 opensl_destroy_recorder(cubeb_stream * stm) 1764 { 1765 XASSERT(stm); 1766 XASSERT(stm->recorderObj); 1767 1768 if (stm->recorderBufferQueueItf) { 1769 SLresult res = 1770 (*stm->recorderBufferQueueItf)->Clear(stm->recorderBufferQueueItf); 1771 if (res != SL_RESULT_SUCCESS) { 1772 LOG("Failed to clear recorder buffer queue. Error code: %u", res); 1773 return CUBEB_ERROR; 1774 } 1775 stm->recorderBufferQueueItf = nullptr; 1776 for (uint32_t i = 0; i < stm->input_array_capacity; ++i) { 1777 free(stm->input_buffer_array[i]); 1778 } 1779 } 1780 1781 (*stm->recorderObj)->Destroy(stm->recorderObj); 1782 stm->recorderObj = nullptr; 1783 stm->recorderItf = nullptr; 1784 1785 if (stm->input_queue) { 1786 array_queue_destroy(stm->input_queue); 1787 } 1788 free(stm->input_silent_buffer); 1789 1790 return CUBEB_OK; 1791 } 1792 1793 static void 1794 opensl_stream_destroy(cubeb_stream * stm) 1795 { 1796 XASSERT(stm->draining || stm->shutdown); 1797 1798 // If we're still draining at stream destroy time, pause the streams now so we 1799 // can destroy them safely. 1800 if (stm->draining) { 1801 opensl_stream_stop(stm); 1802 } 1803 // Sleep for 10ms to give active streams time to pause so that no further 1804 // buffer callbacks occur. Inspired by the same workaround (sleepBeforeClose) 1805 // in liboboe. 1806 usleep(10 * 1000); 1807 1808 if (stm->playerObj) { 1809 (*stm->playerObj)->Destroy(stm->playerObj); 1810 stm->playerObj = nullptr; 1811 stm->play = nullptr; 1812 stm->bufq = nullptr; 1813 for (uint32_t i = 0; i < stm->queuebuf_capacity; ++i) { 1814 free(stm->queuebuf[i]); 1815 } 1816 } 1817 1818 if (stm->recorderObj) { 1819 int r = opensl_destroy_recorder(stm); 1820 XASSERT(r == CUBEB_OK); 1821 } 1822 1823 if (stm->resampler) { 1824 cubeb_resampler_destroy(stm->resampler); 1825 } 1826 1827 pthread_mutex_destroy(&stm->mutex); 1828 1829 LOG("Cubeb stream (%p) destroyed", stm); 1830 free(stm); 1831 } 1832 1833 static int 1834 opensl_stream_get_position(cubeb_stream * stm, uint64_t * position) 1835 { 1836 SLmillisecond msec; 1837 uint32_t compensation_msec = 0; 1838 SLresult res; 1839 1840 res = (*stm->play)->GetPosition(stm->play, &msec); 1841 if (res != SL_RESULT_SUCCESS) { 1842 return CUBEB_ERROR; 1843 } 1844 1845 timespec t{}; 1846 clock_gettime(CLOCK_MONOTONIC, &t); 1847 if (stm->lastPosition == msec) { 1848 compensation_msec = 1849 (t.tv_sec * 1000000000LL + t.tv_nsec - stm->lastPositionTimeStamp) / 1850 1000000; 1851 } else { 1852 stm->lastPositionTimeStamp = t.tv_sec * 1000000000LL + t.tv_nsec; 1853 stm->lastPosition = msec; 1854 } 1855 1856 uint64_t samplerate = stm->user_output_rate; 1857 uint32_t output_latency = stm->output_latency_ms; 1858 1859 XASSERT(stm->written >= 0); 1860 XASSERT(stm->user_output_rate > 0); 1861 XASSERT(stm->output_configured_rate > 0); 1862 pthread_mutex_lock(&stm->mutex); 1863 int64_t maximum_position = stm->written * (int64_t)stm->user_output_rate / 1864 stm->output_configured_rate; 1865 pthread_mutex_unlock(&stm->mutex); 1866 XASSERT(maximum_position >= 0); 1867 1868 if (msec > output_latency) { 1869 int64_t unadjusted_position; 1870 if (stm->lastCompensativePosition > msec + compensation_msec) { 1871 // Over compensation, use lastCompensativePosition. 1872 unadjusted_position = 1873 samplerate * (stm->lastCompensativePosition - output_latency) / 1000; 1874 } else { 1875 unadjusted_position = 1876 samplerate * (msec - output_latency + compensation_msec) / 1000; 1877 stm->lastCompensativePosition = msec + compensation_msec; 1878 } 1879 *position = unadjusted_position < maximum_position ? unadjusted_position 1880 : maximum_position; 1881 } else { 1882 *position = 0; 1883 } 1884 return CUBEB_OK; 1885 } 1886 1887 static int 1888 opensl_stream_get_latency(cubeb_stream * stm, uint32_t * latency) 1889 { 1890 XASSERT(stm); 1891 XASSERT(latency); 1892 1893 uint32_t stream_latency_frames = 1894 stm->user_output_rate * stm->output_latency_ms / 1000; 1895 1896 *latency = static_cast<int>(stream_latency_frames + 1897 cubeb_resampler_latency(stm->resampler)); 1898 1899 return CUBEB_OK; 1900 } 1901 1902 int 1903 opensl_stream_set_volume(cubeb_stream * stm, float volume) 1904 { 1905 SLresult res; 1906 SLmillibel max_level, millibels; 1907 float unclamped_millibels; 1908 1909 res = (*stm->volume)->GetMaxVolumeLevel(stm->volume, &max_level); 1910 1911 if (res != SL_RESULT_SUCCESS) { 1912 return CUBEB_ERROR; 1913 } 1914 1915 /* millibels are 100*dB, so the conversion from the volume's linear amplitude 1916 * is 100 * 20 * log(volume). However we clamp the resulting value before 1917 * passing it to lroundf() in order to prevent it from silently returning an 1918 * erroneous value when the unclamped value exceeds the size of a long. */ 1919 unclamped_millibels = 100.0f * 20.0f * log10f(fmaxf(volume, 0.0f)); 1920 unclamped_millibels = fmaxf(unclamped_millibels, SL_MILLIBEL_MIN); 1921 unclamped_millibels = fminf(unclamped_millibels, max_level); 1922 1923 millibels = static_cast<SLmillibel>(lroundf(unclamped_millibels)); 1924 1925 res = (*stm->volume)->SetVolumeLevel(stm->volume, millibels); 1926 1927 if (res != SL_RESULT_SUCCESS) { 1928 return CUBEB_ERROR; 1929 } 1930 return CUBEB_OK; 1931 } 1932 1933 struct cubeb_ops const opensl_ops = { 1934 .init = opensl_init, 1935 .get_backend_id = opensl_get_backend_id, 1936 .get_max_channel_count = opensl_get_max_channel_count, 1937 .get_min_latency = nullptr, 1938 .get_preferred_sample_rate = nullptr, 1939 .get_supported_input_processing_params = nullptr, 1940 .enumerate_devices = nullptr, 1941 .device_collection_destroy = nullptr, 1942 .destroy = opensl_destroy, 1943 .stream_init = opensl_stream_init, 1944 .stream_destroy = opensl_stream_destroy, 1945 .stream_start = opensl_stream_start, 1946 .stream_stop = opensl_stream_stop, 1947 .stream_get_position = opensl_stream_get_position, 1948 .stream_get_latency = opensl_stream_get_latency, 1949 .stream_get_input_latency = nullptr, 1950 .stream_set_volume = opensl_stream_set_volume, 1951 .stream_set_name = nullptr, 1952 .stream_get_current_device = nullptr, 1953 .stream_set_input_mute = nullptr, 1954 .stream_set_input_processing_params = nullptr, 1955 .stream_device_destroy = nullptr, 1956 .stream_register_device_changed_callback = nullptr, 1957 .register_device_collection_changed = nullptr};