blob: 1809619d0262e996e301829f05fb9206caa093e1 [file] [log] [blame]
aimitakeshid074e302010-07-29 10:12:27 +09001/*
2 * Copyright (C) 2010 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
Takeshi Aimidc549d62010-09-20 23:40:41 +090017//#define LOG_NDEBUG 0
aimitakeshid074e302010-07-29 10:12:27 +090018#define LOG_TAG "DrmManager(Native)"
19#include "utils/Log.h"
20
21#include <utils/String8.h>
22#include <drm/DrmInfo.h>
23#include <drm/DrmInfoEvent.h>
24#include <drm/DrmRights.h>
25#include <drm/DrmConstraints.h>
Takeshi Aimidc9186562010-11-16 13:56:11 +090026#include <drm/DrmMetadata.h>
aimitakeshid074e302010-07-29 10:12:27 +090027#include <drm/DrmInfoStatus.h>
28#include <drm/DrmInfoRequest.h>
29#include <drm/DrmSupportInfo.h>
30#include <drm/DrmConvertedStatus.h>
31#include <IDrmEngine.h>
32
33#include "DrmManager.h"
34#include "ReadWriteUtils.h"
35
36#define DECRYPT_FILE_ERROR -1
37
38using namespace android;
39
40const String8 DrmManager::EMPTY_STRING("");
41
42DrmManager::DrmManager() :
43 mDecryptSessionId(0),
44 mConvertId(0) {
45
46}
47
48DrmManager::~DrmManager() {
49
50}
51
Takeshi Aimidc549d62010-09-20 23:40:41 +090052int DrmManager::addUniqueId(int uniqueId) {
Gloria Wang2ef2d492011-03-04 14:45:03 -080053 Mutex::Autolock _l(mLock);
Takeshi Aimidc549d62010-09-20 23:40:41 +090054 if (0 == uniqueId) {
55 int temp = 0;
56 bool foundUniqueId = false;
57 srand(time(NULL));
58
59 while (!foundUniqueId) {
60 const int size = mUniqueIdVector.size();
61 temp = rand() % 100;
62
63 int index = 0;
64 for (; index < size; ++index) {
65 if (mUniqueIdVector.itemAt(index) == temp) {
66 foundUniqueId = false;
67 break;
68 }
69 }
70 if (index == size) {
71 foundUniqueId = true;
72 }
73 }
74 uniqueId = temp;
75 }
76 mUniqueIdVector.push(uniqueId);
77 return uniqueId;
78}
79
80void DrmManager::removeUniqueId(int uniqueId) {
Gloria Wang2ef2d492011-03-04 14:45:03 -080081 Mutex::Autolock _l(mLock);
Takeshi Aimidc549d62010-09-20 23:40:41 +090082 for (unsigned int i = 0; i < mUniqueIdVector.size(); i++) {
83 if (uniqueId == mUniqueIdVector.itemAt(i)) {
84 mUniqueIdVector.removeAt(i);
85 break;
86 }
87 }
88}
89
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +090090status_t DrmManager::loadPlugIns() {
Glenn Kastencbba7202011-01-11 17:15:49 -080091 String8 pluginDirPath("/system/lib/drm");
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +090092 return loadPlugIns(pluginDirPath);
aimitakeshid074e302010-07-29 10:12:27 +090093}
94
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +090095status_t DrmManager::loadPlugIns(const String8& plugInDirPath) {
aimitakeshid074e302010-07-29 10:12:27 +090096 if (mSupportInfoToPlugInIdMap.isEmpty()) {
97 mPlugInManager.loadPlugIns(plugInDirPath);
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +090098 Vector<String8> plugInPathList = mPlugInManager.getPlugInIdList();
99 for (unsigned int i = 0; i < plugInPathList.size(); ++i) {
100 String8 plugInPath = plugInPathList[i];
101 DrmSupportInfo* info = mPlugInManager.getPlugIn(plugInPath).getSupportInfo(0);
102 if (NULL != info) {
103 mSupportInfoToPlugInIdMap.add(*info, plugInPath);
James Dong3f0341c2011-04-24 12:38:35 -0700104 delete info;
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900105 }
106 }
aimitakeshid074e302010-07-29 10:12:27 +0900107 }
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900108 return DRM_NO_ERROR;
109}
aimitakeshid074e302010-07-29 10:12:27 +0900110
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900111status_t DrmManager::unloadPlugIns() {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800112 Mutex::Autolock _l(mLock);
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900113 mConvertSessionMap.clear();
114 mDecryptSessionMap.clear();
115 mPlugInManager.unloadPlugIns();
116 mSupportInfoToPlugInIdMap.clear();
aimitakeshid074e302010-07-29 10:12:27 +0900117 return DRM_NO_ERROR;
118}
119
120status_t DrmManager::setDrmServiceListener(
121 int uniqueId, const sp<IDrmServiceListener>& drmServiceListener) {
Gloria Wang192b5912011-03-11 14:07:21 -0800122 Mutex::Autolock _l(mListenerLock);
Takeshi Aimif05913a2010-11-30 16:27:42 +0900123 if (NULL != drmServiceListener.get()) {
124 mServiceListeners.add(uniqueId, drmServiceListener);
125 } else {
126 mServiceListeners.removeItem(uniqueId);
127 }
aimitakeshid074e302010-07-29 10:12:27 +0900128 return DRM_NO_ERROR;
129}
130
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900131void DrmManager::addClient(int uniqueId) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800132 Mutex::Autolock _l(mLock);
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900133 if (!mSupportInfoToPlugInIdMap.isEmpty()) {
134 Vector<String8> plugInIdList = mPlugInManager.getPlugInIdList();
135 for (unsigned int index = 0; index < plugInIdList.size(); index++) {
136 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInIdList.itemAt(index));
137 rDrmEngine.initialize(uniqueId);
138 rDrmEngine.setOnInfoListener(uniqueId, this);
139 }
140 }
141}
aimitakeshid074e302010-07-29 10:12:27 +0900142
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900143void DrmManager::removeClient(int uniqueId) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800144 Mutex::Autolock _l(mLock);
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900145 Vector<String8> plugInIdList = mPlugInManager.getPlugInIdList();
aimitakeshid074e302010-07-29 10:12:27 +0900146 for (unsigned int index = 0; index < plugInIdList.size(); index++) {
147 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInIdList.itemAt(index));
148 rDrmEngine.terminate(uniqueId);
149 }
aimitakeshid074e302010-07-29 10:12:27 +0900150}
151
152DrmConstraints* DrmManager::getConstraints(int uniqueId, const String8* path, const int action) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800153 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900154 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, *path);
155 if (EMPTY_STRING != plugInId) {
156 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
157 return rDrmEngine.getConstraints(uniqueId, path, action);
158 }
159 return NULL;
160}
161
Takeshi Aimidc9186562010-11-16 13:56:11 +0900162DrmMetadata* DrmManager::getMetadata(int uniqueId, const String8* path) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800163 Mutex::Autolock _l(mLock);
Takeshi Aimidc9186562010-11-16 13:56:11 +0900164 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, *path);
165 if (EMPTY_STRING != plugInId) {
166 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
167 return rDrmEngine.getMetadata(uniqueId, path);
168 }
169 return NULL;
170}
171
aimitakeshid074e302010-07-29 10:12:27 +0900172status_t DrmManager::installDrmEngine(int uniqueId, const String8& absolutePath) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800173 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900174 mPlugInManager.loadPlugIn(absolutePath);
175
176 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(absolutePath);
177 rDrmEngine.initialize(uniqueId);
178 rDrmEngine.setOnInfoListener(uniqueId, this);
179
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900180 DrmSupportInfo* info = rDrmEngine.getSupportInfo(0);
aimitakeshid074e302010-07-29 10:12:27 +0900181 mSupportInfoToPlugInIdMap.add(*info, absolutePath);
James Dong3f0341c2011-04-24 12:38:35 -0700182 delete info;
aimitakeshid074e302010-07-29 10:12:27 +0900183
184 return DRM_NO_ERROR;
185}
186
187bool DrmManager::canHandle(int uniqueId, const String8& path, const String8& mimeType) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800188 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900189 const String8 plugInId = getSupportedPlugInId(mimeType);
190 bool result = (EMPTY_STRING != plugInId) ? true : false;
191
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900192 if (0 < path.length()) {
aimitakeshid074e302010-07-29 10:12:27 +0900193 if (result) {
194 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
195 result = rDrmEngine.canHandle(uniqueId, path);
196 } else {
Gloria Wang289401b2011-03-02 12:33:00 -0800197 String8 extension = path.getPathExtension();
198 if (String8("") != extension) {
199 result = canHandle(uniqueId, path);
200 }
aimitakeshid074e302010-07-29 10:12:27 +0900201 }
202 }
203 return result;
204}
205
206DrmInfoStatus* DrmManager::processDrmInfo(int uniqueId, const DrmInfo* drmInfo) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800207 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900208 const String8 plugInId = getSupportedPlugInId(drmInfo->getMimeType());
209 if (EMPTY_STRING != plugInId) {
210 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
211 return rDrmEngine.processDrmInfo(uniqueId, drmInfo);
212 }
213 return NULL;
214}
215
216bool DrmManager::canHandle(int uniqueId, const String8& path) {
217 bool result = false;
218 Vector<String8> plugInPathList = mPlugInManager.getPlugInIdList();
219
220 for (unsigned int i = 0; i < plugInPathList.size(); ++i) {
221 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInPathList[i]);
222 result = rDrmEngine.canHandle(uniqueId, path);
223
224 if (result) {
225 break;
226 }
227 }
228 return result;
229}
230
231DrmInfo* DrmManager::acquireDrmInfo(int uniqueId, const DrmInfoRequest* drmInfoRequest) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800232 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900233 const String8 plugInId = getSupportedPlugInId(drmInfoRequest->getMimeType());
234 if (EMPTY_STRING != plugInId) {
235 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
236 return rDrmEngine.acquireDrmInfo(uniqueId, drmInfoRequest);
237 }
238 return NULL;
239}
240
Takeshi Aimidc549d62010-09-20 23:40:41 +0900241status_t DrmManager::saveRights(int uniqueId, const DrmRights& drmRights,
aimitakeshid074e302010-07-29 10:12:27 +0900242 const String8& rightsPath, const String8& contentPath) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800243 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900244 const String8 plugInId = getSupportedPlugInId(drmRights.getMimeType());
Takeshi Aimidc549d62010-09-20 23:40:41 +0900245 status_t result = DRM_ERROR_UNKNOWN;
aimitakeshid074e302010-07-29 10:12:27 +0900246 if (EMPTY_STRING != plugInId) {
247 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900248 result = rDrmEngine.saveRights(uniqueId, drmRights, rightsPath, contentPath);
aimitakeshid074e302010-07-29 10:12:27 +0900249 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900250 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900251}
252
253String8 DrmManager::getOriginalMimeType(int uniqueId, const String8& path) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800254 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900255 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, path);
256 if (EMPTY_STRING != plugInId) {
257 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
258 return rDrmEngine.getOriginalMimeType(uniqueId, path);
259 }
260 return EMPTY_STRING;
261}
262
263int DrmManager::getDrmObjectType(int uniqueId, const String8& path, const String8& mimeType) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800264 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900265 const String8 plugInId = getSupportedPlugInId(uniqueId, path, mimeType);
266 if (EMPTY_STRING != plugInId) {
267 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
268 return rDrmEngine.getDrmObjectType(uniqueId, path, mimeType);
269 }
270 return DrmObjectType::UNKNOWN;
271}
272
273int DrmManager::checkRightsStatus(int uniqueId, const String8& path, int action) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800274 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900275 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, path);
276 if (EMPTY_STRING != plugInId) {
277 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
278 return rDrmEngine.checkRightsStatus(uniqueId, path, action);
279 }
280 return RightsStatus::RIGHTS_INVALID;
281}
282
Takeshi Aimidc549d62010-09-20 23:40:41 +0900283status_t DrmManager::consumeRights(
aimitakeshid074e302010-07-29 10:12:27 +0900284 int uniqueId, DecryptHandle* decryptHandle, int action, bool reserve) {
Takeshi Aimidc549d62010-09-20 23:40:41 +0900285 status_t result = DRM_ERROR_UNKNOWN;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800286 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900287 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
288 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900289 result = drmEngine->consumeRights(uniqueId, decryptHandle, action, reserve);
aimitakeshid074e302010-07-29 10:12:27 +0900290 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900291 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900292}
293
Takeshi Aimidc549d62010-09-20 23:40:41 +0900294status_t DrmManager::setPlaybackStatus(
Gloria Wang5fc3edb2010-11-19 15:19:36 -0800295 int uniqueId, DecryptHandle* decryptHandle, int playbackStatus, int64_t position) {
Takeshi Aimidc549d62010-09-20 23:40:41 +0900296 status_t result = DRM_ERROR_UNKNOWN;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800297 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900298 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
299 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900300 result = drmEngine->setPlaybackStatus(uniqueId, decryptHandle, playbackStatus, position);
aimitakeshid074e302010-07-29 10:12:27 +0900301 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900302 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900303}
304
305bool DrmManager::validateAction(
306 int uniqueId, const String8& path, int action, const ActionDescription& description) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800307 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900308 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, path);
309 if (EMPTY_STRING != plugInId) {
310 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
311 return rDrmEngine.validateAction(uniqueId, path, action, description);
312 }
313 return false;
314}
315
Takeshi Aimidc549d62010-09-20 23:40:41 +0900316status_t DrmManager::removeRights(int uniqueId, const String8& path) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800317 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900318 const String8 plugInId = getSupportedPlugInIdFromPath(uniqueId, path);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900319 status_t result = DRM_ERROR_UNKNOWN;
aimitakeshid074e302010-07-29 10:12:27 +0900320 if (EMPTY_STRING != plugInId) {
321 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900322 result = rDrmEngine.removeRights(uniqueId, path);
aimitakeshid074e302010-07-29 10:12:27 +0900323 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900324 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900325}
326
Takeshi Aimidc549d62010-09-20 23:40:41 +0900327status_t DrmManager::removeAllRights(int uniqueId) {
aimitakeshid074e302010-07-29 10:12:27 +0900328 Vector<String8> plugInIdList = mPlugInManager.getPlugInIdList();
Takeshi Aimidc549d62010-09-20 23:40:41 +0900329 status_t result = DRM_ERROR_UNKNOWN;
aimitakeshid074e302010-07-29 10:12:27 +0900330 for (unsigned int index = 0; index < plugInIdList.size(); index++) {
331 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInIdList.itemAt(index));
Takeshi Aimidc549d62010-09-20 23:40:41 +0900332 result = rDrmEngine.removeAllRights(uniqueId);
333 if (DRM_NO_ERROR != result) {
334 break;
335 }
aimitakeshid074e302010-07-29 10:12:27 +0900336 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900337 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900338}
339
340int DrmManager::openConvertSession(int uniqueId, const String8& mimeType) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800341 Mutex::Autolock _l(mConvertLock);
aimitakeshid074e302010-07-29 10:12:27 +0900342 int convertId = -1;
343
344 const String8 plugInId = getSupportedPlugInId(mimeType);
345 if (EMPTY_STRING != plugInId) {
346 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
347
Takeshi Aimidc549d62010-09-20 23:40:41 +0900348 if (DRM_NO_ERROR == rDrmEngine.openConvertSession(uniqueId, mConvertId + 1)) {
Takeshi Aimidc549d62010-09-20 23:40:41 +0900349 ++mConvertId;
350 convertId = mConvertId;
351 mConvertSessionMap.add(convertId, &rDrmEngine);
352 }
aimitakeshid074e302010-07-29 10:12:27 +0900353 }
354 return convertId;
355}
356
357DrmConvertedStatus* DrmManager::convertData(
358 int uniqueId, int convertId, const DrmBuffer* inputData) {
359 DrmConvertedStatus *drmConvertedStatus = NULL;
360
Gloria Wang2ef2d492011-03-04 14:45:03 -0800361 Mutex::Autolock _l(mConvertLock);
aimitakeshid074e302010-07-29 10:12:27 +0900362 if (mConvertSessionMap.indexOfKey(convertId) != NAME_NOT_FOUND) {
363 IDrmEngine* drmEngine = mConvertSessionMap.valueFor(convertId);
364 drmConvertedStatus = drmEngine->convertData(uniqueId, convertId, inputData);
365 }
366 return drmConvertedStatus;
367}
368
369DrmConvertedStatus* DrmManager::closeConvertSession(int uniqueId, int convertId) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800370 Mutex::Autolock _l(mConvertLock);
aimitakeshid074e302010-07-29 10:12:27 +0900371 DrmConvertedStatus *drmConvertedStatus = NULL;
372
373 if (mConvertSessionMap.indexOfKey(convertId) != NAME_NOT_FOUND) {
374 IDrmEngine* drmEngine = mConvertSessionMap.valueFor(convertId);
375 drmConvertedStatus = drmEngine->closeConvertSession(uniqueId, convertId);
376 mConvertSessionMap.removeItem(convertId);
377 }
378 return drmConvertedStatus;
379}
380
381status_t DrmManager::getAllSupportInfo(
382 int uniqueId, int* length, DrmSupportInfo** drmSupportInfoArray) {
Gloria Wang2ef2d492011-03-04 14:45:03 -0800383 Mutex::Autolock _l(mLock);
aimitakeshid074e302010-07-29 10:12:27 +0900384 Vector<String8> plugInPathList = mPlugInManager.getPlugInIdList();
385 int size = plugInPathList.size();
386 int validPlugins = 0;
387
388 if (0 < size) {
389 Vector<DrmSupportInfo> drmSupportInfoList;
390
391 for (int i = 0; i < size; ++i) {
392 String8 plugInPath = plugInPathList[i];
393 DrmSupportInfo* drmSupportInfo
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900394 = mPlugInManager.getPlugIn(plugInPath).getSupportInfo(0);
aimitakeshid074e302010-07-29 10:12:27 +0900395 if (NULL != drmSupportInfo) {
396 drmSupportInfoList.add(*drmSupportInfo);
397 delete drmSupportInfo; drmSupportInfo = NULL;
398 }
399 }
400
401 validPlugins = drmSupportInfoList.size();
402 if (0 < validPlugins) {
403 *drmSupportInfoArray = new DrmSupportInfo[validPlugins];
404 for (int i = 0; i < validPlugins; ++i) {
405 (*drmSupportInfoArray)[i] = drmSupportInfoList[i];
406 }
407 }
408 }
409 *length = validPlugins;
410 return DRM_NO_ERROR;
411}
412
Gloria Wang5fc3edb2010-11-19 15:19:36 -0800413DecryptHandle* DrmManager::openDecryptSession(int uniqueId, int fd, off64_t offset, off64_t length) {
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900414 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900415 status_t result = DRM_ERROR_CANNOT_HANDLE;
416 Vector<String8> plugInIdList = mPlugInManager.getPlugInIdList();
417
418 DecryptHandle* handle = new DecryptHandle();
419 if (NULL != handle) {
aimitakeshid074e302010-07-29 10:12:27 +0900420 handle->decryptId = mDecryptSessionId + 1;
421
422 for (unsigned int index = 0; index < plugInIdList.size(); index++) {
423 String8 plugInId = plugInIdList.itemAt(index);
424 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
425 result = rDrmEngine.openDecryptSession(uniqueId, handle, fd, offset, length);
426
aimitakeshid074e302010-07-29 10:12:27 +0900427 if (DRM_NO_ERROR == result) {
428 ++mDecryptSessionId;
429 mDecryptSessionMap.add(mDecryptSessionId, &rDrmEngine);
aimitakeshid074e302010-07-29 10:12:27 +0900430 break;
431 }
432 }
433 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900434 if (DRM_NO_ERROR != result) {
aimitakeshid074e302010-07-29 10:12:27 +0900435 delete handle; handle = NULL;
aimitakeshid074e302010-07-29 10:12:27 +0900436 }
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900437 return handle;
438}
aimitakeshid074e302010-07-29 10:12:27 +0900439
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900440DecryptHandle* DrmManager::openDecryptSession(int uniqueId, const char* uri) {
441 Mutex::Autolock _l(mDecryptLock);
442 status_t result = DRM_ERROR_CANNOT_HANDLE;
443 Vector<String8> plugInIdList = mPlugInManager.getPlugInIdList();
444
445 DecryptHandle* handle = new DecryptHandle();
446 if (NULL != handle) {
447 handle->decryptId = mDecryptSessionId + 1;
448
449 for (unsigned int index = 0; index < plugInIdList.size(); index++) {
450 String8 plugInId = plugInIdList.itemAt(index);
451 IDrmEngine& rDrmEngine = mPlugInManager.getPlugIn(plugInId);
452 result = rDrmEngine.openDecryptSession(uniqueId, handle, uri);
453
454 if (DRM_NO_ERROR == result) {
455 ++mDecryptSessionId;
456 mDecryptSessionMap.add(mDecryptSessionId, &rDrmEngine);
457 break;
458 }
459 }
460 }
461 if (DRM_NO_ERROR != result) {
462 delete handle; handle = NULL;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800463 LOGV("DrmManager::openDecryptSession: no capable plug-in found");
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900464 }
aimitakeshid074e302010-07-29 10:12:27 +0900465 return handle;
466}
467
Takeshi Aimidc549d62010-09-20 23:40:41 +0900468status_t DrmManager::closeDecryptSession(int uniqueId, DecryptHandle* decryptHandle) {
Takeshi Aimic7b3ccc2010-10-08 23:05:49 +0900469 Mutex::Autolock _l(mDecryptLock);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900470 status_t result = DRM_ERROR_UNKNOWN;
aimitakeshid074e302010-07-29 10:12:27 +0900471 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
472 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900473 result = drmEngine->closeDecryptSession(uniqueId, decryptHandle);
474 if (DRM_NO_ERROR == result) {
475 mDecryptSessionMap.removeItem(decryptHandle->decryptId);
476 }
aimitakeshid074e302010-07-29 10:12:27 +0900477 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900478 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900479}
480
Takeshi Aimidc549d62010-09-20 23:40:41 +0900481status_t DrmManager::initializeDecryptUnit(
aimitakeshid074e302010-07-29 10:12:27 +0900482 int uniqueId, DecryptHandle* decryptHandle, int decryptUnitId, const DrmBuffer* headerInfo) {
Takeshi Aimidc549d62010-09-20 23:40:41 +0900483 status_t result = DRM_ERROR_UNKNOWN;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800484 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900485 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
486 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900487 result = drmEngine->initializeDecryptUnit(uniqueId, decryptHandle, decryptUnitId, headerInfo);
aimitakeshid074e302010-07-29 10:12:27 +0900488 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900489 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900490}
491
Takeshi Aimidc549d62010-09-20 23:40:41 +0900492status_t DrmManager::decrypt(int uniqueId, DecryptHandle* decryptHandle, int decryptUnitId,
493 const DrmBuffer* encBuffer, DrmBuffer** decBuffer, DrmBuffer* IV) {
494 status_t result = DRM_ERROR_UNKNOWN;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800495
496 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900497 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
498 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900499 result = drmEngine->decrypt(
500 uniqueId, decryptHandle, decryptUnitId, encBuffer, decBuffer, IV);
aimitakeshid074e302010-07-29 10:12:27 +0900501 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900502 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900503}
504
Takeshi Aimidc549d62010-09-20 23:40:41 +0900505status_t DrmManager::finalizeDecryptUnit(
aimitakeshid074e302010-07-29 10:12:27 +0900506 int uniqueId, DecryptHandle* decryptHandle, int decryptUnitId) {
Takeshi Aimidc549d62010-09-20 23:40:41 +0900507 status_t result = DRM_ERROR_UNKNOWN;
Gloria Wang2ef2d492011-03-04 14:45:03 -0800508 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900509 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
510 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
Takeshi Aimidc549d62010-09-20 23:40:41 +0900511 result = drmEngine->finalizeDecryptUnit(uniqueId, decryptHandle, decryptUnitId);
aimitakeshid074e302010-07-29 10:12:27 +0900512 }
Takeshi Aimidc549d62010-09-20 23:40:41 +0900513 return result;
aimitakeshid074e302010-07-29 10:12:27 +0900514}
515
516ssize_t DrmManager::pread(int uniqueId, DecryptHandle* decryptHandle,
Gloria Wang5fc3edb2010-11-19 15:19:36 -0800517 void* buffer, ssize_t numBytes, off64_t offset) {
aimitakeshid074e302010-07-29 10:12:27 +0900518 ssize_t result = DECRYPT_FILE_ERROR;
519
Gloria Wang2ef2d492011-03-04 14:45:03 -0800520 Mutex::Autolock _l(mDecryptLock);
aimitakeshid074e302010-07-29 10:12:27 +0900521 if (mDecryptSessionMap.indexOfKey(decryptHandle->decryptId) != NAME_NOT_FOUND) {
522 IDrmEngine* drmEngine = mDecryptSessionMap.valueFor(decryptHandle->decryptId);
523 result = drmEngine->pread(uniqueId, decryptHandle, buffer, numBytes, offset);
524 }
525 return result;
526}
527
aimitakeshid074e302010-07-29 10:12:27 +0900528String8 DrmManager::getSupportedPlugInId(
529 int uniqueId, const String8& path, const String8& mimeType) {
530 String8 plugInId("");
531
532 if (EMPTY_STRING != mimeType) {
533 plugInId = getSupportedPlugInId(mimeType);
534 } else {
535 plugInId = getSupportedPlugInIdFromPath(uniqueId, path);
536 }
537 return plugInId;
538}
539
540String8 DrmManager::getSupportedPlugInId(const String8& mimeType) {
541 String8 plugInId("");
542
543 if (EMPTY_STRING != mimeType) {
544 for (unsigned int index = 0; index < mSupportInfoToPlugInIdMap.size(); index++) {
545 const DrmSupportInfo& drmSupportInfo = mSupportInfoToPlugInIdMap.keyAt(index);
546
547 if (drmSupportInfo.isSupportedMimeType(mimeType)) {
548 plugInId = mSupportInfoToPlugInIdMap.valueFor(drmSupportInfo);
549 break;
550 }
551 }
552 }
553 return plugInId;
554}
555
556String8 DrmManager::getSupportedPlugInIdFromPath(int uniqueId, const String8& path) {
557 String8 plugInId("");
558 const String8 fileSuffix = path.getPathExtension();
559
560 for (unsigned int index = 0; index < mSupportInfoToPlugInIdMap.size(); index++) {
561 const DrmSupportInfo& drmSupportInfo = mSupportInfoToPlugInIdMap.keyAt(index);
562
563 if (drmSupportInfo.isSupportedFileSuffix(fileSuffix)) {
564 String8 key = mSupportInfoToPlugInIdMap.valueFor(drmSupportInfo);
565 IDrmEngine& drmEngine = mPlugInManager.getPlugIn(key);
566
567 if (drmEngine.canHandle(uniqueId, path)) {
568 plugInId = key;
569 break;
570 }
571 }
572 }
573 return plugInId;
574}
575
576void DrmManager::onInfo(const DrmInfoEvent& event) {
Gloria Wang192b5912011-03-11 14:07:21 -0800577 Mutex::Autolock _l(mListenerLock);
aimitakeshid074e302010-07-29 10:12:27 +0900578 for (unsigned int index = 0; index < mServiceListeners.size(); index++) {
579 int uniqueId = mServiceListeners.keyAt(index);
580
581 if (uniqueId == event.getUniqueId()) {
582 sp<IDrmServiceListener> serviceListener = mServiceListeners.valueFor(uniqueId);
583 serviceListener->notify(event);
584 }
585 }
586}
587