import exynos 7570 bsp
[GitHub/LineageOS/android_hardware_samsung_slsi_exynos7580.git] / mobicore / rootpa / Code / Common / pacmp3.c
1 /*
2 * Copyright (c) 2013 TRUSTONIC LIMITED
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 *
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 *
15 * 3. Neither the name of the TRUSTONIC LIMITED nor the names of its
16 * contributors may be used to endorse or promote products derived from
17 * this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
23 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
24 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
25 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
26 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
27 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
28 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
29 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31
32 #include <string.h>
33 #include <stdlib.h>
34 #include <wrapper.h>
35 #include <TlCm/3.0/cmpMap.h>
36 #include <TlCm/tlCmApiCommon.h>
37
38 #include "tools.h"
39 #include "logging.h"
40 #include "rootpaErrors.h"
41 #include "pacmtl.h"
42 #include "pacmp3.h"
43 #include "registry.h"
44
45 static mcSpid_t spid_;
46 static mcUuid_t tltUuid_;
47 static CallbackFunctionP callbackP_=NULL;
48
49 void setCallbackP(CallbackFunctionP callbackP)
50 {
51 callbackP_=callbackP;
52 }
53
54 // recovery from factory reset
55 bool factoryResetAssumed()
56 {
57 uint32_t contSize=0;
58 void* containerP=NULL;
59 mcResult_t result1=MC_DRV_OK;
60 mcResult_t result2=MC_DRV_OK;
61
62 if((result1=regReadAuthToken((AUTHTOKENCONTAINERP*)&containerP, &contSize))==MC_DRV_OK)
63 {
64 free(containerP);
65 return false;
66 }
67
68 if((result2=regReadRoot((ROOTCONTAINERP*)&containerP, &contSize))==MC_DRV_OK)
69 {
70 free(containerP);
71 return false;
72 }
73
74 // if neither root container, nor auth token container exists, we assume that factory reset has been performed.
75 if(MC_DRV_ERR_INVALID_DEVICE_FILE==result1 && MC_DRV_ERR_INVALID_DEVICE_FILE==result2)
76 {
77 LOGD("factoryResetAssumed returning true");
78 return true;
79 }
80
81 return false;
82 }
83 // recovery from factory reset
84
85 /*
86 */
87 uint32_t sizeOfCmp()
88 {
89 return (sizeof(cmp_t)); // could also use CMP_SIZE, but this way we only allocate the amount we really need
90 }
91
92 cmpCommandId_t getCmpCommandId(const uint8_t* commandP)
93 {
94 if(NULL==commandP) return 0xFFFFFFFF;
95 return ((cmpCommandHeaderMap_t*)commandP)->commandId;
96 }
97
98
99 uint32_t getCmpReturnCode(const uint8_t* cmpMsgP)
100 {
101 return ((cmpResponseHeader_t*)cmpMsgP)->returnCode;
102 }
103
104 rootpaerror_t allocateResponseBuffer(CmpMessage* responseP, CMTHANDLE handle )
105 {
106 uint32_t elementIndex=1;
107 uint32_t offset=0;
108
109 if(!getRspElementInfo(&elementIndex, handle, &offset, &(responseP->length)))
110 {
111 return ROOTPA_ERROR_INTERNAL;
112 }
113 LOGD("allocateResponseBuffer, size %d", responseP->length);
114 responseP->contentP=(uint8_t*)malloc(responseP->length);
115 if(responseP->contentP==NULL) return ROOTPA_ERROR_OUT_OF_MEMORY;
116 return ROOTPA_OK;
117 }
118
119 bool ensureMappedBufferSize(CMTHANDLE handle, uint32_t neededSize)
120 {
121 if( neededSize > handle->mappedSize)
122 {
123 uint8_t* newMappedP = (uint8_t*)realloc(handle->mappedP, neededSize);
124 if(!newMappedP)
125 {
126 LOGE("ensureMappedBufferSize, unable to allocate more memory %d", neededSize);
127 return false;
128 }
129 handle->mappedP = newMappedP;
130 }
131 return true;
132 }
133
134 rootpaerror_t addAuthTokenContainer(uint32_t* indexP, uint32_t* offsetP, CMTHANDLE handle, mcResult_t* mcRetP)
135 {
136 rootpaerror_t ret=ROOTPA_ERROR_OUT_OF_MEMORY;
137 AUTHTOKENCONTAINERP authTokenP = NULL;
138 uint32_t contSize=0;
139
140 if((*mcRetP=regReadAuthToken(&authTokenP, &contSize))==MC_DRV_OK)
141 {
142 if(ensureMappedBufferSize(handle, (*offsetP) + contSize))
143 {
144 memcpy(handle->mappedP+(*offsetP), authTokenP, contSize);
145 setCmdElementInfo(indexP, handle->wsmP, offsetP, contSize);
146 ret=ROOTPA_OK;
147 }
148 }
149 else if (MC_DRV_ERR_INVALID_DEVICE_FILE==*mcRetP)
150 {
151 ret=ROOTPA_ERROR_REGISTRY_OBJECT_NOT_AVAILABLE;
152 }
153 else
154 {
155 ret=ROOTPA_ERROR_REGISTRY;
156 }
157 free(authTokenP);
158 return ret;
159 }
160
161 rootpaerror_t addRootContainer(uint32_t* indexP, uint32_t* offsetP, CMTHANDLE handle, mcResult_t* mcRetP)
162 {
163 rootpaerror_t ret=ROOTPA_ERROR_OUT_OF_MEMORY;
164 ROOTCONTAINERP rootP = NULL;
165 uint32_t contSize=0;
166
167 if((*mcRetP=regReadRoot(&rootP, &contSize))==MC_DRV_OK)
168 {
169 if(ensureMappedBufferSize(handle, (*offsetP) + contSize))
170 {
171 memcpy(handle->mappedP+(*offsetP), rootP, contSize);
172 setCmdElementInfo(indexP, handle->wsmP, offsetP, contSize);
173 ret=ROOTPA_OK;
174 }
175 }
176 else if (MC_DRV_ERR_INVALID_DEVICE_FILE==*mcRetP)
177 {
178 ret=ROOTPA_ERROR_REGISTRY_OBJECT_NOT_AVAILABLE;
179 }
180 else
181 {
182 ret=ROOTPA_ERROR_REGISTRY;
183 }
184 free(rootP);
185 return ret;
186 }
187
188 rootpaerror_t addSpContainer(uint32_t* indexP, uint32_t* offsetP, mcSpid_t spid, CMTHANDLE handle, mcResult_t* mcRetP)
189 {
190 rootpaerror_t ret=ROOTPA_ERROR_OUT_OF_MEMORY;
191 SPCONTAINERP spP = NULL;
192 uint32_t contSize=0;
193
194 if((*mcRetP=regReadSp(spid, &spP, &contSize))==MC_DRV_OK)
195 {
196 if(ensureMappedBufferSize(handle, (*offsetP) + contSize))
197 {
198 memcpy(handle->mappedP+(*offsetP),spP,contSize);
199 setCmdElementInfo(indexP, handle->wsmP, offsetP, contSize);
200 ret=ROOTPA_OK;
201 }
202 }
203 else if (MC_DRV_ERR_INVALID_DEVICE_FILE==*mcRetP)
204 {
205 ret=ROOTPA_ERROR_REGISTRY_OBJECT_NOT_AVAILABLE;
206 }
207 else
208 {
209 ret=ROOTPA_ERROR_REGISTRY;
210 }
211 free(spP);
212 return ret;
213 }
214
215
216 rootpaerror_t addTltContainer(uint32_t* indexP, uint32_t* offsetP, const mcUuid_t* uuidP, mcSpid_t spid, CMTHANDLE handle, mcResult_t* mcRetP)
217 {
218 rootpaerror_t ret=ROOTPA_ERROR_OUT_OF_MEMORY;
219 TLTCONTAINERP tltP = NULL;
220 uint32_t contSize=0;
221
222 if((*mcRetP=regReadTlt(uuidP, &tltP, &contSize, spid))==MC_DRV_OK)
223 {
224 if(ensureMappedBufferSize(handle, (*offsetP) + contSize))
225 {
226 memcpy(handle->mappedP+(*offsetP),tltP,contSize);
227 setCmdElementInfo(indexP, handle->wsmP, offsetP, contSize);
228 ret=ROOTPA_OK;
229 }
230 }
231 else if (MC_DRV_ERR_INVALID_DEVICE_FILE==*mcRetP)
232 {
233 ret=ROOTPA_ERROR_REGISTRY_OBJECT_NOT_AVAILABLE;
234 }
235 else
236 {
237 ret=ROOTPA_ERROR_REGISTRY;
238 }
239
240 free(tltP);
241 return ret;
242 }
243
244
245 rootpaerror_t prepareCommand(cmpCommandId_t commandId, CmpMessage* inCommandP, CMTHANDLE handle, CmpMessage* responseP)
246 {
247 uint8_t* outCommandP =handle->mappedP;
248
249 uint32_t offset=0;
250 uint32_t elementIndex=1;
251 rootpaerror_t ret=ROOTPA_OK;
252 mcResult_t mcRet=MC_DRV_OK;
253 LOGI("prepareCommand command id %d length %d", commandId, inCommandP->length); // this is LOGI level on purpose to indicate that CMP command has reached RootPA
254
255 memset(handle->wsmP,0,sizeOfCmp());
256
257 setCmdMapInfo(handle->wsmP, &handle->mapInfo);
258 setCmdCmpVersionAndCmdId(handle->wsmP, commandId);
259 setCmdElementInfo(&elementIndex, handle->wsmP, &offset, inCommandP->length);
260 if(ensureMappedBufferSize(handle, inCommandP->length))
261 {
262 memcpy(handle->mappedP, inCommandP->contentP, inCommandP->length);
263 }
264 else
265 {
266 responseP->hdr.ret=ROOTPA_ERROR_OUT_OF_MEMORY;
267 return ROOTPA_ERROR_OUT_OF_MEMORY;
268 }
269 switch(commandId)
270 {
271 case MC_CMP_CMD_BEGIN_SOC_AUTHENTICATION:
272 if (callbackP_) callbackP_(AUTHENTICATING_SOC, ROOTPA_OK, NULL);
273 ret=addAuthTokenContainer(&elementIndex, &offset, handle, &mcRet);
274 break;
275
276 case MC_CMP_CMD_BEGIN_ROOT_AUTHENTICATION:
277 if (callbackP_) callbackP_(AUTHENTICATING_ROOT, ROOTPA_OK, NULL);
278 ret=addRootContainer(&elementIndex, &offset, handle, &mcRet);
279 break;
280
281 case MC_CMP_CMD_BEGIN_SP_AUTHENTICATION:
282 ret=addRootContainer(&elementIndex, &offset, handle, &mcRet);
283 if(ROOTPA_OK==ret)
284 {
285 mcSpid_t spid=((cmpCmdBeginSpAuthentication_t*)outCommandP)->cmd.spid;
286 ret=addSpContainer(&elementIndex, &offset, spid, handle, &mcRet);
287 }
288 break;
289 case MC_CMP_CMD_ROOT_CONT_REGISTER_ACTIVATE:
290 if (callbackP_) callbackP_(CREATING_ROOT_CONTAINER, ROOTPA_OK, NULL);
291 break;
292
293 case MC_CMP_CMD_ROOT_CONT_UNREGISTER:
294 if (callbackP_) callbackP_(UNREGISTERING_ROOT_CONTAINER, ROOTPA_OK, NULL);
295 break;
296
297 case MC_CMP_CMD_SP_CONT_ACTIVATE:
298 spid_=((cmpCmdSpContActivate_t*)outCommandP)->cmd.sdata.spid;
299 break;
300 case MC_CMP_CMD_SP_CONT_LOCK_BY_ROOT:
301 spid_=((cmpCmdSpContLockByRoot_t*)outCommandP)->cmd.sdata.spid;
302 ret=addSpContainer(&elementIndex, &offset, spid_, handle, &mcRet);
303 break;
304 case MC_CMP_CMD_SP_CONT_LOCK_BY_SP :
305 spid_=((cmpCmdSpContLockBySp_t*)outCommandP)->cmd.sdata.spid;
306 break;
307 case MC_CMP_CMD_SP_CONT_REGISTER:
308 if (callbackP_) callbackP_(CREATING_SP_CONTAINER, ROOTPA_OK, NULL);
309 spid_=((cmpCmdSpContRegister_t*)outCommandP)->cmd.sdata.spid;
310 break;
311 case MC_CMP_CMD_SP_CONT_REGISTER_ACTIVATE :
312 if (callbackP_) callbackP_(CREATING_SP_CONTAINER, ROOTPA_OK, NULL);
313 spid_=((cmpCmdSpContRegister_t*)outCommandP)->cmd.sdata.spid;
314 break;
315 case MC_CMP_CMD_SP_CONT_UNLOCK_BY_ROOT:
316 spid_=((cmpCmdSpContUnlockByRoot_t*)outCommandP)->cmd.sdata.spid;
317 ret=addSpContainer(&elementIndex, &offset, spid_, handle, &mcRet);
318 break;
319 case MC_CMP_CMD_SP_CONT_UNLOCK_BY_SP :
320 spid_=((cmpCmdSpContUnlockBySp_t*)outCommandP)->cmd.sdata.spid;
321 break;
322 case MC_CMP_CMD_SP_CONT_UNREGISTER:
323 spid_=((cmpCmdSpContUnregister_t*)outCommandP)->cmd.sdata.spid;
324 break;
325 case MC_CMP_CMD_TLT_CONT_ACTIVATE:
326 spid_=((cmpCmdTltContActivate_t*)outCommandP)->cmd.sdata.spid;
327 memcpy(&tltUuid_,&((cmpCmdTltContActivate_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
328 ret=addTltContainer(&elementIndex, &offset, &tltUuid_, spid_, handle, &mcRet);
329 break;
330 case MC_CMP_CMD_TLT_CONT_LOCK_BY_SP:
331 spid_=((cmpCmdTltContLockBySp_t*)outCommandP)->cmd.sdata.spid;
332 memcpy(&tltUuid_,&((cmpCmdTltContLockBySp_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
333 ret=addTltContainer(&elementIndex, &offset, &tltUuid_, spid_, handle, &mcRet);
334 break;
335 case MC_CMP_CMD_TLT_CONT_PERSONALIZE:
336 ret=addTltContainer(&elementIndex, &offset, &((cmpCmdTltContPersonalize_t*)outCommandP)->cmd.sdata.uuid,
337 ((cmpCmdTltContPersonalize_t*)outCommandP)->cmd.sdata.spid,
338 handle, &mcRet);
339 break;
340 case MC_CMP_CMD_TLT_CONT_REGISTER:
341 spid_=((cmpCmdTltContRegister_t*)outCommandP)->cmd.sdata.spid;
342 memcpy(&tltUuid_,&((cmpCmdTltContRegister_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
343 break;
344 case MC_CMP_CMD_TLT_CONT_REGISTER_ACTIVATE:
345 spid_=((cmpCmdTltContRegisterActivate_t*)outCommandP)->cmd.sdata.spid;
346 memcpy(&tltUuid_,&((cmpCmdTltContRegisterActivate_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
347 break;
348 case MC_CMP_CMD_TLT_CONT_UNLOCK_BY_SP:
349 spid_=((cmpCmdTltContUnlockBySp_t*)outCommandP)->cmd.sdata.spid;
350 memcpy(&tltUuid_,&((cmpCmdTltContUnlockBySp_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
351 ret=addTltContainer(&elementIndex, &offset, &tltUuid_, spid_, handle, &mcRet);
352 break;
353 case MC_CMP_CMD_TLT_CONT_UNREGISTER:
354 spid_=((cmpCmdTltContUnlockBySp_t*)outCommandP)->cmd.sdata.spid;
355 memcpy(&tltUuid_,&((cmpCmdTltContUnlockBySp_t*)outCommandP)->cmd.sdata.uuid, sizeof(mcUuid_t));
356 break;
357 default:
358 // nothing extra to do, just return ret at the end of function
359 break;
360
361 }
362 responseP->hdr.ret=ret;
363 responseP->hdr.intRet=mcRet;
364 return ret;
365 }
366
367
368 mcResult_t storeContainers(cmpCommandId_t commandId, CMTHANDLE handle, uint32_t elementIndex, uint32_t offset)
369 {
370 mcResult_t mcRet=MC_DRV_OK;
371 uint32_t length=0;
372 LOGD(">>pacmp3 storeContainers for %d element %d offset %d", commandId, elementIndex, offset);
373
374 // store the containers when needed
375 switch(commandId)
376 {
377 case MC_CMP_CMD_GENERATE_AUTH_TOKEN:
378 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
379 {
380 mcRet=regWriteAuthToken((AUTHTOKENCONTAINERP) (handle->mappedP+offset), length);
381 }
382 else
383 {
384 mcRet=-1;
385 }
386 break;
387
388 case MC_CMP_CMD_ROOT_CONT_REGISTER_ACTIVATE:
389 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
390 {
391 mcRet=regWriteRoot((ROOTCONTAINERP) (handle->mappedP+offset), length);
392 }
393 else
394 {
395 mcRet=-1;
396 }
397
398 if(MC_DRV_OK==mcRet)
399 {
400 mcSoAuthTokenCont_t* authTokenP=NULL;
401 uint32_t authTokenSize=0;
402
403 mcRet=regReadAuthToken(&authTokenP, &authTokenSize);
404 if(mcRet!=MC_DRV_OK)
405 {
406 LOGE("pacmp3 storeContainers for %d regReadAuthToken failed %d, since this was only precaution, continuing", commandId, mcRet);
407 }
408 mcRet=regDeleteAuthToken();
409 if(mcRet!=MC_DRV_OK)
410 {
411 LOGE("pacmp3 storeContainers for %d regDeleteAuthToken failed %d, trying to recover", commandId, mcRet);
412 // try to recover, remove root, but only if there is auth token stored
413 if(authTokenP)
414 {
415 mcRet=regWriteAuthToken((AUTHTOKENCONTAINERP) authTokenP, authTokenSize); // trying to be failsafe here. Deleting failed but rewriting the token anyway
416 if(MC_DRV_OK==mcRet)
417 {
418 regCleanupRoot(); // since we were able to restore authToken we delete root (due to an error in registry handling)
419 }
420 }
421 }
422 free(authTokenP);
423 }
424 else
425 {
426 LOGE("pacmp3 storeContainers for %d regWriteRoot failed %d", commandId, mcRet);
427 }
428 break;
429
430
431 case MC_CMP_CMD_ROOT_CONT_LOCK_BY_ROOT:
432 case MC_CMP_CMD_ROOT_CONT_UNLOCK_BY_ROOT:
433 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
434 {
435 mcRet=regWriteRoot((ROOTCONTAINERP) (handle->mappedP+offset), length);
436 }
437 else
438 {
439 mcRet=-1;
440 }
441
442 break;
443
444 case MC_CMP_CMD_ROOT_CONT_UNREGISTER:
445 mcRet=regCleanupRoot();
446 break;
447
448 case MC_CMP_CMD_SP_CONT_UNLOCK_BY_ROOT:
449 case MC_CMP_CMD_SP_CONT_UNLOCK_BY_SP:
450 case MC_CMP_CMD_SP_CONT_ACTIVATE:
451 case MC_CMP_CMD_SP_CONT_LOCK_BY_ROOT:
452 case MC_CMP_CMD_SP_CONT_LOCK_BY_SP:
453 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
454 {
455 mcRet=regWriteSp(spid_, (SPCONTAINERP) (handle->mappedP+offset), length);
456 }
457 else
458 {
459 mcRet=-1;
460 }
461
462 break;
463
464 case MC_CMP_CMD_SP_CONT_REGISTER:
465 case MC_CMP_CMD_SP_CONT_REGISTER_ACTIVATE:
466 {
467 // Root container is in the buffer first, that is why we read it first
468 // we write it last since if SP container writing fails we do not want
469 // to write root container
470 uint32_t rootLength=0;
471 ROOTCONTAINERP rootP=NULL;
472 if(getRspElementInfo(&elementIndex, handle, &offset, &rootLength))
473 {
474 rootP=(ROOTCONTAINERP) (handle->mappedP+offset);
475 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
476 {
477 mcRet=regWriteSp(spid_, (SPCONTAINERP) (handle->mappedP+offset), length);
478 }
479 else
480 {
481 mcRet=-1;
482 }
483 }
484 else
485 {
486 mcRet=-1;
487 }
488
489 if(MC_DRV_OK==mcRet)
490 {
491 mcRet=regWriteRoot(rootP, rootLength);
492 }
493 else
494 {
495 LOGE("pacmp3 storeContainers for %d regWriteSp failed %d", commandId, mcRet);
496 }
497 break;
498
499 }
500 case MC_CMP_CMD_SP_CONT_UNREGISTER:
501 mcRet=regCleanupSp(spid_);
502 if(MC_DRV_OK!=mcRet)
503 {
504 LOGE("pacmp3 storeContainers for %d regCleanupSp failed %d, , still attempting storing root", commandId, mcRet);
505 }
506
507 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
508 {
509 mcRet=regWriteRoot((ROOTCONTAINERP) (handle->mappedP+offset), length);
510 }
511 else
512 {
513 mcRet=-1;
514 }
515
516 break;
517
518
519 case MC_CMP_CMD_TLT_CONT_REGISTER:
520 case MC_CMP_CMD_TLT_CONT_REGISTER_ACTIVATE:
521 {
522 // SP container is in the buffer first, that is why we read it first
523 // we write it last since if TLT container writing fails we do not want
524 // to write SP container
525 uint32_t spLength=0;
526 SPCONTAINERP spP=NULL;
527 if(getRspElementInfo(&elementIndex, handle, &offset, &spLength))
528 {
529 spP=(SPCONTAINERP) (handle->mappedP+offset);
530 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
531 {
532 mcRet=regWriteTlt(&tltUuid_,(TLTCONTAINERP) (handle->mappedP+offset), length, spid_);
533 }
534 else
535 {
536 mcRet=-1;
537 }
538 }
539 else
540 {
541 mcRet=-1;
542 }
543
544 if(MC_DRV_OK==mcRet)
545 {
546 mcRet=regWriteSp(spid_, spP, spLength);
547 if(MC_DRV_OK!=mcRet)
548 {
549 LOGE("pacmp3 storeContainers for %d regWriteSp failed %d", commandId, mcRet);
550 regCleanupTlt(&tltUuid_, spid_);
551 }
552 }
553 else
554 {
555 LOGE("pacmp3 storeContainers for %d regWriteTlt failed %d", commandId, mcRet);
556 }
557 break;
558
559 }
560 case MC_CMP_CMD_TLT_CONT_ACTIVATE:
561 case MC_CMP_CMD_TLT_CONT_LOCK_BY_SP:
562 case MC_CMP_CMD_TLT_CONT_UNLOCK_BY_SP:
563 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
564 {
565 mcRet=regWriteTlt(&tltUuid_,(TLTCONTAINERP) (handle->mappedP+offset), length, spid_);
566 }
567 else
568 {
569 mcRet=-1;
570 }
571
572 break;
573
574 case MC_CMP_CMD_TLT_CONT_UNREGISTER:
575 mcRet=regCleanupTlt(&tltUuid_, spid_);
576 if(MC_DRV_OK!=mcRet)
577 {
578 LOGE("pacmp3 storeContainers for %d regCleanupTlt failed %d, still attempting storing sp", commandId, mcRet);
579 }
580
581 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
582 {
583 mcRet=regWriteSp(spid_, (SPCONTAINERP) (handle->mappedP+offset), length);
584 if(MC_DRV_OK!=mcRet)
585 {
586 LOGE("pacmp3 storeContainers for %d regWriteSp failed %d", commandId, mcRet);
587 }
588 }
589 else
590 {
591 mcRet=-1;
592 }
593
594 break;
595
596 default:
597 LOGD("pacmp3 storeContainers nothing to store");
598 // nothing to do
599 break;
600 }
601 LOGD("<<pacmp3 storeContainers %d %d", commandId, mcRet);
602 return mcRet;
603 }
604 /**
605 handleResponse stores the container received in response and copies the response to the buffer to be returned
606 to the client Note that the container is not store id cmtl returned an error, but the content of the response is
607 returned to the client.
608 */
609 rootpaerror_t handleResponse(cmpCommandId_t commandId, CmpMessage* outResponseP, CMTHANDLE handle)
610 {
611 mcResult_t mcRet=MC_DRV_OK;
612 rootpaerror_t ret=ROOTPA_OK;
613 uint32_t elementIndex=1;
614 uint32_t offset=0;
615 uint32_t length=0;
616
617 LOGD(">>handleResponse for command %d ", commandId);
618
619 if(isValidResponseTo(commandId, handle->wsmP)==false)
620 {
621 LOGE("no valid response to %d", commandId);
622 outResponseP->hdr.ret=ROOTPA_ERROR_COMMAND_EXECUTION;
623 return ROOTPA_ERROR_COMMAND_EXECUTION;
624 }
625
626 ret=allocateResponseBuffer(outResponseP, handle);
627
628 if(ROOTPA_OK==ret)
629 {
630 if(getRspElementInfo(&elementIndex, handle, &offset, &length))
631 {
632 memcpy(outResponseP->contentP, handle->mappedP+offset, length );
633 }
634 else
635 {
636 return ROOTPA_ERROR_INTERNAL;
637 }
638
639 if (getCmpReturnCode(handle->mappedP)!=SUCCESSFUL) // this checking is here since we want the response to be returned even in case of CMP error
640 {
641 LOGE("executeOneCmpCommand: command execution failed 0x%x", getCmpReturnCode(handle->mappedP));
642 outResponseP->hdr.intRet=getCmpReturnCode(handle->mappedP);
643 return ROOTPA_ERROR_COMMAND_EXECUTION;
644 }
645 }
646 else
647 {
648 outResponseP->hdr.ret=ret;
649 LOGE("executeOneCmpCommand: response buffer allocation failed %d (0x%x)", ret, handle->lasterror);
650 return ret;
651 }
652
653 mcRet=storeContainers(commandId, handle, elementIndex, offset);
654
655 if(mcRet != MC_DRV_OK)
656 {
657 LOGE("pacmp3 handleResponse for %d registry failed %d", commandId, mcRet);
658 if((mcResult_t)-1==mcRet)
659 {
660 ret = ROOTPA_ERROR_INTERNAL;
661 }
662 else
663 {
664 ret = ROOTPA_ERROR_REGISTRY;
665 }
666 if(0==outResponseP->hdr.intRet)
667 {
668 outResponseP->hdr.intRet=mcRet;
669 }
670 outResponseP->hdr.ret=ret;
671 }
672 LOGD("<<handleResponse returning %d ", ret);
673 return ret;
674 }