19066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/*
29066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project
39066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
49066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
59066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * you may not use this file except in compliance with the License.
69066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * You may obtain a copy of the License at
79066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
89066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
99066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project *
109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * See the License for the specific language governing permissions and
149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project * limitations under the License.
159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project */
169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <drm_rights_manager.h>
189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <drm_inner.h>
199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <drm_file.h>
209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project#include <drm_i18n.h>
219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic int32_t drm_getString(uint8_t* string, int32_t len, int32_t handle)
239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t i;
259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (i = 0; i < len; i++) {
279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_read(handle, &string[i], 1))
289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (string[i] == '\n') {
309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            string[i + 1] = '\0';
319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            break;
329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic int32_t drm_putString(uint8_t* string, int32_t handle)
389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t i = 0;
409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (i = 0;; i++) {
429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (string[i] == '\0')
439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            break;
449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_write(handle, &string[i], 1))
459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic int32_t drm_writeToUidTxt(uint8_t* Uid, int32_t* id)
519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t length;
539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t i;
549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t idStr[8];
559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t idMax;
569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t(*uidStr)[256];
579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN];
589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen;
599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t handle;
619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t fileRes;
629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (*id < 1)
649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* convert in ucs2 */
679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen(DRM_UID_FILE_PATH);
689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        (uint8_t *)DRM_UID_FILE_PATH,
709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_READ,
779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes) {
799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_open(nameUcs2,
809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_WRITE,
829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_write(handle, (uint8_t *)"0\n", 2);
849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_open(nameUcs2,
869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_READ,
889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (!drm_getString(idStr, 8, handle)) {
929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    idMax = atoi((char *)idStr);
969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (idMax < *id)
989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uidStr = malloc((idMax + 1) * 256);
999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    else
1009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uidStr = malloc(idMax * 256);
1019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (i = 0; i < idMax; i++) {
1039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (!drm_getString(uidStr[i], 256, handle)) {
1049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
1059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            free(uidStr);
1069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
1079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
1089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    length = strlen((char *)Uid);
1109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    strcpy((char *)uidStr[*id - 1], (char *)Uid);
1119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uidStr[*id - 1][length] = '\n';
1129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uidStr[*id - 1][length + 1] = '\0';
1139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (idMax < (*id))
1149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        idMax++;
1159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
1169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_open(nameUcs2,
1189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    nameLen,
1199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    DRM_FILE_MODE_WRITE,
1209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    &handle);
1219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    sprintf((char *)idStr, "%d", idMax);
1229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (!drm_putString(idStr, handle)) {
1249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
1259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(uidStr);
1269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
1279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_FAILURE == DRM_file_write(handle, (uint8_t *)"\n", 1)) {
1299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
1309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(uidStr);
1319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
1329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (i = 0; i < idMax; i++) {
1349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (!drm_putString(uidStr[i], handle)) {
1359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
1369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            free(uidStr);
1379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
1389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
1399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_FAILURE == DRM_file_write(handle, (uint8_t *)"\n", 1)) {
1419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
1429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(uidStr);
1439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
1449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
1469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    free(uidStr);
1479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
1489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
1499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project/* See objmng_files.h */
1519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_readFromUidTxt(uint8_t* Uid, int32_t* id, int32_t option)
1529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
1539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t i;
1549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t p[256] = { 0 };
1559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t idStr[8];
1569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t idMax = 0;
1579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN];
1589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen = 0;
1599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
1609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t handle;
1619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t fileRes;
1629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == id || NULL == Uid)
1649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
1659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_startup();
1679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* convert in ucs2 */
1699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen(DRM_UID_FILE_PATH);
1709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
1719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        (uint8_t *)DRM_UID_FILE_PATH,
1729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
1739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
1749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
1759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
1769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
1779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
1789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_READ,
1799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
1809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes) {
1819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_open(nameUcs2,
1829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
1839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_WRITE,
1849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
1859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_write(handle, (uint8_t *)"0\n", 2);
1869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
1879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_open(nameUcs2,
1889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
1899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_READ,
1909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
1919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (!drm_getString(idStr, 8, handle)) {
1949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
1959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
1969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
1979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    idMax = atoi((char *)idStr);
1989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
1999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (option == GET_UID) {
2009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (*id < 1 || *id > idMax) {
2019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
2029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
2039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        for (i = 1; i <= *id; i++) {
2059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (!drm_getString(Uid, 256, handle)) {
2069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                DRM_file_close(handle);
2079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                return FALSE;
2089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
2099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
2119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return TRUE;
2129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (option == GET_ID) {
2149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        *id = -1;
2159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        for (i = 1; i <= idMax; i++) {
2169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (!drm_getString(p, 256, handle)) {
2179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                DRM_file_close(handle);
2189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                return FALSE;
2199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
2209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (strstr((char *)p, (char *)Uid) != NULL
2219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                && strlen((char *)p) == strlen((char *)Uid) + 1) {
2229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                *id = i;
2239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                DRM_file_close(handle);
2249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                return TRUE;
2259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
2269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if ((*id == -1) && (strlen((char *)p) < 3))
2279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                *id = i;
2289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (*id != -1) {
2309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
2319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
2329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        *id = idMax + 1;
2349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
2359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
2369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
2389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return FALSE;
2399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
2409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectstatic int32_t drm_acquireId(uint8_t* uid, int32_t* id)
2429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
2439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (TRUE == drm_readFromUidTxt(uid, id, GET_ID))
2449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return TRUE;
2459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    drm_writeToUidTxt(uid, id);
2479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return FALSE; /* The Uid is not exit, then return FALSE indicate it */
2499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
2509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_writeOrReadInfo(int32_t id, T_DRM_Rights* Ro, int32_t* RoAmount, int32_t option)
2529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
2539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t fullname[MAX_FILENAME_LEN] = {0};
2549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t tmpRoAmount;
2559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN];
2569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen = 0;
2579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
2589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t handle;
2599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t fileRes;
2609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    sprintf((char *)fullname, ANDROID_DRM_CORE_PATH"%d"EXTENSION_NAME_INFO, id);
2629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* convert in ucs2 */
2649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen((char *)fullname);
2659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
2669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        fullname,
2679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
2689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
2699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
2709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
2719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
2729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            nameLen,
2739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            DRM_FILE_MODE_READ,
2749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            &handle);
2759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes) {
2769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (GET_ALL_RO == option || GET_A_RO == option)
2779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
2789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (GET_ROAMOUNT == option) {
2809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            *RoAmount = -1;
2819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return TRUE;
2829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
2849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
2869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_open(nameUcs2,
2879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                nameLen,
2889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                DRM_FILE_MODE_READ | DRM_FILE_MODE_WRITE,
2899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                &handle);
2909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
2919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    switch(option) {
2929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    case GET_ROAMOUNT:
2939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_read(handle, (uint8_t*)RoAmount, sizeof(int32_t))) {
2949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
2959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
2969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
2979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        break;
2989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    case GET_ALL_RO:
2999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_setPosition(handle, sizeof(int32_t));
3009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_read(handle, (uint8_t*)Ro, (*RoAmount) * sizeof(T_DRM_Rights))) {
3029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
3039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
3049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        break;
3069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    case SAVE_ALL_RO:
3079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_write(handle, (uint8_t*)RoAmount, sizeof(int32_t))) {
3089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
3099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
3109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (NULL != Ro && *RoAmount >= 1) {
3139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (DRM_FILE_FAILURE == DRM_file_write(handle, (uint8_t*) Ro, (*RoAmount) * sizeof(T_DRM_Rights))) {
3149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                DRM_file_close(handle);
3159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                return FALSE;
3169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
3179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        break;
3199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    case GET_A_RO:
3209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_setPosition(handle, sizeof(int32_t) + (*RoAmount - 1) * sizeof(T_DRM_Rights));
3219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_read(handle, (uint8_t*)Ro, sizeof(T_DRM_Rights))) {
3239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
3249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
3259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        break;
3279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    case SAVE_A_RO:
3289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_setPosition(handle, sizeof(int32_t) + (*RoAmount - 1) * sizeof(T_DRM_Rights));
3299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_write(handle, (uint8_t*)Ro, sizeof(T_DRM_Rights))) {
3319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
3329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
3339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_setPosition(handle, 0);
3369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (DRM_FILE_FAILURE == DRM_file_read(handle, (uint8_t*)&tmpRoAmount, sizeof(int32_t))) {
3379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_close(handle);
3389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            return FALSE;
3399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (tmpRoAmount < *RoAmount) {
3419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_setPosition(handle, 0);
3429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            DRM_file_write(handle, (uint8_t*)RoAmount, sizeof(int32_t));
3439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
3449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        break;
3459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    default:
3469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
3479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
3489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
3499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
3519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
3529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
3539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_appendRightsInfo(T_DRM_Rights* rights)
3559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
3569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t id;
3579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t roAmount;
3589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == rights)
3609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
3619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    drm_acquireId(rights->uid, &id);
3639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (FALSE == drm_writeOrReadInfo(id, NULL, &roAmount, GET_ROAMOUNT))
3659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
3669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (-1 == roAmount)
3689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        roAmount = 0;
3699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* The RO amount increase */
3719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    roAmount++;
3729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* Save the rights information */
3749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (FALSE == drm_writeOrReadInfo(id, rights, &roAmount, SAVE_A_RO))
3759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
3769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
3789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
3799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_getMaxIdFromUidTxt()
3819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
3829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t idStr[8];
3839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t idMax = 0;
3849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN] = {0};
3859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen = 0;
3869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
3879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t handle;
3889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t fileRes;
3899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
3909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* convert in ucs2 */
3919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen(DRM_UID_FILE_PATH);
3929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
3939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        (uint8_t *)DRM_UID_FILE_PATH,
3949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
3959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
3969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
3979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
3989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
3999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
4009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        DRM_FILE_MODE_READ,
4019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &handle);
4029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* this means the uid.txt file is not exist, so there is not any DRM object */
4049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes)
4059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return 0;
4069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (!drm_getString(idStr, 8, handle)) {
4089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_file_close(handle);
4099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return -1;
4109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
4129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    idMax = atoi((char *)idStr);
4149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return idMax;
4159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_removeIdInfoFile(int32_t id)
4189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
4199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t filename[MAX_FILENAME_LEN] = {0};
4209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN];
4219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen = 0;
4229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
4239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (id <= 0)
4259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    sprintf((char *)filename, ANDROID_DRM_CORE_PATH"%d"EXTENSION_NAME_INFO, id);
4289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* convert in ucs2 */
4309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen((char *)filename);
4319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
4329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        filename,
4339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
4349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
4359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
4369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
4379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != DRM_file_delete(nameUcs2, nameLen))
4389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
4419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
4429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_updateUidTxtWhenDelete(int32_t id)
4449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
4459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint16_t nameUcs2[MAX_FILENAME_LEN];
4469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t nameLen = 0;
4479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bytesConsumed;
4489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t handle;
4499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t fileRes;
4509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t bufferLen;
4519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t *buffer;
4529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t idStr[8];
4539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t idMax;
4549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (id <= 0)
4569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = strlen(DRM_UID_FILE_PATH);
4599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    nameLen = DRM_i18n_mbsToWcs(DRM_CHARSET_UTF8,
4609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        (uint8_t *)DRM_UID_FILE_PATH,
4619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameLen,
4629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        nameUcs2,
4639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        MAX_FILENAME_LEN,
4649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                        &bytesConsumed);
4659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    bufferLen = DRM_file_getFileLength(nameUcs2, nameLen);
4669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (bufferLen <= 0)
4679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    buffer = (uint8_t *)malloc(bufferLen);
4709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == buffer)
4719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
4749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            nameLen,
4759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            DRM_FILE_MODE_READ,
4769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                            &handle);
4779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes) {
4789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(buffer);
4799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
4809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
4819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    drm_getString(idStr, 8, handle);
4839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    idMax = atoi((char *)idStr);
4849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    bufferLen -= strlen((char *)idStr);
4869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_read(handle, buffer, bufferLen);
4879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    buffer[bufferLen] = '\0';
4889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
4899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* handle this buffer */
4919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    {
4929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uint8_t *pStart, *pEnd;
4939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        int32_t i, movLen;
4949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
4959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        pStart = buffer;
4969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        pEnd = pStart;
4979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        for (i = 0; i < id; i++) {
4989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (pEnd != pStart)
4999066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                pStart = ++pEnd;
5009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            while ('\n' != *pEnd)
5019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                pEnd++;
5029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (pStart == pEnd)
5039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                pStart--;
5049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
5059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        movLen = bufferLen - (pEnd - buffer);
5069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        memmove(pStart, pEnd, movLen);
5079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        bufferLen -= (pEnd - pStart);
5089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != DRM_file_delete(nameUcs2, nameLen)) {
5119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(buffer);
5129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    fileRes = DRM_file_open(nameUcs2,
5169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        nameLen,
5179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        DRM_FILE_MODE_WRITE,
5189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        &handle);
5199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (DRM_FILE_SUCCESS != fileRes) {
5209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        free(buffer);
5219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5239066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    sprintf((char *)idStr, "%d", idMax);
5249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    drm_putString(idStr, handle);
5259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_write(handle, (uint8_t*)"\n", 1);
5269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_write(handle, buffer, bufferLen);
5279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    free(buffer);
5289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    DRM_file_close(handle);
5299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
5309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_getKey(uint8_t* uid, uint8_t* KeyValue)
5339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    T_DRM_Rights ro;
5359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t id, roAmount;
5369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == uid || NULL == KeyValue)
5389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (FALSE == drm_readFromUidTxt(uid, &id, GET_ID))
5419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5429066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (FALSE == drm_writeOrReadInfo(id, NULL, &roAmount, GET_ROAMOUNT))
5449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (roAmount <= 0)
5479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    memset(&ro, 0, sizeof(T_DRM_Rights));
5509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    roAmount = 1;
5519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (FALSE == drm_writeOrReadInfo(id, &ro, &roAmount, GET_A_RO))
5529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
5539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    memcpy(KeyValue, ro.KeyValue, DRM_KEY_LEN);
5559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
5569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectvoid drm_discardPaddingByte(uint8_t *decryptedBuf, int32_t *decryptedBufLen)
5599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t tmpLen = *decryptedBufLen;
5619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t i;
5629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == decryptedBuf || *decryptedBufLen < 0)
5649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return;
5659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    /* Check whether the last several bytes are padding or not */
5679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    for (i = 1; i < decryptedBuf[tmpLen - 1]; i++) {
5689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        if (decryptedBuf[tmpLen - 1 - i] != decryptedBuf[tmpLen - 1])
5699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            break; /* Not the padding bytes */
5709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (i == decryptedBuf[tmpLen - 1]) /* They are padding bytes */
5729066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        *decryptedBufLen = tmpLen - i;
5739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return;
5749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
5759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
57664e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yehint32_t drm_aesDecBuffer(uint8_t * Buffer, int32_t * BufferLen, AES_KEY *key)
5779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
5789066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t dbuf[3 * DRM_ONE_AES_BLOCK_LEN], buf[DRM_ONE_AES_BLOCK_LEN];
5799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint64_t i, len, wlen = DRM_ONE_AES_BLOCK_LEN, curLen, restLen;
5809066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    uint8_t *pTarget, *pTargetHead;
5819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    pTargetHead = Buffer;
5839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    pTarget = Buffer;
5849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    curLen = 0;
5859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    restLen = *BufferLen;
5869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (restLen > 2 * DRM_ONE_AES_BLOCK_LEN) {
5889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        len = 2 * DRM_ONE_AES_BLOCK_LEN;
5899066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    } else {
5909066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        len = restLen;
5919066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
5929066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    memcpy(dbuf, Buffer, (size_t)len);
5939066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    restLen -= len;
5949066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    Buffer += len;
5959066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
5969066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (len < 2 * DRM_ONE_AES_BLOCK_LEN) { /* The original file is less than one block in length */
5979066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        len -= DRM_ONE_AES_BLOCK_LEN;
5989066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /* Decrypt from position len to position len + DRM_ONE_AES_BLOCK_LEN */
59964e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh        AES_decrypt((dbuf + len), (dbuf + len), key);
6009066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6019066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /* Undo the CBC chaining */
6029066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        for (i = 0; i < len; ++i)
6039066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            dbuf[i] ^= dbuf[i + DRM_ONE_AES_BLOCK_LEN];
6049066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6059066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        /* Output the decrypted bytes */
6069066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        memcpy(pTarget, dbuf, (size_t)len);
6079066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        pTarget += len;
6089066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    } else {
6099066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        uint8_t *b1 = dbuf, *b2 = b1 + DRM_ONE_AES_BLOCK_LEN, *b3 = b2 + DRM_ONE_AES_BLOCK_LEN, *bt;
6109066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6119066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        for (;;) { /* While some ciphertext remains, prepare to decrypt block b2 */
6129066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            /* Read in the next block to see if ciphertext stealing is needed */
6139066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            b3 = Buffer;
6149066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (restLen > DRM_ONE_AES_BLOCK_LEN) {
6159066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                len = DRM_ONE_AES_BLOCK_LEN;
6169066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            } else {
6179066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                len = restLen;
6189066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
6199066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            restLen -= len;
6209066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            Buffer += len;
6219066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6229066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            /* Decrypt the b2 block */
62364e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh            AES_decrypt((uint8_t *)b2, buf, key);
6249066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6259066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (len == 0 || len == DRM_ONE_AES_BLOCK_LEN) { /* No ciphertext stealing */
6269066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Unchain CBC using the previous ciphertext block in b1 */
6279066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                for (i = 0; i < DRM_ONE_AES_BLOCK_LEN; ++i)
6289066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    buf[i] ^= b1[i];
6299066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            } else { /* Partial last block - use ciphertext stealing */
6309066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                wlen = len;
6319066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Produce last 'len' bytes of plaintext by xoring with */
6329066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* The lowest 'len' bytes of next block b3 - C[N-1] */
6339066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                for (i = 0; i < len; ++i)
6349066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    buf[i] ^= b3[i];
6359066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6369066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Reconstruct the C[N-1] block in b3 by adding in the */
6379066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Last (DRM_ONE_AES_BLOCK_LEN - len) bytes of C[N-2] in b2 */
6389066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                for (i = len; i < DRM_ONE_AES_BLOCK_LEN; ++i)
6399066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    b3[i] = buf[i];
6409066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6419066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Decrypt the C[N-1] block in b3 */
64264e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh                AES_decrypt((uint8_t *)b3, (uint8_t *)b3, key);
6439066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6449066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Produce the last but one plaintext block by xoring with */
6459066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* The last but two ciphertext block */
6469066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                for (i = 0; i < DRM_ONE_AES_BLOCK_LEN; ++i)
6479066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                    b3[i] ^= b1[i];
6489066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6499066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                /* Write decrypted plaintext blocks */
6509066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                memcpy(pTarget, b3, DRM_ONE_AES_BLOCK_LEN);
6519066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                pTarget += DRM_ONE_AES_BLOCK_LEN;
6529066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
6539066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6549066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            /* Write the decrypted plaintext block */
6559066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            memcpy(pTarget, buf, (size_t)wlen);
6569066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            pTarget += wlen;
6579066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6589066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            if (len != DRM_ONE_AES_BLOCK_LEN) {
6599066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                *BufferLen = pTarget - pTargetHead;
6609066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project                return 0;
6619066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            }
6629066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6639066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            /* Advance the buffer pointers */
6649066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project            bt = b1, b1 = b2, b2 = b3, b3 = bt;
6659066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        }
6669066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    }
6679066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return 0;
6689066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
6699066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6709066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Projectint32_t drm_updateDcfDataLen(uint8_t* pDcfLastData, uint8_t* keyValue, int32_t* moreBytes)
6719066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project{
67264e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh    AES_KEY key;
6739066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    int32_t len = DRM_TWO_AES_BLOCK_LEN;
6749066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6759066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    if (NULL == pDcfLastData || NULL == keyValue)
6769066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
6779066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
67864e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh    AES_set_decrypt_key(keyValue, DRM_KEY_LEN * 8, &key);
6799066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
68064e69e8ab8f63c0bba14d1e17c0e9595487fc0dcChia-chi Yeh    if (drm_aesDecBuffer(pDcfLastData, &len, &key) < 0)
6819066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project        return FALSE;
6829066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6839066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    drm_discardPaddingByte(pDcfLastData, &len);
6849066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6859066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    *moreBytes = DRM_TWO_AES_BLOCK_LEN - len;
6869066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project
6879066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project    return TRUE;
6889066cfe9886ac131c34d59ed0e2d287b0e3c0087The Android Open Source Project}
689