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 #define LOG_TAG "android.hardware.drm@1.0-impl" 17 18 #include <utils/KeyedVector.h> 19 #include <utils/String8.h> 20 21 #include "DrmPlugin.h" 22 #include "TypeConvert.h" 23 24 namespace android { 25 namespace hardware { 26 namespace drm { 27 namespace V1_0 { 28 namespace implementation { 29 30 // Methods from ::android::hardware::drm::V1_0::IDrmPlugin follow. 31 openSession(openSession_cb _hidl_cb)32 Return<void> DrmPlugin::openSession(openSession_cb _hidl_cb) { 33 Vector<uint8_t> legacySessionId; 34 status_t status = mLegacyPlugin->openSession(legacySessionId); 35 _hidl_cb(toStatus(status), toHidlVec(legacySessionId)); 36 return Void(); 37 } 38 closeSession(const hidl_vec<uint8_t> & sessionId)39 Return<Status> DrmPlugin::closeSession(const hidl_vec<uint8_t>& sessionId) { 40 return toStatus(mLegacyPlugin->closeSession(toVector(sessionId))); 41 } 42 getKeyRequest(const hidl_vec<uint8_t> & scope,const hidl_vec<uint8_t> & initData,const hidl_string & mimeType,KeyType keyType,const hidl_vec<KeyValue> & optionalParameters,getKeyRequest_cb _hidl_cb)43 Return<void> DrmPlugin::getKeyRequest(const hidl_vec<uint8_t>& scope, 44 const hidl_vec<uint8_t>& initData, const hidl_string& mimeType, 45 KeyType keyType, const hidl_vec<KeyValue>& optionalParameters, 46 getKeyRequest_cb _hidl_cb) { 47 48 status_t status = android::OK; 49 50 android::DrmPlugin::KeyType legacyKeyType; 51 switch(keyType) { 52 case KeyType::OFFLINE: 53 legacyKeyType = android::DrmPlugin::kKeyType_Offline; 54 break; 55 case KeyType::STREAMING: 56 legacyKeyType = android::DrmPlugin::kKeyType_Streaming; 57 break; 58 case KeyType::RELEASE: 59 legacyKeyType = android::DrmPlugin::kKeyType_Release; 60 break; 61 default: 62 status = android::BAD_VALUE; 63 break; 64 } 65 66 Vector<uint8_t> legacyRequest; 67 KeyRequestType requestType = KeyRequestType::UNKNOWN; 68 String8 defaultUrl; 69 70 if (status == android::OK) { 71 android::KeyedVector<String8, String8> legacyOptionalParameters; 72 for (size_t i = 0; i < optionalParameters.size(); i++) { 73 legacyOptionalParameters.add(String8(optionalParameters[i].key.c_str()), 74 String8(optionalParameters[i].value.c_str())); 75 } 76 77 android::DrmPlugin::KeyRequestType legacyRequestType = 78 android::DrmPlugin::kKeyRequestType_Unknown; 79 80 status = mLegacyPlugin->getKeyRequest(toVector(scope), 81 toVector(initData), String8(mimeType.c_str()), legacyKeyType, 82 legacyOptionalParameters, legacyRequest, defaultUrl, 83 &legacyRequestType); 84 85 switch(legacyRequestType) { 86 case android::DrmPlugin::kKeyRequestType_Initial: 87 requestType = KeyRequestType::INITIAL; 88 break; 89 case android::DrmPlugin::kKeyRequestType_Renewal: 90 requestType = KeyRequestType::RENEWAL; 91 break; 92 case android::DrmPlugin::kKeyRequestType_Release: 93 requestType = KeyRequestType::RELEASE; 94 break; 95 case android::DrmPlugin::kKeyRequestType_Unknown: 96 default: 97 requestType = KeyRequestType::UNKNOWN; 98 break; 99 } 100 } 101 _hidl_cb(toStatus(status), toHidlVec(legacyRequest), requestType, defaultUrl.c_str()); 102 return Void(); 103 } 104 provideKeyResponse(const hidl_vec<uint8_t> & scope,const hidl_vec<uint8_t> & response,provideKeyResponse_cb _hidl_cb)105 Return<void> DrmPlugin::provideKeyResponse(const hidl_vec<uint8_t>& scope, 106 const hidl_vec<uint8_t>& response, provideKeyResponse_cb _hidl_cb) { 107 108 Vector<uint8_t> keySetId; 109 status_t status = mLegacyPlugin->provideKeyResponse(toVector(scope), 110 toVector(response), keySetId); 111 _hidl_cb(toStatus(status), toHidlVec(keySetId)); 112 return Void(); 113 } 114 removeKeys(const hidl_vec<uint8_t> & sessionId)115 Return<Status> DrmPlugin::removeKeys(const hidl_vec<uint8_t>& sessionId) { 116 return toStatus(mLegacyPlugin->removeKeys(toVector(sessionId))); 117 } 118 restoreKeys(const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & keySetId)119 Return<Status> DrmPlugin::restoreKeys(const hidl_vec<uint8_t>& sessionId, 120 const hidl_vec<uint8_t>& keySetId) { 121 status_t legacyStatus = mLegacyPlugin->restoreKeys(toVector(sessionId), 122 toVector(keySetId)); 123 return toStatus(legacyStatus); 124 } 125 queryKeyStatus(const hidl_vec<uint8_t> & sessionId,queryKeyStatus_cb _hidl_cb)126 Return<void> DrmPlugin::queryKeyStatus(const hidl_vec<uint8_t>& sessionId, 127 queryKeyStatus_cb _hidl_cb) { 128 129 android::KeyedVector<String8, String8> legacyInfoMap; 130 status_t status = mLegacyPlugin->queryKeyStatus(toVector(sessionId), 131 legacyInfoMap); 132 133 Vector<KeyValue> infoMapVec; 134 for (size_t i = 0; i < legacyInfoMap.size(); i++) { 135 KeyValue keyValuePair; 136 keyValuePair.key = legacyInfoMap.keyAt(i); 137 keyValuePair.value = legacyInfoMap.valueAt(i); 138 infoMapVec.push_back(keyValuePair); 139 } 140 _hidl_cb(toStatus(status), toHidlVec(infoMapVec)); 141 return Void(); 142 } 143 getProvisionRequest(const hidl_string & certificateType,const hidl_string & certificateAuthority,getProvisionRequest_cb _hidl_cb)144 Return<void> DrmPlugin::getProvisionRequest( 145 const hidl_string& certificateType, 146 const hidl_string& certificateAuthority, 147 getProvisionRequest_cb _hidl_cb) { 148 149 Vector<uint8_t> legacyRequest; 150 String8 legacyDefaultUrl; 151 status_t status = mLegacyPlugin->getProvisionRequest( 152 String8(certificateType.c_str()), String8(certificateAuthority.c_str()), 153 legacyRequest, legacyDefaultUrl); 154 155 _hidl_cb(toStatus(status), toHidlVec(legacyRequest), 156 hidl_string(legacyDefaultUrl)); 157 return Void(); 158 } 159 provideProvisionResponse(const hidl_vec<uint8_t> & response,provideProvisionResponse_cb _hidl_cb)160 Return<void> DrmPlugin::provideProvisionResponse( 161 const hidl_vec<uint8_t>& response, 162 provideProvisionResponse_cb _hidl_cb) { 163 164 Vector<uint8_t> certificate; 165 Vector<uint8_t> wrappedKey; 166 167 status_t legacyStatus = mLegacyPlugin->provideProvisionResponse( 168 toVector(response), certificate, wrappedKey); 169 170 _hidl_cb(toStatus(legacyStatus), toHidlVec(certificate), 171 toHidlVec(wrappedKey)); 172 return Void(); 173 } 174 getSecureStops(getSecureStops_cb _hidl_cb)175 Return<void> DrmPlugin::getSecureStops(getSecureStops_cb _hidl_cb) { 176 List<Vector<uint8_t> > legacySecureStops; 177 status_t status = mLegacyPlugin->getSecureStops(legacySecureStops); 178 179 Vector<SecureStop> secureStopsVec; 180 List<Vector<uint8_t> >::iterator iter = legacySecureStops.begin(); 181 182 while (iter != legacySecureStops.end()) { 183 SecureStop secureStop; 184 secureStop.opaqueData = toHidlVec(*iter++); 185 secureStopsVec.push_back(secureStop); 186 } 187 188 _hidl_cb(toStatus(status), toHidlVec(secureStopsVec)); 189 return Void(); 190 } 191 getSecureStop(const hidl_vec<uint8_t> & secureStopId,getSecureStop_cb _hidl_cb)192 Return<void> DrmPlugin::getSecureStop(const hidl_vec<uint8_t>& secureStopId, 193 getSecureStop_cb _hidl_cb) { 194 195 Vector<uint8_t> legacySecureStop; 196 status_t status = mLegacyPlugin->getSecureStop(toVector(secureStopId), 197 legacySecureStop); 198 199 SecureStop secureStop; 200 secureStop.opaqueData = toHidlVec(legacySecureStop); 201 _hidl_cb(toStatus(status), secureStop); 202 return Void(); 203 } 204 releaseAllSecureStops()205 Return<Status> DrmPlugin::releaseAllSecureStops() { 206 return toStatus(mLegacyPlugin->releaseAllSecureStops()); 207 } 208 releaseSecureStop(const hidl_vec<uint8_t> & secureStopId)209 Return<Status> DrmPlugin::releaseSecureStop( 210 const hidl_vec<uint8_t>& secureStopId) { 211 status_t legacyStatus = 212 mLegacyPlugin->releaseSecureStops(toVector(secureStopId)); 213 return toStatus(legacyStatus); 214 } 215 getPropertyString(const hidl_string & propertyName,getPropertyString_cb _hidl_cb)216 Return<void> DrmPlugin::getPropertyString(const hidl_string& propertyName, 217 getPropertyString_cb _hidl_cb) { 218 String8 legacyValue; 219 status_t status = mLegacyPlugin->getPropertyString( 220 String8(propertyName.c_str()), legacyValue); 221 _hidl_cb(toStatus(status), legacyValue.c_str()); 222 return Void(); 223 } 224 getPropertyByteArray(const hidl_string & propertyName,getPropertyByteArray_cb _hidl_cb)225 Return<void> DrmPlugin::getPropertyByteArray(const hidl_string& propertyName, 226 getPropertyByteArray_cb _hidl_cb) { 227 Vector<uint8_t> legacyValue; 228 status_t status = mLegacyPlugin->getPropertyByteArray( 229 String8(propertyName.c_str()), legacyValue); 230 _hidl_cb(toStatus(status), toHidlVec(legacyValue)); 231 return Void(); 232 } 233 setPropertyString(const hidl_string & propertyName,const hidl_string & value)234 Return<Status> DrmPlugin::setPropertyString(const hidl_string& propertyName, 235 const hidl_string& value) { 236 status_t legacyStatus = 237 mLegacyPlugin->setPropertyString(String8(propertyName.c_str()), 238 String8(value.c_str())); 239 return toStatus(legacyStatus); 240 } 241 setPropertyByteArray(const hidl_string & propertyName,const hidl_vec<uint8_t> & value)242 Return<Status> DrmPlugin::setPropertyByteArray( 243 const hidl_string& propertyName, const hidl_vec<uint8_t>& value) { 244 status_t legacyStatus = 245 mLegacyPlugin->setPropertyByteArray(String8(propertyName.c_str()), 246 toVector(value)); 247 return toStatus(legacyStatus); 248 } 249 setCipherAlgorithm(const hidl_vec<uint8_t> & sessionId,const hidl_string & algorithm)250 Return<Status> DrmPlugin::setCipherAlgorithm( 251 const hidl_vec<uint8_t>& sessionId, const hidl_string& algorithm) { 252 status_t legacyStatus = 253 mLegacyPlugin->setCipherAlgorithm(toVector(sessionId), 254 String8(algorithm.c_str())); 255 return toStatus(legacyStatus); 256 } 257 setMacAlgorithm(const hidl_vec<uint8_t> & sessionId,const hidl_string & algorithm)258 Return<Status> DrmPlugin::setMacAlgorithm( 259 const hidl_vec<uint8_t>& sessionId, const hidl_string& algorithm) { 260 status_t legacyStatus = 261 mLegacyPlugin->setMacAlgorithm(toVector(sessionId), 262 String8(algorithm.c_str())); 263 return toStatus(legacyStatus); 264 } 265 encrypt(const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & keyId,const hidl_vec<uint8_t> & input,const hidl_vec<uint8_t> & iv,encrypt_cb _hidl_cb)266 Return<void> DrmPlugin::encrypt(const hidl_vec<uint8_t>& sessionId, 267 const hidl_vec<uint8_t>& keyId, const hidl_vec<uint8_t>& input, 268 const hidl_vec<uint8_t>& iv, encrypt_cb _hidl_cb) { 269 270 Vector<uint8_t> legacyOutput; 271 status_t status = mLegacyPlugin->encrypt(toVector(sessionId), 272 toVector(keyId), toVector(input), toVector(iv), legacyOutput); 273 _hidl_cb(toStatus(status), toHidlVec(legacyOutput)); 274 return Void(); 275 } 276 decrypt(const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & keyId,const hidl_vec<uint8_t> & input,const hidl_vec<uint8_t> & iv,decrypt_cb _hidl_cb)277 Return<void> DrmPlugin::decrypt(const hidl_vec<uint8_t>& sessionId, 278 const hidl_vec<uint8_t>& keyId, const hidl_vec<uint8_t>& input, 279 const hidl_vec<uint8_t>& iv, decrypt_cb _hidl_cb) { 280 281 Vector<uint8_t> legacyOutput; 282 status_t status = mLegacyPlugin->decrypt(toVector(sessionId), 283 toVector(keyId), toVector(input), toVector(iv), legacyOutput); 284 _hidl_cb(toStatus(status), toHidlVec(legacyOutput)); 285 return Void(); 286 } 287 sign(const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & keyId,const hidl_vec<uint8_t> & message,sign_cb _hidl_cb)288 Return<void> DrmPlugin::sign(const hidl_vec<uint8_t>& sessionId, 289 const hidl_vec<uint8_t>& keyId, const hidl_vec<uint8_t>& message, 290 sign_cb _hidl_cb) { 291 Vector<uint8_t> legacySignature; 292 status_t status = mLegacyPlugin->sign(toVector(sessionId), 293 toVector(keyId), toVector(message), legacySignature); 294 _hidl_cb(toStatus(status), toHidlVec(legacySignature)); 295 return Void(); 296 } 297 verify(const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & keyId,const hidl_vec<uint8_t> & message,const hidl_vec<uint8_t> & signature,verify_cb _hidl_cb)298 Return<void> DrmPlugin::verify(const hidl_vec<uint8_t>& sessionId, 299 const hidl_vec<uint8_t>& keyId, const hidl_vec<uint8_t>& message, 300 const hidl_vec<uint8_t>& signature, verify_cb _hidl_cb) { 301 302 bool match; 303 status_t status = mLegacyPlugin->verify(toVector(sessionId), 304 toVector(keyId), toVector(message), toVector(signature), 305 match); 306 _hidl_cb(toStatus(status), match); 307 return Void(); 308 } 309 signRSA(const hidl_vec<uint8_t> & sessionId,const hidl_string & algorithm,const hidl_vec<uint8_t> & message,const hidl_vec<uint8_t> & wrappedKey,signRSA_cb _hidl_cb)310 Return<void> DrmPlugin::signRSA(const hidl_vec<uint8_t>& sessionId, 311 const hidl_string& algorithm, const hidl_vec<uint8_t>& message, 312 const hidl_vec<uint8_t>& wrappedKey, signRSA_cb _hidl_cb) { 313 314 Vector<uint8_t> legacySignature; 315 status_t status = mLegacyPlugin->signRSA(toVector(sessionId), 316 String8(algorithm.c_str()), toVector(message), toVector(wrappedKey), 317 legacySignature); 318 _hidl_cb(toStatus(status), toHidlVec(legacySignature)); 319 return Void(); 320 } 321 setListener(const sp<IDrmPluginListener> & listener)322 Return<void> DrmPlugin::setListener(const sp<IDrmPluginListener>& listener) { 323 mListener = listener; 324 mLegacyPlugin->setListener(listener == NULL ? NULL : this); 325 return Void(); 326 } 327 sendEvent(EventType eventType,const hidl_vec<uint8_t> & sessionId,const hidl_vec<uint8_t> & data)328 Return<void> DrmPlugin::sendEvent(EventType eventType, 329 const hidl_vec<uint8_t>& sessionId, const hidl_vec<uint8_t>& data) { 330 if (mListener != nullptr) { 331 mListener->sendEvent(eventType, sessionId, data); 332 } 333 return Void(); 334 } 335 sendExpirationUpdate(const hidl_vec<uint8_t> & sessionId,int64_t expiryTimeInMS)336 Return<void> DrmPlugin::sendExpirationUpdate( 337 const hidl_vec<uint8_t>& sessionId, int64_t expiryTimeInMS) { 338 if (mListener != nullptr) { 339 mListener->sendExpirationUpdate(sessionId, expiryTimeInMS); 340 } 341 return Void(); 342 } 343 sendKeysChange(const hidl_vec<uint8_t> & sessionId,const hidl_vec<KeyStatus> & keyStatusList,bool hasNewUsableKey)344 Return<void> DrmPlugin::sendKeysChange(const hidl_vec<uint8_t>& sessionId, 345 const hidl_vec<KeyStatus>& keyStatusList, bool hasNewUsableKey) { 346 if (mListener != nullptr) { 347 mListener->sendKeysChange(sessionId, keyStatusList, hasNewUsableKey); 348 } 349 return Void(); 350 } 351 352 353 // Methods from android::DrmPluginListener 354 sendEvent(android::DrmPlugin::EventType legacyEventType,int,Vector<uint8_t> const * sessionId,Vector<uint8_t> const * data)355 void DrmPlugin::sendEvent(android::DrmPlugin::EventType legacyEventType, 356 int /*unused*/, Vector<uint8_t> const *sessionId, 357 Vector<uint8_t> const *data) { 358 359 EventType eventType; 360 bool sendEvent = true; 361 switch(legacyEventType) { 362 case android::DrmPlugin::kDrmPluginEventProvisionRequired: 363 eventType = EventType::PROVISION_REQUIRED; 364 break; 365 case android::DrmPlugin::kDrmPluginEventKeyNeeded: 366 eventType = EventType::KEY_NEEDED; 367 break; 368 case android::DrmPlugin::kDrmPluginEventKeyExpired: 369 eventType = EventType::KEY_EXPIRED; 370 break; 371 case android::DrmPlugin::kDrmPluginEventVendorDefined: 372 eventType = EventType::VENDOR_DEFINED; 373 break; 374 case android::DrmPlugin::kDrmPluginEventSessionReclaimed: 375 eventType = EventType::SESSION_RECLAIMED; 376 break; 377 default: 378 sendEvent = false; 379 break; 380 } 381 if (sendEvent) { 382 Vector<uint8_t> emptyVector; 383 mListener->sendEvent(eventType, 384 toHidlVec(sessionId == NULL ? emptyVector: *sessionId), 385 toHidlVec(data == NULL ? emptyVector: *data)); 386 } 387 } 388 sendExpirationUpdate(Vector<uint8_t> const * sessionId,int64_t expiryTimeInMS)389 void DrmPlugin::sendExpirationUpdate(Vector<uint8_t> const *sessionId, 390 int64_t expiryTimeInMS) { 391 mListener->sendExpirationUpdate(toHidlVec(*sessionId), expiryTimeInMS); 392 } 393 sendKeysChange(Vector<uint8_t> const * sessionId,Vector<android::DrmPlugin::KeyStatus> const * legacyKeyStatusList,bool hasNewUsableKey)394 void DrmPlugin::sendKeysChange(Vector<uint8_t> const *sessionId, 395 Vector<android::DrmPlugin::KeyStatus> const *legacyKeyStatusList, 396 bool hasNewUsableKey) { 397 398 Vector<KeyStatus> keyStatusVec; 399 for (size_t i = 0; i < legacyKeyStatusList->size(); i++) { 400 const android::DrmPlugin::KeyStatus &legacyKeyStatus = 401 legacyKeyStatusList->itemAt(i); 402 403 KeyStatus keyStatus; 404 405 switch(legacyKeyStatus.mType) { 406 case android::DrmPlugin::kKeyStatusType_Usable: 407 keyStatus.type = KeyStatusType::USABLE; 408 break; 409 case android::DrmPlugin::kKeyStatusType_Expired: 410 keyStatus.type = KeyStatusType::EXPIRED; 411 break; 412 case android::DrmPlugin::kKeyStatusType_OutputNotAllowed: 413 keyStatus.type = KeyStatusType::OUTPUTNOTALLOWED; 414 break; 415 case android::DrmPlugin::kKeyStatusType_StatusPending: 416 keyStatus.type = KeyStatusType::STATUSPENDING; 417 break; 418 case android::DrmPlugin::kKeyStatusType_InternalError: 419 default: 420 keyStatus.type = KeyStatusType::INTERNALERROR; 421 break; 422 } 423 424 keyStatus.keyId = toHidlVec(legacyKeyStatus.mKeyId); 425 keyStatusVec.push_back(keyStatus); 426 } 427 mListener->sendKeysChange(toHidlVec(*sessionId), 428 toHidlVec(keyStatusVec), hasNewUsableKey); 429 } 430 431 } // namespace implementation 432 } // namespace V1_0 433 } // namespace drm 434 } // namespace hardware 435 } // namespace android 436