1 /* 2 * Copyright (C) 2016 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef OBOE_DEFINITIONS_H 18 #define OBOE_DEFINITIONS_H 19 20 #include <cstdint> 21 #include <type_traits> 22 23 // Oboe needs to be able to build on old NDKs so we use hard coded constants. 24 // The correctness of these constants is verified in "aaudio/AAudioLoader.cpp". 25 26 namespace oboe { 27 28 /** 29 * Represents any attribute, property or value which hasn't been specified. 30 */ 31 constexpr int32_t kUnspecified = 0; 32 33 // TODO: Investigate using std::chrono 34 /** 35 * The number of nanoseconds in a microsecond. 1,000. 36 */ 37 constexpr int64_t kNanosPerMicrosecond = 1000; 38 39 /** 40 * The number of nanoseconds in a millisecond. 1,000,000. 41 */ 42 constexpr int64_t kNanosPerMillisecond = kNanosPerMicrosecond * 1000; 43 44 /** 45 * The number of milliseconds in a second. 1,000. 46 */ 47 constexpr int64_t kMillisPerSecond = 1000; 48 49 /** 50 * The number of nanoseconds in a second. 1,000,000,000. 51 */ 52 constexpr int64_t kNanosPerSecond = kNanosPerMillisecond * kMillisPerSecond; 53 54 /** 55 * The state of the audio stream. 56 */ 57 enum class StreamState : int32_t { // aaudio_stream_state_t 58 Uninitialized = 0, // AAUDIO_STREAM_STATE_UNINITIALIZED, 59 Unknown = 1, // AAUDIO_STREAM_STATE_UNKNOWN, 60 Open = 2, // AAUDIO_STREAM_STATE_OPEN, 61 Starting = 3, // AAUDIO_STREAM_STATE_STARTING, 62 Started = 4, // AAUDIO_STREAM_STATE_STARTED, 63 Pausing = 5, // AAUDIO_STREAM_STATE_PAUSING, 64 Paused = 6, // AAUDIO_STREAM_STATE_PAUSED, 65 Flushing = 7, // AAUDIO_STREAM_STATE_FLUSHING, 66 Flushed = 8, // AAUDIO_STREAM_STATE_FLUSHED, 67 Stopping = 9, // AAUDIO_STREAM_STATE_STOPPING, 68 Stopped = 10, // AAUDIO_STREAM_STATE_STOPPED, 69 Closing = 11, // AAUDIO_STREAM_STATE_CLOSING, 70 Closed = 12, // AAUDIO_STREAM_STATE_CLOSED, 71 Disconnected = 13, // AAUDIO_STREAM_STATE_DISCONNECTED, 72 }; 73 74 /** 75 * The direction of the stream. 76 */ 77 enum class Direction : int32_t { // aaudio_direction_t 78 79 /** 80 * Used for playback. 81 */ 82 Output = 0, // AAUDIO_DIRECTION_OUTPUT, 83 84 /** 85 * Used for recording. 86 */ 87 Input = 1, // AAUDIO_DIRECTION_INPUT, 88 }; 89 90 /** 91 * The format of audio samples. 92 */ 93 enum class AudioFormat : int32_t { // aaudio_format_t 94 /** 95 * Invalid format. 96 */ 97 Invalid = -1, // AAUDIO_FORMAT_INVALID, 98 99 /** 100 * Unspecified format. Format will be decided by Oboe. 101 */ 102 Unspecified = 0, // AAUDIO_FORMAT_UNSPECIFIED, 103 104 /** 105 * Signed 16-bit integers. 106 */ 107 I16 = 1, // AAUDIO_FORMAT_PCM_I16, 108 109 /** 110 * Single precision floating point. 111 * 112 * This is the recommended format for most applications. 113 * But note that the use of Float may prevent the opening of 114 * a low-latency input path on OpenSL ES or Legacy AAudio streams. 115 */ 116 Float = 2, // AAUDIO_FORMAT_PCM_FLOAT, 117 118 /** 119 * Signed 24-bit integers, packed into 3 bytes. 120 * 121 * Note that the use of this format does not guarantee that 122 * the full precision will be provided. The underlying device may 123 * be using I16 format. 124 * 125 * Added in API 31 (S). 126 */ 127 I24 = 3, // AAUDIO_FORMAT_PCM_I24_PACKED 128 129 /** 130 * Signed 32-bit integers. 131 * 132 * Note that the use of this format does not guarantee that 133 * the full precision will be provided. The underlying device may 134 * be using I16 format. 135 * 136 * Added in API 31 (S). 137 */ 138 I32 = 4, // AAUDIO_FORMAT_PCM_I32 139 140 }; 141 142 /** 143 * The result of an audio callback. 144 */ 145 enum class DataCallbackResult : int32_t { // aaudio_data_callback_result_t 146 // Indicates to the caller that the callbacks should continue. 147 Continue = 0, // AAUDIO_CALLBACK_RESULT_CONTINUE, 148 149 // Indicates to the caller that the callbacks should stop immediately. 150 Stop = 1, // AAUDIO_CALLBACK_RESULT_STOP, 151 }; 152 153 /** 154 * The result of an operation. All except the `OK` result indicates that an error occurred. 155 * The `Result` can be converted into a human readable string using `convertToText`. 156 */ 157 enum class Result : int32_t { // aaudio_result_t 158 OK = 0, // AAUDIO_OK 159 ErrorBase = -900, // AAUDIO_ERROR_BASE, 160 ErrorDisconnected = -899, // AAUDIO_ERROR_DISCONNECTED, 161 ErrorIllegalArgument = -898, // AAUDIO_ERROR_ILLEGAL_ARGUMENT, 162 ErrorInternal = -896, // AAUDIO_ERROR_INTERNAL, 163 ErrorInvalidState = -895, // AAUDIO_ERROR_INVALID_STATE, 164 ErrorInvalidHandle = -892, // AAUDIO_ERROR_INVALID_HANDLE, 165 ErrorUnimplemented = -890, // AAUDIO_ERROR_UNIMPLEMENTED, 166 ErrorUnavailable = -889, // AAUDIO_ERROR_UNAVAILABLE, 167 ErrorNoFreeHandles = -888, // AAUDIO_ERROR_NO_FREE_HANDLES, 168 ErrorNoMemory = -887, // AAUDIO_ERROR_NO_MEMORY, 169 ErrorNull = -886, // AAUDIO_ERROR_NULL, 170 ErrorTimeout = -885, // AAUDIO_ERROR_TIMEOUT, 171 ErrorWouldBlock = -884, // AAUDIO_ERROR_WOULD_BLOCK, 172 ErrorInvalidFormat = -883, // AAUDIO_ERROR_INVALID_FORMAT, 173 ErrorOutOfRange = -882, // AAUDIO_ERROR_OUT_OF_RANGE, 174 ErrorNoService = -881, // AAUDIO_ERROR_NO_SERVICE, 175 ErrorInvalidRate = -880, // AAUDIO_ERROR_INVALID_RATE, 176 // Reserved for future AAudio result types 177 Reserved1, 178 Reserved2, 179 Reserved3, 180 Reserved4, 181 Reserved5, 182 Reserved6, 183 Reserved7, 184 Reserved8, 185 Reserved9, 186 Reserved10, 187 ErrorClosed = -869, 188 }; 189 190 /** 191 * The sharing mode of the audio stream. 192 */ 193 enum class SharingMode : int32_t { // aaudio_sharing_mode_t 194 195 /** 196 * This will be the only stream using a particular source or sink. 197 * This mode will provide the lowest possible latency. 198 * You should close EXCLUSIVE streams immediately when you are not using them. 199 * 200 * If you do not need the lowest possible latency then we recommend using Shared, 201 * which is the default. 202 */ 203 Exclusive = 0, // AAUDIO_SHARING_MODE_EXCLUSIVE, 204 205 /** 206 * Multiple applications can share the same device. 207 * The data from output streams will be mixed by the audio service. 208 * The data for input streams will be distributed by the audio service. 209 * 210 * This will have higher latency than the EXCLUSIVE mode. 211 */ 212 Shared = 1, // AAUDIO_SHARING_MODE_SHARED, 213 }; 214 215 /** 216 * The performance mode of the audio stream. 217 */ 218 enum class PerformanceMode : int32_t { // aaudio_performance_mode_t 219 220 /** 221 * No particular performance needs. Default. 222 */ 223 None = 10, // AAUDIO_PERFORMANCE_MODE_NONE, 224 225 /** 226 * Extending battery life is most important. 227 */ 228 PowerSaving = 11, // AAUDIO_PERFORMANCE_MODE_POWER_SAVING, 229 230 /** 231 * Reducing latency is most important. 232 */ 233 LowLatency = 12, // AAUDIO_PERFORMANCE_MODE_LOW_LATENCY 234 }; 235 236 /** 237 * The underlying audio API used by the audio stream. 238 */ 239 enum class AudioApi : int32_t { 240 /** 241 * Try to use AAudio. If not available then use OpenSL ES. 242 */ 243 Unspecified = kUnspecified, 244 245 /** 246 * Use OpenSL ES. 247 * Note that OpenSL ES is deprecated in Android 13, API 30 and above. 248 */ 249 OpenSLES, 250 251 /** 252 * Try to use AAudio. Fail if unavailable. 253 * AAudio was first supported in Android 8, API 26 and above. 254 * It is only recommended for API 27 and above. 255 */ 256 AAudio 257 }; 258 259 /** 260 * Specifies the quality of the sample rate conversion performed by Oboe. 261 * Higher quality will require more CPU load. 262 * Higher quality conversion will probably be implemented using a sinc based resampler. 263 */ 264 enum class SampleRateConversionQuality : int32_t { 265 /** 266 * No conversion by Oboe. Underlying APIs may still do conversion. 267 */ 268 None, 269 /** 270 * Fastest conversion but may not sound great. 271 * This may be implemented using bilinear interpolation. 272 */ 273 Fastest, 274 /** 275 * Low quality conversion with 8 taps. 276 */ 277 Low, 278 /** 279 * Medium quality conversion with 16 taps. 280 */ 281 Medium, 282 /** 283 * High quality conversion with 32 taps. 284 */ 285 High, 286 /** 287 * Highest quality conversion, which may be expensive in terms of CPU. 288 */ 289 Best, 290 }; 291 292 /** 293 * The Usage attribute expresses *why* you are playing a sound, what is this sound used for. 294 * This information is used by certain platforms or routing policies 295 * to make more refined volume or routing decisions. 296 * 297 * Note that these match the equivalent values in AudioAttributes in the Android Java API. 298 * 299 * This attribute only has an effect on Android API 28+. 300 */ 301 enum class Usage : int32_t { // aaudio_usage_t 302 /** 303 * Use this for streaming media, music performance, video, podcasts, etcetera. 304 */ 305 Media = 1, // AAUDIO_USAGE_MEDIA 306 307 /** 308 * Use this for voice over IP, telephony, etcetera. 309 */ 310 VoiceCommunication = 2, // AAUDIO_USAGE_VOICE_COMMUNICATION 311 312 /** 313 * Use this for sounds associated with telephony such as busy tones, DTMF, etcetera. 314 */ 315 VoiceCommunicationSignalling = 3, // AAUDIO_USAGE_VOICE_COMMUNICATION_SIGNALLING 316 317 /** 318 * Use this to demand the users attention. 319 */ 320 Alarm = 4, // AAUDIO_USAGE_ALARM 321 322 /** 323 * Use this for notifying the user when a message has arrived or some 324 * other background event has occured. 325 */ 326 Notification = 5, // AAUDIO_USAGE_NOTIFICATION 327 328 /** 329 * Use this when the phone rings. 330 */ 331 NotificationRingtone = 6, // AAUDIO_USAGE_NOTIFICATION_RINGTONE 332 333 /** 334 * Use this to attract the users attention when, for example, the battery is low. 335 */ 336 NotificationEvent = 10, // AAUDIO_USAGE_NOTIFICATION_EVENT 337 338 /** 339 * Use this for screen readers, etcetera. 340 */ 341 AssistanceAccessibility = 11, // AAUDIO_USAGE_ASSISTANCE_ACCESSIBILITY 342 343 /** 344 * Use this for driving or navigation directions. 345 */ 346 AssistanceNavigationGuidance = 12, // AAUDIO_USAGE_ASSISTANCE_NAVIGATION_GUIDANCE 347 348 /** 349 * Use this for user interface sounds, beeps, etcetera. 350 */ 351 AssistanceSonification = 13, // AAUDIO_USAGE_ASSISTANCE_SONIFICATION 352 353 /** 354 * Use this for game audio and sound effects. 355 */ 356 Game = 14, // AAUDIO_USAGE_GAME 357 358 /** 359 * Use this for audio responses to user queries, audio instructions or help utterances. 360 */ 361 Assistant = 16, // AAUDIO_USAGE_ASSISTANT 362 }; 363 364 365 /** 366 * The ContentType attribute describes *what* you are playing. 367 * It expresses the general category of the content. This information is optional. 368 * But in case it is known (for instance {@link Movie} for a 369 * movie streaming service or {@link Speech} for 370 * an audio book application) this information might be used by the audio framework to 371 * enforce audio focus. 372 * 373 * Note that these match the equivalent values in AudioAttributes in the Android Java API. 374 * 375 * This attribute only has an effect on Android API 28+. 376 */ 377 enum ContentType : int32_t { // aaudio_content_type_t 378 379 /** 380 * Use this for spoken voice, audio books, etcetera. 381 */ 382 Speech = 1, // AAUDIO_CONTENT_TYPE_SPEECH 383 384 /** 385 * Use this for pre-recorded or live music. 386 */ 387 Music = 2, // AAUDIO_CONTENT_TYPE_MUSIC 388 389 /** 390 * Use this for a movie or video soundtrack. 391 */ 392 Movie = 3, // AAUDIO_CONTENT_TYPE_MOVIE 393 394 /** 395 * Use this for sound is designed to accompany a user action, 396 * such as a click or beep sound made when the user presses a button. 397 */ 398 Sonification = 4, // AAUDIO_CONTENT_TYPE_SONIFICATION 399 }; 400 401 /** 402 * Defines the audio source. 403 * An audio source defines both a default physical source of audio signal, and a recording 404 * configuration. 405 * 406 * Note that these match the equivalent values in MediaRecorder.AudioSource in the Android Java API. 407 * 408 * This attribute only has an effect on Android API 28+. 409 */ 410 enum InputPreset : int32_t { // aaudio_input_preset_t 411 /** 412 * Use this preset when other presets do not apply. 413 */ 414 Generic = 1, // AAUDIO_INPUT_PRESET_GENERIC 415 416 /** 417 * Use this preset when recording video. 418 */ 419 Camcorder = 5, // AAUDIO_INPUT_PRESET_CAMCORDER 420 421 /** 422 * Use this preset when doing speech recognition. 423 */ 424 VoiceRecognition = 6, // AAUDIO_INPUT_PRESET_VOICE_RECOGNITION 425 426 /** 427 * Use this preset when doing telephony or voice messaging. 428 */ 429 VoiceCommunication = 7, // AAUDIO_INPUT_PRESET_VOICE_COMMUNICATION 430 431 /** 432 * Use this preset to obtain an input with no effects. 433 * Note that this input will not have automatic gain control 434 * so the recorded volume may be very low. 435 */ 436 Unprocessed = 9, // AAUDIO_INPUT_PRESET_UNPROCESSED 437 438 /** 439 * Use this preset for capturing audio meant to be processed in real time 440 * and played back for live performance (e.g karaoke). 441 * The capture path will minimize latency and coupling with playback path. 442 */ 443 VoicePerformance = 10, // AAUDIO_INPUT_PRESET_VOICE_PERFORMANCE 444 445 }; 446 447 /** 448 * This attribute can be used to allocate a session ID to the audio stream. 449 * 450 * This attribute only has an effect on Android API 28+. 451 */ 452 enum SessionId { 453 /** 454 * Do not allocate a session ID. 455 * Effects cannot be used with this stream. 456 * Default. 457 */ 458 None = -1, // AAUDIO_SESSION_ID_NONE 459 460 /** 461 * Allocate a session ID that can be used to attach and control 462 * effects using the Java AudioEffects API. 463 * Note that the use of this flag may result in higher latency. 464 * 465 * Note that this matches the value of AudioManager.AUDIO_SESSION_ID_GENERATE. 466 */ 467 Allocate = 0, // AAUDIO_SESSION_ID_ALLOCATE 468 }; 469 470 /** 471 * The channel count of the audio stream. The underlying type is `int32_t`. 472 * Use of this enum is convenient to avoid "magic" 473 * numbers when specifying the channel count. 474 * 475 * For example, you can write 476 * `builder.setChannelCount(ChannelCount::Stereo)` 477 * rather than `builder.setChannelCount(2)` 478 * 479 */ 480 enum ChannelCount : int32_t { 481 /** 482 * Audio channel count definition, use Mono or Stereo 483 */ 484 Unspecified = kUnspecified, 485 486 /** 487 * Use this for mono audio 488 */ 489 Mono = 1, 490 491 /** 492 * Use this for stereo audio. 493 */ 494 Stereo = 2, 495 }; 496 497 /** 498 * The channel mask of the audio stream. The underlying type is `uint32_t`. 499 * Use of this enum is convenient. 500 * 501 * ChannelMask::Unspecified means this is not specified. 502 * The rest of the enums are channel position masks. 503 * Use the combinations of the channel position masks defined below instead of 504 * using those values directly. 505 */ 506 enum class ChannelMask : uint32_t { // aaudio_channel_mask_t 507 Unspecified = kUnspecified, 508 FrontLeft = 1 << 0, 509 FrontRight = 1 << 1, 510 FrontCenter = 1 << 2, 511 LowFrequency = 1 << 3, 512 BackLeft = 1 << 4, 513 BackRight = 1 << 5, 514 FrontLeftOfCenter = 1 << 6, 515 FrontRightOfCenter = 1 << 7, 516 BackCenter = 1 << 8, 517 SideLeft = 1 << 9, 518 SideRight = 1 << 10, 519 TopCenter = 1 << 11, 520 TopFrontLeft = 1 << 12, 521 TopFrontCenter = 1 << 13, 522 TopFrontRight = 1 << 14, 523 TopBackLeft = 1 << 15, 524 TopBackCenter = 1 << 16, 525 TopBackRight = 1 << 17, 526 TopSideLeft = 1 << 18, 527 TopSideRight = 1 << 19, 528 BottomFrontLeft = 1 << 20, 529 BottomFrontCenter = 1 << 21, 530 BottomFrontRight = 1 << 22, 531 LowFrequency2 = 1 << 23, 532 FrontWideLeft = 1 << 24, 533 FrontWideRight = 1 << 25, 534 535 Mono = FrontLeft, 536 537 Stereo = FrontLeft | 538 FrontRight, 539 540 CM2Point1 = FrontLeft | 541 FrontRight | 542 LowFrequency, 543 544 Tri = FrontLeft | 545 FrontRight | 546 FrontCenter, 547 548 TriBack = FrontLeft | 549 FrontRight | 550 BackCenter, 551 552 CM3Point1 = FrontLeft | 553 FrontRight | 554 FrontCenter | 555 LowFrequency, 556 557 CM2Point0Point2 = FrontLeft | 558 FrontRight | 559 TopSideLeft | 560 TopSideRight, 561 562 CM2Point1Point2 = CM2Point0Point2 | 563 LowFrequency, 564 565 CM3Point0Point2 = FrontLeft | 566 FrontRight | 567 FrontCenter | 568 TopSideLeft | 569 TopSideRight, 570 571 CM3Point1Point2 = CM3Point0Point2 | 572 LowFrequency, 573 574 Quad = FrontLeft | 575 FrontRight | 576 BackLeft | 577 BackRight, 578 579 QuadSide = FrontLeft | 580 FrontRight | 581 SideLeft | 582 SideRight, 583 584 Surround = FrontLeft | 585 FrontRight | 586 FrontCenter | 587 BackCenter, 588 589 Penta = Quad | 590 FrontCenter, 591 592 // aka 5Point1Back 593 CM5Point1 = FrontLeft | 594 FrontRight | 595 FrontCenter | 596 LowFrequency | 597 BackLeft | 598 BackRight, 599 600 CM5Point1Side = FrontLeft | 601 FrontRight | 602 FrontCenter | 603 LowFrequency | 604 SideLeft | 605 SideRight, 606 607 CM6Point1 = FrontLeft | 608 FrontRight | 609 FrontCenter | 610 LowFrequency | 611 BackLeft | 612 BackRight | 613 BackCenter, 614 615 CM7Point1 = CM5Point1 | 616 SideLeft | 617 SideRight, 618 619 CM5Point1Point2 = CM5Point1 | 620 TopSideLeft | 621 TopSideRight, 622 623 CM5Point1Point4 = CM5Point1 | 624 TopFrontLeft | 625 TopFrontRight | 626 TopBackLeft | 627 TopBackRight, 628 629 CM7Point1Point2 = CM7Point1 | 630 TopSideLeft | 631 TopSideRight, 632 633 CM7Point1Point4 = CM7Point1 | 634 TopFrontLeft | 635 TopFrontRight | 636 TopBackLeft | 637 TopBackRight, 638 639 CM9Point1Point4 = CM7Point1Point4 | 640 FrontWideLeft | 641 FrontWideRight, 642 643 CM9Point1Point6 = CM9Point1Point4 | 644 TopSideLeft | 645 TopSideRight, 646 647 FrontBack = FrontCenter | 648 BackCenter, 649 }; 650 651 /** 652 * On API 16 to 26 OpenSL ES will be used. When using OpenSL ES the optimal values for sampleRate and 653 * framesPerBurst are not known by the native code. 654 * On API 17+ these values should be obtained from the AudioManager using this code: 655 * 656 * <pre><code> 657 * // Note that this technique only works for built-in speakers and headphones. 658 * AudioManager myAudioMgr = (AudioManager) getSystemService(Context.AUDIO_SERVICE); 659 * String sampleRateStr = myAudioMgr.getProperty(AudioManager.PROPERTY_OUTPUT_SAMPLE_RATE); 660 * int defaultSampleRate = Integer.parseInt(sampleRateStr); 661 * String framesPerBurstStr = myAudioMgr.getProperty(AudioManager.PROPERTY_OUTPUT_FRAMES_PER_BUFFER); 662 * int defaultFramesPerBurst = Integer.parseInt(framesPerBurstStr); 663 * </code></pre> 664 * 665 * It can then be passed down to Oboe through JNI. 666 * 667 * AAudio will get the optimal framesPerBurst from the HAL and will ignore this value. 668 */ 669 class DefaultStreamValues { 670 671 public: 672 673 /** The default sample rate to use when opening new audio streams */ 674 static int32_t SampleRate; 675 /** The default frames per burst to use when opening new audio streams */ 676 static int32_t FramesPerBurst; 677 /** The default channel count to use when opening new audio streams */ 678 static int32_t ChannelCount; 679 680 }; 681 682 /** 683 * The time at which the frame at `position` was presented 684 */ 685 struct FrameTimestamp { 686 int64_t position; // in frames 687 int64_t timestamp; // in nanoseconds 688 }; 689 690 class OboeGlobals { 691 public: 692 areWorkaroundsEnabled()693 static bool areWorkaroundsEnabled() { 694 return mWorkaroundsEnabled; 695 } 696 697 /** 698 * Disable this when writing tests to reproduce bugs in AAudio or OpenSL ES 699 * that have workarounds in Oboe. 700 * @param enabled 701 */ setWorkaroundsEnabled(bool enabled)702 static void setWorkaroundsEnabled(bool enabled) { 703 mWorkaroundsEnabled = enabled; 704 } 705 706 private: 707 static bool mWorkaroundsEnabled; 708 }; 709 } // namespace oboe 710 711 #endif // OBOE_DEFINITIONS_H 712