1 /*
2 * Copyright (C) 2019 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 #include <aaudio/AAudio.h>
17 #include <aaudio/AAudioTesting.h>
18 #include <android/media/audio/common/AudioDevice.h>
19 #include <android/media/audio/common/AudioMMapPolicyInfo.h>
20 #include <android/media/audio/common/AudioMMapPolicyType.h>
21 #include <media/AidlConversionCppNdk.h>
22 #include <media/AudioSystem.h>
23 #include <system/audio-hal-enums.h>
24 #include <utility/AAudioUtilities.h>
25
26 #include "AudioGlobal.h"
27
28 /******************************************
29 * Static globals.
30 */
31 namespace aaudio {
32
33 using android::media::audio::common::AudioDevice;
34 using android::media::audio::common::AudioMMapPolicyInfo;
35 using android::media::audio::common::AudioMMapPolicyType;
36
37 static aaudio_policy_t g_MMapPolicy = AAUDIO_UNSPECIFIED;
38
AudioGlobal_getMMapPolicy()39 aaudio_policy_t AudioGlobal_getMMapPolicy() {
40 return g_MMapPolicy;
41 }
42
AudioGlobal_setMMapPolicy(aaudio_policy_t policy)43 aaudio_result_t AudioGlobal_setMMapPolicy(aaudio_policy_t policy) {
44 aaudio_result_t result = AAUDIO_OK;
45 switch(policy) {
46 case AAUDIO_UNSPECIFIED:
47 case AAUDIO_POLICY_NEVER:
48 case AAUDIO_POLICY_AUTO:
49 case AAUDIO_POLICY_ALWAYS:
50 g_MMapPolicy = policy;
51 break;
52 default:
53 result = AAUDIO_ERROR_ILLEGAL_ARGUMENT;
54 break;
55 }
56 return result;
57 }
58
59 #define AAUDIO_CASE_ENUM(name) case name: return #name
60
AudioGlobal_convertResultToText(aaudio_result_t returnCode)61 const char* AudioGlobal_convertResultToText(aaudio_result_t returnCode) {
62 switch (returnCode) {
63 AAUDIO_CASE_ENUM(AAUDIO_OK);
64 AAUDIO_CASE_ENUM(AAUDIO_ERROR_DISCONNECTED);
65 AAUDIO_CASE_ENUM(AAUDIO_ERROR_ILLEGAL_ARGUMENT);
66 // reserved
67 AAUDIO_CASE_ENUM(AAUDIO_ERROR_INTERNAL);
68 AAUDIO_CASE_ENUM(AAUDIO_ERROR_INVALID_STATE);
69 // reserved
70 // reserved
71 AAUDIO_CASE_ENUM(AAUDIO_ERROR_INVALID_HANDLE);
72 // reserved
73 AAUDIO_CASE_ENUM(AAUDIO_ERROR_UNIMPLEMENTED);
74 AAUDIO_CASE_ENUM(AAUDIO_ERROR_UNAVAILABLE);
75 AAUDIO_CASE_ENUM(AAUDIO_ERROR_NO_FREE_HANDLES);
76 AAUDIO_CASE_ENUM(AAUDIO_ERROR_NO_MEMORY);
77 AAUDIO_CASE_ENUM(AAUDIO_ERROR_NULL);
78 AAUDIO_CASE_ENUM(AAUDIO_ERROR_TIMEOUT);
79 AAUDIO_CASE_ENUM(AAUDIO_ERROR_WOULD_BLOCK);
80 AAUDIO_CASE_ENUM(AAUDIO_ERROR_INVALID_FORMAT);
81 AAUDIO_CASE_ENUM(AAUDIO_ERROR_OUT_OF_RANGE);
82 AAUDIO_CASE_ENUM(AAUDIO_ERROR_NO_SERVICE);
83 AAUDIO_CASE_ENUM(AAUDIO_ERROR_INVALID_RATE);
84 }
85 return "Unrecognized";
86 }
87
AudioGlobal_convertFormatToText(aaudio_format_t format)88 const char* AudioGlobal_convertFormatToText(aaudio_format_t format) {
89 switch (format) {
90 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_UNSPECIFIED);
91 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_INVALID);
92 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_PCM_I16);
93 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_PCM_FLOAT);
94 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_PCM_I24_PACKED);
95 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_PCM_I32);
96 AAUDIO_CASE_ENUM(AAUDIO_FORMAT_IEC61937);
97 }
98 return "Unrecognized";
99 }
100
AudioGlobal_convertDirectionToText(aaudio_direction_t direction)101 const char* AudioGlobal_convertDirectionToText(aaudio_direction_t direction) {
102 switch (direction) {
103 AAUDIO_CASE_ENUM(AAUDIO_DIRECTION_INPUT);
104 AAUDIO_CASE_ENUM(AAUDIO_DIRECTION_OUTPUT);
105 }
106 return "Unrecognized";
107 }
108
AudioGlobal_convertPerformanceModeToText(aaudio_performance_mode_t mode)109 const char* AudioGlobal_convertPerformanceModeToText(aaudio_performance_mode_t mode) {
110 switch (mode) {
111 AAUDIO_CASE_ENUM(AAUDIO_PERFORMANCE_MODE_POWER_SAVING);
112 AAUDIO_CASE_ENUM(AAUDIO_PERFORMANCE_MODE_NONE);
113 AAUDIO_CASE_ENUM(AAUDIO_PERFORMANCE_MODE_LOW_LATENCY);
114 }
115 return "Unrecognized";
116 }
117
AudioGlobal_convertSharingModeToText(aaudio_sharing_mode_t mode)118 const char* AudioGlobal_convertSharingModeToText(aaudio_sharing_mode_t mode) {
119 switch (mode) {
120 AAUDIO_CASE_ENUM(AAUDIO_SHARING_MODE_SHARED);
121 AAUDIO_CASE_ENUM(AAUDIO_SHARING_MODE_EXCLUSIVE);
122 }
123 return "Unrecognized";
124 }
125
AudioGlobal_convertStreamStateToText(aaudio_stream_state_t state)126 const char* AudioGlobal_convertStreamStateToText(aaudio_stream_state_t state) {
127 switch (state) {
128 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_UNINITIALIZED);
129 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_UNKNOWN);
130 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_OPEN);
131 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_STARTING);
132 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_STARTED);
133 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_PAUSING);
134 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_PAUSED);
135 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_FLUSHING);
136 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_FLUSHED);
137 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_STOPPING);
138 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_STOPPED);
139 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_CLOSING);
140 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_CLOSED);
141 AAUDIO_CASE_ENUM(AAUDIO_STREAM_STATE_DISCONNECTED);
142 }
143 return "Unrecognized";
144 }
145
146 namespace {
147
getPlatformMMapPolicy(AudioMMapPolicyType policyType,AAudio_DeviceType device,aaudio_direction_t direction)148 aaudio_policy_t getPlatformMMapPolicy(AudioMMapPolicyType policyType, AAudio_DeviceType device,
149 aaudio_direction_t direction) {
150 if (direction != AAUDIO_DIRECTION_INPUT && direction != AAUDIO_DIRECTION_OUTPUT) {
151 return AAUDIO_ERROR_ILLEGAL_ARGUMENT;
152 }
153 const audio_devices_t deviceType = AAudioConvert_aaudioToAndroidDeviceType(device, direction);
154 if (deviceType == AUDIO_DEVICE_NONE) {
155 return AAUDIO_ERROR_ILLEGAL_ARGUMENT;
156 }
157
158 AudioMMapPolicyInfo policyInfo;
159 if (android::status_t status = android::AudioSystem::getMmapPolicyForDevice(
160 policyType, deviceType, &policyInfo);
161 status != android::NO_ERROR) {
162 return AAudioConvert_androidToAAudioResult(status);
163 }
164 return AAudioConvert_androidToAAudioMMapPolicy(policyInfo.mmapPolicy);
165 }
166
167 } // namespace
168
AudioGlobal_getPlatformMMapPolicy(AAudio_DeviceType device,aaudio_direction_t direction)169 aaudio_policy_t AudioGlobal_getPlatformMMapPolicy(
170 AAudio_DeviceType device, aaudio_direction_t direction) {
171 return getPlatformMMapPolicy(AudioMMapPolicyType::DEFAULT, device, direction);
172 }
173
AudioGlobal_getPlatformMMapExclusivePolicy(AAudio_DeviceType device,aaudio_direction_t direction)174 aaudio_policy_t AudioGlobal_getPlatformMMapExclusivePolicy(
175 AAudio_DeviceType device, aaudio_direction_t direction) {
176 return getPlatformMMapPolicy(AudioMMapPolicyType::EXCLUSIVE, device, direction);
177 }
178
179 #undef AAUDIO_CASE_ENUM
180
181 } // namespace aaudio
182