blob: 9b1da1306f141d7e52cf706ee08179611fad87b4 [file] [log] [blame]
Eric Laurentb7a11d82014-04-18 17:40:41 -07001/*
2**
3** Copyright 2014, The Android Open Source Project
4**
5** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
8**
9** http://www.apache.org/licenses/LICENSE-2.0
10**
11** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
15** limitations under the License.
16*/
17
18#define LOG_TAG "ISoundTrigger"
19#include <utils/Log.h>
20#include <utils/Errors.h>
21#include <binder/IMemory.h>
22#include <soundtrigger/ISoundTrigger.h>
23#include <soundtrigger/ISoundTriggerHwService.h>
24#include <soundtrigger/ISoundTriggerClient.h>
25#include <system/sound_trigger.h>
26
27namespace android {
28
29enum {
30 DETACH = IBinder::FIRST_CALL_TRANSACTION,
31 LOAD_SOUND_MODEL,
32 UNLOAD_SOUND_MODEL,
33 START_RECOGNITION,
34 STOP_RECOGNITION,
Michael Dooley67e3d412018-10-16 19:51:16 +000035 GET_MODEL_STATE,
Nicholas Ambur41947e22019-10-01 11:53:40 -070036 SET_PARAMETER,
37 GET_PARAMETER,
38 QUERY_PARAMETER,
Eric Laurentb7a11d82014-04-18 17:40:41 -070039};
40
41class BpSoundTrigger: public BpInterface<ISoundTrigger>
42{
43public:
Chih-Hung Hsieh090ef602016-04-27 10:39:54 -070044 explicit BpSoundTrigger(const sp<IBinder>& impl)
Eric Laurentb7a11d82014-04-18 17:40:41 -070045 : BpInterface<ISoundTrigger>(impl)
46 {
47 }
48
49 void detach()
50 {
51 ALOGV("detach");
52 Parcel data, reply;
53 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
54 remote()->transact(DETACH, data, &reply);
55 }
56
57 status_t loadSoundModel(const sp<IMemory>& modelMemory,
58 sound_model_handle_t *handle)
59 {
60 if (modelMemory == 0 || handle == NULL) {
61 return BAD_VALUE;
62 }
63 Parcel data, reply;
64 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
Marco Nelissen06b46062014-11-14 07:58:25 -080065 data.writeStrongBinder(IInterface::asBinder(modelMemory));
Eric Laurentb7a11d82014-04-18 17:40:41 -070066 status_t status = remote()->transact(LOAD_SOUND_MODEL, data, &reply);
Eric Laurent014620f2015-10-05 17:21:00 -070067 if (status != NO_ERROR) {
Eric Laurentb7a11d82014-04-18 17:40:41 -070068 return status;
69 }
Eric Laurent014620f2015-10-05 17:21:00 -070070 status = (status_t)reply.readInt32();
71 if (status == NO_ERROR) {
72 reply.read(handle, sizeof(sound_model_handle_t));
73 }
Eric Laurentb7a11d82014-04-18 17:40:41 -070074 return status;
75 }
76
77 virtual status_t unloadSoundModel(sound_model_handle_t handle)
78 {
79 Parcel data, reply;
80 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
81 data.write(&handle, sizeof(sound_model_handle_t));
82 status_t status = remote()->transact(UNLOAD_SOUND_MODEL, data, &reply);
Eric Laurent014620f2015-10-05 17:21:00 -070083 if (status == NO_ERROR) {
Eric Laurentb7a11d82014-04-18 17:40:41 -070084 status = (status_t)reply.readInt32();
85 }
86 return status;
87 }
88
89 virtual status_t startRecognition(sound_model_handle_t handle,
90 const sp<IMemory>& dataMemory)
91 {
92 Parcel data, reply;
93 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
94 data.write(&handle, sizeof(sound_model_handle_t));
95 if (dataMemory == 0) {
96 data.writeInt32(0);
97 } else {
98 data.writeInt32(dataMemory->size());
99 }
Marco Nelissen06b46062014-11-14 07:58:25 -0800100 data.writeStrongBinder(IInterface::asBinder(dataMemory));
Eric Laurentb7a11d82014-04-18 17:40:41 -0700101 status_t status = remote()->transact(START_RECOGNITION, data, &reply);
Eric Laurent014620f2015-10-05 17:21:00 -0700102 if (status == NO_ERROR) {
Eric Laurentb7a11d82014-04-18 17:40:41 -0700103 status = (status_t)reply.readInt32();
104 }
105 return status;
106 }
107
108 virtual status_t stopRecognition(sound_model_handle_t handle)
109 {
110 Parcel data, reply;
111 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
112 data.write(&handle, sizeof(sound_model_handle_t));
113 status_t status = remote()->transact(STOP_RECOGNITION, data, &reply);
Eric Laurent014620f2015-10-05 17:21:00 -0700114 if (status == NO_ERROR) {
Eric Laurentb7a11d82014-04-18 17:40:41 -0700115 status = (status_t)reply.readInt32();
116 }
117 return status;
118 }
119
mike dooley6e189b12018-11-07 15:44:37 +0100120 virtual status_t getModelState(sound_model_handle_t handle)
Michael Dooley67e3d412018-10-16 19:51:16 +0000121 {
122 Parcel data, reply;
123 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
124 data.write(&handle, sizeof(sound_model_handle_t));
125 status_t status = remote()->transact(GET_MODEL_STATE, data, &reply);
126 if (status == NO_ERROR) {
127 status = (status_t)reply.readInt32();
Michael Dooley67e3d412018-10-16 19:51:16 +0000128 }
129 return status;
130 }
131
Nicholas Ambur41947e22019-10-01 11:53:40 -0700132 virtual status_t setParameter(sound_model_handle_t handle,
133 sound_trigger_model_parameter_t param,
134 int32_t value)
135 {
136 Parcel data, reply;
137 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
138 data.write(&handle, sizeof(sound_model_handle_t));
139 data.write(&param, sizeof(sound_trigger_model_parameter_t));
140 data.writeInt32(value);
141 status_t status = remote()->transact(SET_PARAMETER, data, &reply);
142 if (status == NO_ERROR) {
143 status = (status_t)reply.readInt32();
144 }
145 return status;
146 }
147
148 virtual status_t getParameter(sound_model_handle_t handle,
149 sound_trigger_model_parameter_t param,
150 int32_t* value)
151 {
152 Parcel data, reply;
153 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
154 data.write(&handle, sizeof(sound_model_handle_t));
155 data.write(&param, sizeof(sound_trigger_model_parameter_t));
156 status_t status = remote()->transact(GET_PARAMETER, data, &reply);
157 if (status == NO_ERROR) {
158 status = (status_t)reply.readInt32();
159 *value = reply.readInt32();
160 }
161 return status;
162 }
163
164 virtual status_t queryParameter(sound_model_handle_t handle,
165 sound_trigger_model_parameter_t param,
166 sound_trigger_model_parameter_range_t* param_range)
167 {
168 Parcel data, reply;
169 data.writeInterfaceToken(ISoundTrigger::getInterfaceDescriptor());
170 data.write(&handle, sizeof(sound_model_handle_t));
171 data.write(&param, sizeof(sound_trigger_model_parameter_t));
172 status_t status = remote()->transact(QUERY_PARAMETER, data, &reply);
173 if (status == NO_ERROR) {
174 status = (status_t)reply.readInt32();
175 param_range->start = reply.readInt32();
176 param_range->end = reply.readInt32();
177 }
178 return status;
179 }
180
Eric Laurentb7a11d82014-04-18 17:40:41 -0700181};
182
183IMPLEMENT_META_INTERFACE(SoundTrigger, "android.hardware.ISoundTrigger");
184
185// ----------------------------------------------------------------------
186
187status_t BnSoundTrigger::onTransact(
188 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
189{
190 switch(code) {
191 case DETACH: {
192 ALOGV("DETACH");
193 CHECK_INTERFACE(ISoundTrigger, data, reply);
194 detach();
195 return NO_ERROR;
196 } break;
197 case LOAD_SOUND_MODEL: {
198 CHECK_INTERFACE(ISoundTrigger, data, reply);
199 sp<IMemory> modelMemory = interface_cast<IMemory>(
200 data.readStrongBinder());
201 sound_model_handle_t handle;
202 status_t status = loadSoundModel(modelMemory, &handle);
203 reply->writeInt32(status);
204 if (status == NO_ERROR) {
205 reply->write(&handle, sizeof(sound_model_handle_t));
206 }
207 return NO_ERROR;
208 }
209 case UNLOAD_SOUND_MODEL: {
210 CHECK_INTERFACE(ISoundTrigger, data, reply);
211 sound_model_handle_t handle;
212 data.read(&handle, sizeof(sound_model_handle_t));
213 status_t status = unloadSoundModel(handle);
214 reply->writeInt32(status);
215 return NO_ERROR;
216 }
217 case START_RECOGNITION: {
218 CHECK_INTERFACE(ISoundTrigger, data, reply);
219 sound_model_handle_t handle;
220 data.read(&handle, sizeof(sound_model_handle_t));
221 sp<IMemory> dataMemory;
222 if (data.readInt32() != 0) {
223 dataMemory = interface_cast<IMemory>(data.readStrongBinder());
224 }
225 status_t status = startRecognition(handle, dataMemory);
226 reply->writeInt32(status);
227 return NO_ERROR;
228 }
229 case STOP_RECOGNITION: {
230 CHECK_INTERFACE(ISoundTrigger, data, reply);
231 sound_model_handle_t handle;
232 data.read(&handle, sizeof(sound_model_handle_t));
233 status_t status = stopRecognition(handle);
234 reply->writeInt32(status);
235 return NO_ERROR;
236 }
Michael Dooley67e3d412018-10-16 19:51:16 +0000237 case GET_MODEL_STATE: {
238 CHECK_INTERFACE(ISoundTrigger, data, reply);
239 sound_model_handle_t handle;
240 status_t status = UNKNOWN_ERROR;
241 status_t ret = data.read(&handle, sizeof(sound_model_handle_t));
242 if (ret == NO_ERROR) {
mike dooley6e189b12018-11-07 15:44:37 +0100243 status = getModelState(handle);
Michael Dooley67e3d412018-10-16 19:51:16 +0000244 }
245 reply->writeInt32(status);
246 return ret;
247 }
Nicholas Ambur41947e22019-10-01 11:53:40 -0700248 case SET_PARAMETER: {
249 CHECK_INTERFACE(ISoundTrigger, data, reply);
250 sound_model_handle_t handle;
251 sound_trigger_model_parameter_t param;
252 int32_t value;
253 status_t status = UNKNOWN_ERROR;
254 status_t ret;
255 ret = data.read(&handle, sizeof(sound_model_handle_t));
256 if (ret != NO_ERROR) {
257 return ret;
258 }
259 ret = data.read(&param, sizeof(sound_trigger_model_parameter_t));
260 if (ret != NO_ERROR) {
261 return ret;
262 }
263 ret = data.read(&value, sizeof(int32_t));
264 if (ret != NO_ERROR) {
265 return ret;
266 }
267 status = setParameter(handle, param, value);
268 reply->writeInt32(status);
269 return NO_ERROR;
270 }
271 case GET_PARAMETER: {
272 CHECK_INTERFACE(ISoundTrigger, data, reply);
273 sound_model_handle_t handle;
274 sound_trigger_model_parameter_t param;
275 int32_t value;
276 status_t status = UNKNOWN_ERROR;
277 status_t ret;
278 ret = data.read(&handle, sizeof(sound_model_handle_t));
279 if (ret != NO_ERROR) {
280 return ret;
281 }
282 ret = data.read(&param, sizeof(sound_trigger_model_parameter_t));
283 if (ret != NO_ERROR) {
284 return ret;
285 }
286 status = getParameter(handle, param, &value);
287 reply->writeInt32(status);
288 reply->writeInt32(value);
289 return NO_ERROR;
290 }
291 case QUERY_PARAMETER: {
292 CHECK_INTERFACE(ISoundTrigger, data, reply);
293 sound_model_handle_t handle;
294 sound_trigger_model_parameter_t param;
295 status_t ret;
296 status_t status = UNKNOWN_ERROR;
297 sound_trigger_model_parameter_range_t retValue;
298 ret = data.read(&handle, sizeof(sound_model_handle_t));
299 if (ret != NO_ERROR) {
300 return ret;
301 }
302 ret = data.read(&param, sizeof(sound_trigger_model_parameter_t));
303 if (ret != NO_ERROR) {
304 return ret;
305 }
306 status = queryParameter(handle, param, &retValue);
307 reply->writeInt32(status);
308 reply->writeInt32(retValue.start);
309 reply->writeInt32(retValue.end);
310 return NO_ERROR;
311 }
Eric Laurentb7a11d82014-04-18 17:40:41 -0700312 default:
313 return BBinder::onTransact(code, data, reply, flags);
314 }
315}
316
317// ----------------------------------------------------------------------------
318
319}; // namespace android