blob: 8d8d0880b21c500ae6c88872f211978c2f1f256c [file] [log] [blame]
Andreas Hubered3e3e02012-03-26 11:13:27 -07001/*
2 * Copyright (C) 2012 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//#define LOG_NDEBUG 0
18#define LOG_TAG "ICrypto"
Andreas Hubered3e3e02012-03-26 11:13:27 -070019#include <binder/Parcel.h>
Jeff Tinkerc481b502015-04-06 18:21:05 -070020#include <binder/IMemory.h>
Jeff Tinker5231cc12018-01-11 00:14:53 -080021#include <cutils/log.h>
Andreas Huber5b8987e2012-04-19 12:52:20 -070022#include <media/stagefright/MediaErrors.h>
Andreas Hubered3e3e02012-03-26 11:13:27 -070023#include <media/stagefright/foundation/ADebug.h>
Andreas Huber5b8987e2012-04-19 12:52:20 -070024#include <media/stagefright/foundation/AString.h>
Jeff Tinker7d2c6e82018-02-16 16:14:59 -080025#include <mediadrm/ICrypto.h>
Jeff Tinker5231cc12018-01-11 00:14:53 -080026#include <utils/Log.h>
Andreas Hubered3e3e02012-03-26 11:13:27 -070027
28namespace android {
29
30enum {
Andreas Huber1bd139a2012-04-03 14:19:20 -070031 INIT_CHECK = IBinder::FIRST_CALL_TRANSACTION,
32 IS_CRYPTO_SUPPORTED,
33 CREATE_PLUGIN,
34 DESTROY_PLUGIN,
35 REQUIRES_SECURE_COMPONENT,
36 DECRYPT,
Jeff Tinker2514d082014-11-03 13:29:35 -080037 NOTIFY_RESOLUTION,
Jeff Tinker18495702015-04-10 04:10:59 -070038 SET_MEDIADRM_SESSION,
Chong Zhangd07c9272017-03-28 11:02:06 -070039 SET_HEAP,
40 UNSET_HEAP,
Andreas Hubered3e3e02012-03-26 11:13:27 -070041};
42
43struct BpCrypto : public BpInterface<ICrypto> {
Chih-Hung Hsieh090ef602016-04-27 10:39:54 -070044 explicit BpCrypto(const sp<IBinder> &impl)
Andreas Hubered3e3e02012-03-26 11:13:27 -070045 : BpInterface<ICrypto>(impl) {
46 }
47
Andreas Huber1bd139a2012-04-03 14:19:20 -070048 virtual status_t initCheck() const {
Andreas Hubered3e3e02012-03-26 11:13:27 -070049 Parcel data, reply;
50 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Andreas Huber1bd139a2012-04-03 14:19:20 -070051 remote()->transact(INIT_CHECK, data, &reply);
Andreas Hubered3e3e02012-03-26 11:13:27 -070052
53 return reply.readInt32();
54 }
55
Jeff Tinkerbafb6822013-03-22 15:26:39 -070056 virtual bool isCryptoSchemeSupported(const uint8_t uuid[16]) {
Andreas Hubered3e3e02012-03-26 11:13:27 -070057 Parcel data, reply;
58 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Andreas Huber1bd139a2012-04-03 14:19:20 -070059 data.write(uuid, 16);
60 remote()->transact(IS_CRYPTO_SUPPORTED, data, &reply);
61
62 return reply.readInt32() != 0;
63 }
64
65 virtual status_t createPlugin(
66 const uint8_t uuid[16], const void *opaqueData, size_t opaqueSize) {
67 Parcel data, reply;
68 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
69 data.write(uuid, 16);
70 data.writeInt32(opaqueSize);
Andreas Huber705868c2012-04-11 15:41:45 -070071
72 if (opaqueSize > 0) {
73 data.write(opaqueData, opaqueSize);
74 }
75
Andreas Huber1bd139a2012-04-03 14:19:20 -070076 remote()->transact(CREATE_PLUGIN, data, &reply);
Andreas Hubered3e3e02012-03-26 11:13:27 -070077
78 return reply.readInt32();
79 }
80
Andreas Huber1bd139a2012-04-03 14:19:20 -070081 virtual status_t destroyPlugin() {
Andreas Hubered3e3e02012-03-26 11:13:27 -070082 Parcel data, reply;
83 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Andreas Huber1bd139a2012-04-03 14:19:20 -070084 remote()->transact(DESTROY_PLUGIN, data, &reply);
Andreas Hubered3e3e02012-03-26 11:13:27 -070085
86 return reply.readInt32();
87 }
88
Andreas Huber1bd139a2012-04-03 14:19:20 -070089 virtual bool requiresSecureDecoderComponent(
90 const char *mime) const {
Andreas Hubered3e3e02012-03-26 11:13:27 -070091 Parcel data, reply;
92 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Andreas Huber1bd139a2012-04-03 14:19:20 -070093 data.writeCString(mime);
94 remote()->transact(REQUIRES_SECURE_COMPONENT, data, &reply);
Andreas Hubered3e3e02012-03-26 11:13:27 -070095
Andreas Huber1bd139a2012-04-03 14:19:20 -070096 return reply.readInt32() != 0;
Andreas Hubered3e3e02012-03-26 11:13:27 -070097 }
98
Jeff Tinkera53d6552017-01-20 00:31:46 -080099 virtual ssize_t decrypt(const uint8_t key[16], const uint8_t iv[16],
Jeff Tinker18cb1ec2015-12-18 11:55:22 -0800100 CryptoPlugin::Mode mode, const CryptoPlugin::Pattern &pattern,
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700101 const SourceBuffer &source, size_t offset,
Andreas Huber1bd139a2012-04-03 14:19:20 -0700102 const CryptoPlugin::SubSample *subSamples, size_t numSubSamples,
Jeff Tinkera53d6552017-01-20 00:31:46 -0800103 const DestinationBuffer &destination, AString *errorDetailMsg) {
Andreas Hubered3e3e02012-03-26 11:13:27 -0700104 Parcel data, reply;
105 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Andreas Huber1bd139a2012-04-03 14:19:20 -0700106 data.writeInt32(mode);
Jeff Tinker18cb1ec2015-12-18 11:55:22 -0800107 data.writeInt32(pattern.mEncryptBlocks);
108 data.writeInt32(pattern.mSkipBlocks);
Andreas Huber4b75a9c2012-04-06 11:06:28 -0700109
110 static const uint8_t kDummy[16] = { 0 };
111
112 if (key == NULL) {
113 key = kDummy;
114 }
115
116 if (iv == NULL) {
117 iv = kDummy;
118 }
119
Andreas Huber1bd139a2012-04-03 14:19:20 -0700120 data.write(key, 16);
121 data.write(iv, 16);
Andreas Hubered3e3e02012-03-26 11:13:27 -0700122
Andreas Huber1bd139a2012-04-03 14:19:20 -0700123 size_t totalSize = 0;
124 for (size_t i = 0; i < numSubSamples; ++i) {
125 totalSize += subSamples[i].mNumBytesOfEncryptedData;
126 totalSize += subSamples[i].mNumBytesOfClearData;
Andreas Hubered3e3e02012-03-26 11:13:27 -0700127 }
128
Andreas Huber1bd139a2012-04-03 14:19:20 -0700129 data.writeInt32(totalSize);
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700130 data.writeStrongBinder(IInterface::asBinder(source.mSharedMemory));
131 data.writeInt32(source.mHeapSeqNum);
Jeff Tinkerc481b502015-04-06 18:21:05 -0700132 data.writeInt32(offset);
Andreas Hubered3e3e02012-03-26 11:13:27 -0700133
Andreas Huber1bd139a2012-04-03 14:19:20 -0700134 data.writeInt32(numSubSamples);
135 data.write(subSamples, sizeof(CryptoPlugin::SubSample) * numSubSamples);
Andreas Hubered3e3e02012-03-26 11:13:27 -0700136
Jeff Tinkera53d6552017-01-20 00:31:46 -0800137 data.writeInt32((int32_t)destination.mType);
138 if (destination.mType == kDestinationTypeNativeHandle) {
139 if (destination.mHandle == NULL) {
140 return BAD_VALUE;
141 }
142 data.writeNativeHandle(destination.mHandle);
Jeff Tinker9ac86b32016-01-23 17:27:58 -0800143 } else {
Jeff Tinkera53d6552017-01-20 00:31:46 -0800144 if (destination.mSharedMemory == NULL) {
145 return BAD_VALUE;
146 }
147 data.writeStrongBinder(IInterface::asBinder(destination.mSharedMemory));
Andreas Hubered3e3e02012-03-26 11:13:27 -0700148 }
149
Andreas Huber1bd139a2012-04-03 14:19:20 -0700150 remote()->transact(DECRYPT, data, &reply);
Andreas Hubered3e3e02012-03-26 11:13:27 -0700151
Edwin Wongfa2b8f22012-07-10 20:01:13 -0700152 ssize_t result = reply.readInt32();
Andreas Hubered3e3e02012-03-26 11:13:27 -0700153
Jeff Tinkerceffd8c2015-05-05 15:09:14 -0700154 if (isCryptoError(result)) {
Jeff Tinker0be134a2017-03-09 17:01:10 -0800155 AString msg = reply.readCString();
156 if (errorDetailMsg) {
157 *errorDetailMsg = msg;
158 }
Andreas Hubered3e3e02012-03-26 11:13:27 -0700159 }
160
Edwin Wongfa2b8f22012-07-10 20:01:13 -0700161 return result;
Andreas Hubered3e3e02012-03-26 11:13:27 -0700162 }
163
Jeff Tinker2514d082014-11-03 13:29:35 -0800164 virtual void notifyResolution(
165 uint32_t width, uint32_t height) {
166 Parcel data, reply;
167 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
168 data.writeInt32(width);
169 data.writeInt32(height);
170 remote()->transact(NOTIFY_RESOLUTION, data, &reply);
171 }
172
Jeff Tinker18495702015-04-10 04:10:59 -0700173 virtual status_t setMediaDrmSession(const Vector<uint8_t> &sessionId) {
174 Parcel data, reply;
175 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
176
177 writeVector(data, sessionId);
178 remote()->transact(SET_MEDIADRM_SESSION, data, &reply);
179
180 return reply.readInt32();
181 }
182
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700183 virtual int32_t setHeap(const sp<IMemoryHeap> &heap) {
Chong Zhangd07c9272017-03-28 11:02:06 -0700184 Parcel data, reply;
185 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
186 data.writeStrongBinder(IInterface::asBinder(heap));
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700187 status_t err = remote()->transact(SET_HEAP, data, &reply);
188 if (err != NO_ERROR) {
189 return -1;
190 }
191 int32_t seqNum;
192 if (reply.readInt32(&seqNum) != NO_ERROR) {
193 return -1;
194 }
195 return seqNum;
Chong Zhangd07c9272017-03-28 11:02:06 -0700196 }
197
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700198 virtual void unsetHeap(int32_t seqNum) {
Chong Zhangd07c9272017-03-28 11:02:06 -0700199 Parcel data, reply;
200 data.writeInterfaceToken(ICrypto::getInterfaceDescriptor());
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700201 data.writeInt32(seqNum);
Chong Zhangd07c9272017-03-28 11:02:06 -0700202 remote()->transact(UNSET_HEAP, data, &reply);
203 return;
204 }
205
206
Andreas Hubered3e3e02012-03-26 11:13:27 -0700207private:
Jeff Tinker18495702015-04-10 04:10:59 -0700208 void readVector(Parcel &reply, Vector<uint8_t> &vector) const {
209 uint32_t size = reply.readInt32();
210 vector.insertAt((size_t)0, size);
211 reply.read(vector.editArray(), size);
212 }
213
214 void writeVector(Parcel &data, Vector<uint8_t> const &vector) const {
215 data.writeInt32(vector.size());
216 data.write(vector.array(), vector.size());
217 }
218
Andreas Hubered3e3e02012-03-26 11:13:27 -0700219 DISALLOW_EVIL_CONSTRUCTORS(BpCrypto);
220};
221
222IMPLEMENT_META_INTERFACE(Crypto, "android.hardware.ICrypto");
223
224////////////////////////////////////////////////////////////////////////////////
225
Jeff Tinker18495702015-04-10 04:10:59 -0700226void BnCrypto::readVector(const Parcel &data, Vector<uint8_t> &vector) const {
227 uint32_t size = data.readInt32();
Jeff Tinkerc1bf68a2018-07-24 14:13:13 -0700228 if (vector.insertAt((size_t)0, size) < 0) {
229 vector.clear();
230 }
231 if (data.read(vector.editArray(), size) != NO_ERROR) {
232 vector.clear();
233 android_errorWriteWithInfoLog(0x534e4554, "62872384", -1, NULL, 0);
234 }
Jeff Tinker18495702015-04-10 04:10:59 -0700235}
236
237void BnCrypto::writeVector(Parcel *reply, Vector<uint8_t> const &vector) const {
238 reply->writeInt32(vector.size());
239 reply->write(vector.array(), vector.size());
240}
241
Andreas Hubered3e3e02012-03-26 11:13:27 -0700242status_t BnCrypto::onTransact(
243 uint32_t code, const Parcel &data, Parcel *reply, uint32_t flags) {
244 switch (code) {
Andreas Huber1bd139a2012-04-03 14:19:20 -0700245 case INIT_CHECK:
Andreas Hubered3e3e02012-03-26 11:13:27 -0700246 {
247 CHECK_INTERFACE(ICrypto, data, reply);
Andreas Huber1bd139a2012-04-03 14:19:20 -0700248 reply->writeInt32(initCheck());
Andreas Hubered3e3e02012-03-26 11:13:27 -0700249
250 return OK;
251 }
252
Andreas Huber1bd139a2012-04-03 14:19:20 -0700253 case IS_CRYPTO_SUPPORTED:
Andreas Hubered3e3e02012-03-26 11:13:27 -0700254 {
255 CHECK_INTERFACE(ICrypto, data, reply);
Andreas Huber1bd139a2012-04-03 14:19:20 -0700256 uint8_t uuid[16];
257 data.read(uuid, sizeof(uuid));
258 reply->writeInt32(isCryptoSchemeSupported(uuid));
Andreas Hubered3e3e02012-03-26 11:13:27 -0700259
260 return OK;
261 }
262
Andreas Huber1bd139a2012-04-03 14:19:20 -0700263 case CREATE_PLUGIN:
Andreas Hubered3e3e02012-03-26 11:13:27 -0700264 {
265 CHECK_INTERFACE(ICrypto, data, reply);
266
Robert Shih63889882020-02-04 17:23:58 -0800267 uint8_t uuid[16] = {0};
268 if (data.read(uuid, sizeof(uuid)) != NO_ERROR) {
269 android_errorWriteLog(0x534e4554, "144767096");
270 reply->writeInt32(BAD_VALUE);
271 return OK;
272 }
Andreas Hubered3e3e02012-03-26 11:13:27 -0700273
Andreas Huber1bd139a2012-04-03 14:19:20 -0700274 size_t opaqueSize = data.readInt32();
Andreas Huber705868c2012-04-11 15:41:45 -0700275 void *opaqueData = NULL;
276
Edwin Wong9247e102017-03-13 16:38:20 -0700277 const size_t kMaxOpaqueSize = 100 * 1024;
278 if (opaqueSize > kMaxOpaqueSize) {
279 return BAD_VALUE;
Andreas Huber705868c2012-04-11 15:41:45 -0700280 }
Andreas Hubered3e3e02012-03-26 11:13:27 -0700281
Edwin Wong9247e102017-03-13 16:38:20 -0700282 opaqueData = malloc(opaqueSize);
283 if (NULL == opaqueData) {
284 return NO_MEMORY;
285 }
286
Robert Shih63889882020-02-04 17:23:58 -0800287 if (data.read(opaqueData, opaqueSize) != NO_ERROR) {
288 android_errorWriteLog(0x534e4554, "144767096");
289 reply->writeInt32(BAD_VALUE);
290 return OK;
291 }
Andreas Huber1bd139a2012-04-03 14:19:20 -0700292 reply->writeInt32(createPlugin(uuid, opaqueData, opaqueSize));
293
Edwin Wong9247e102017-03-13 16:38:20 -0700294 free(opaqueData);
295 opaqueData = NULL;
Andreas Hubered3e3e02012-03-26 11:13:27 -0700296
297 return OK;
298 }
299
Andreas Huber1bd139a2012-04-03 14:19:20 -0700300 case DESTROY_PLUGIN:
Andreas Hubered3e3e02012-03-26 11:13:27 -0700301 {
302 CHECK_INTERFACE(ICrypto, data, reply);
Andreas Huber1bd139a2012-04-03 14:19:20 -0700303 reply->writeInt32(destroyPlugin());
Andreas Hubered3e3e02012-03-26 11:13:27 -0700304
305 return OK;
306 }
307
Andreas Huber1bd139a2012-04-03 14:19:20 -0700308 case REQUIRES_SECURE_COMPONENT:
Andreas Hubered3e3e02012-03-26 11:13:27 -0700309 {
310 CHECK_INTERFACE(ICrypto, data, reply);
311
Andreas Huber1bd139a2012-04-03 14:19:20 -0700312 const char *mime = data.readCString();
Wei Jia2afac0c2016-01-07 12:13:07 -0800313 if (mime == NULL) {
314 reply->writeInt32(BAD_VALUE);
315 } else {
316 reply->writeInt32(requiresSecureDecoderComponent(mime));
317 }
Andreas Hubered3e3e02012-03-26 11:13:27 -0700318
Andreas Huber1bd139a2012-04-03 14:19:20 -0700319 return OK;
320 }
321
322 case DECRYPT:
323 {
324 CHECK_INTERFACE(ICrypto, data, reply);
325
Andreas Huber1bd139a2012-04-03 14:19:20 -0700326 CryptoPlugin::Mode mode = (CryptoPlugin::Mode)data.readInt32();
Jeff Tinker18cb1ec2015-12-18 11:55:22 -0800327 CryptoPlugin::Pattern pattern;
328 pattern.mEncryptBlocks = data.readInt32();
329 pattern.mSkipBlocks = data.readInt32();
Andreas Huber1bd139a2012-04-03 14:19:20 -0700330
331 uint8_t key[16];
332 data.read(key, sizeof(key));
333
334 uint8_t iv[16];
335 data.read(iv, sizeof(iv));
336
337 size_t totalSize = data.readInt32();
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700338
339 SourceBuffer source;
340
341 source.mSharedMemory =
Jeff Tinkerc481b502015-04-06 18:21:05 -0700342 interface_cast<IMemory>(data.readStrongBinder());
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700343 if (source.mSharedMemory == NULL) {
Wei Jia2afac0c2016-01-07 12:13:07 -0800344 reply->writeInt32(BAD_VALUE);
345 return OK;
346 }
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700347 source.mHeapSeqNum = data.readInt32();
348
Jeff Tinkerc481b502015-04-06 18:21:05 -0700349 int32_t offset = data.readInt32();
Andreas Huber1bd139a2012-04-03 14:19:20 -0700350
351 int32_t numSubSamples = data.readInt32();
Jeff Tinker4183d532016-05-20 17:19:31 -0700352 if (numSubSamples < 0 || numSubSamples > 0xffff) {
353 reply->writeInt32(BAD_VALUE);
354 return OK;
355 }
Andreas Huber1bd139a2012-04-03 14:19:20 -0700356
Edwin Wongfdd2cad2018-03-31 16:31:29 -0700357 std::unique_ptr<CryptoPlugin::SubSample[]> subSamples =
358 std::make_unique<CryptoPlugin::SubSample[]>(numSubSamples);
Andreas Huber1bd139a2012-04-03 14:19:20 -0700359
Edwin Wongfdd2cad2018-03-31 16:31:29 -0700360 data.read(subSamples.get(),
Andreas Huber1bd139a2012-04-03 14:19:20 -0700361 sizeof(CryptoPlugin::SubSample) * numSubSamples);
362
Jeff Tinkera53d6552017-01-20 00:31:46 -0800363 DestinationBuffer destination;
364 destination.mType = (DestinationType)data.readInt32();
365 if (destination.mType == kDestinationTypeNativeHandle) {
366 destination.mHandle = data.readNativeHandle();
367 if (destination.mHandle == NULL) {
368 reply->writeInt32(BAD_VALUE);
369 return OK;
370 }
371 } else if (destination.mType == kDestinationTypeSharedMemory) {
372 destination.mSharedMemory =
373 interface_cast<IMemory>(data.readStrongBinder());
374 if (destination.mSharedMemory == NULL) {
375 reply->writeInt32(BAD_VALUE);
376 return OK;
377 }
Jeff Tinker5231cc12018-01-11 00:14:53 -0800378 sp<IMemory> dest = destination.mSharedMemory;
379 if (totalSize > dest->size() ||
380 (size_t)dest->offset() > dest->size() - totalSize) {
381 reply->writeInt32(BAD_VALUE);
382 android_errorWriteLog(0x534e4554, "71389378");
383 return OK;
384 }
Jeff Tinker24420472018-01-11 17:46:16 -0800385 } else {
386 reply->writeInt32(BAD_VALUE);
387 android_errorWriteLog(0x534e4554, "70526702");
388 return OK;
Andreas Hubered3e3e02012-03-26 11:13:27 -0700389 }
390
Andreas Huber5b8987e2012-04-19 12:52:20 -0700391 AString errorDetailMsg;
Jeff Tinkerc481b502015-04-06 18:21:05 -0700392 ssize_t result;
393
Jeff Tinkerc6fc6a32015-08-26 20:22:39 -0700394 size_t sumSubsampleSizes = 0;
395 bool overflow = false;
396 for (int32_t i = 0; i < numSubSamples; ++i) {
397 CryptoPlugin::SubSample &ss = subSamples[i];
398 if (sumSubsampleSizes <= SIZE_MAX - ss.mNumBytesOfEncryptedData) {
399 sumSubsampleSizes += ss.mNumBytesOfEncryptedData;
400 } else {
401 overflow = true;
402 }
403 if (sumSubsampleSizes <= SIZE_MAX - ss.mNumBytesOfClearData) {
404 sumSubsampleSizes += ss.mNumBytesOfClearData;
405 } else {
406 overflow = true;
407 }
408 }
409
410 if (overflow || sumSubsampleSizes != totalSize) {
411 result = -EINVAL;
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700412 } else if (totalSize > source.mSharedMemory->size()) {
Jeff Tinkerbb4877d2015-12-04 16:29:16 -0800413 result = -EINVAL;
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700414 } else if ((size_t)offset > source.mSharedMemory->size() - totalSize) {
Jeff Tinkerc481b502015-04-06 18:21:05 -0700415 result = -EINVAL;
416 } else {
Jeff Tinkera53d6552017-01-20 00:31:46 -0800417 result = decrypt(key, iv, mode, pattern, source, offset,
Edwin Wongfdd2cad2018-03-31 16:31:29 -0700418 subSamples.get(), numSubSamples, destination, &errorDetailMsg);
Jeff Tinkerc481b502015-04-06 18:21:05 -0700419 }
Andreas Hubered3e3e02012-03-26 11:13:27 -0700420
Edwin Wongfa2b8f22012-07-10 20:01:13 -0700421 reply->writeInt32(result);
Andreas Hubered3e3e02012-03-26 11:13:27 -0700422
Jeff Tinkerceffd8c2015-05-05 15:09:14 -0700423 if (isCryptoError(result)) {
Andreas Huber5b8987e2012-04-19 12:52:20 -0700424 reply->writeCString(errorDetailMsg.c_str());
425 }
426
Jeff Tinkera53d6552017-01-20 00:31:46 -0800427 if (destination.mType == kDestinationTypeNativeHandle) {
Jeff Tinker9ac86b32016-01-23 17:27:58 -0800428 int err;
Jeff Tinkera53d6552017-01-20 00:31:46 -0800429 if ((err = native_handle_close(destination.mHandle)) < 0) {
Jeff Tinker9ac86b32016-01-23 17:27:58 -0800430 ALOGW("secure buffer native_handle_close failed: %d", err);
431 }
Jeff Tinkera53d6552017-01-20 00:31:46 -0800432 if ((err = native_handle_delete(destination.mHandle)) < 0) {
Jeff Tinker9ac86b32016-01-23 17:27:58 -0800433 ALOGW("secure buffer native_handle_delete failed: %d", err);
434 }
Andreas Huber1bd139a2012-04-03 14:19:20 -0700435 }
436
Edwin Wongfdd2cad2018-03-31 16:31:29 -0700437 subSamples.reset();
Andreas Hubered3e3e02012-03-26 11:13:27 -0700438 return OK;
439 }
440
Jeff Tinker2514d082014-11-03 13:29:35 -0800441 case NOTIFY_RESOLUTION:
442 {
443 CHECK_INTERFACE(ICrypto, data, reply);
444
445 int32_t width = data.readInt32();
446 int32_t height = data.readInt32();
447 notifyResolution(width, height);
448
449 return OK;
450 }
451
Jeff Tinker18495702015-04-10 04:10:59 -0700452 case SET_MEDIADRM_SESSION:
453 {
454 CHECK_INTERFACE(IDrm, data, reply);
455 Vector<uint8_t> sessionId;
456 readVector(data, sessionId);
457 reply->writeInt32(setMediaDrmSession(sessionId));
458 return OK;
459 }
460
Chong Zhangd07c9272017-03-28 11:02:06 -0700461 case SET_HEAP:
462 {
463 CHECK_INTERFACE(ICrypto, data, reply);
464 sp<IMemoryHeap> heap =
465 interface_cast<IMemoryHeap>(data.readStrongBinder());
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700466 reply->writeInt32(setHeap(heap));
Chong Zhangd07c9272017-03-28 11:02:06 -0700467 return OK;
468 }
469
470 case UNSET_HEAP:
471 {
472 CHECK_INTERFACE(ICrypto, data, reply);
Chong Zhang6dcab2b2017-03-28 14:18:27 -0700473 int32_t seqNum = data.readInt32();
474 unsetHeap(seqNum);
Chong Zhangd07c9272017-03-28 11:02:06 -0700475 return OK;
476 }
477
Andreas Hubered3e3e02012-03-26 11:13:27 -0700478 default:
479 return BBinder::onTransact(code, data, reply, flags);
480 }
481}
482
483} // namespace android