Home | History | Annotate | Download | only in storage
      1 /*
      2  * Copyright (C) 2010 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 #define LOG_TAG "IMountService"
     18 
     19 #include <storage/IMountService.h>
     20 #include <binder/Parcel.h>
     21 
     22 namespace android {
     23 
     24 enum {
     25     TRANSACTION_registerListener = IBinder::FIRST_CALL_TRANSACTION,
     26     TRANSACTION_unregisterListener,
     27     TRANSACTION_isUsbMassStorageConnected,
     28     TRANSACTION_setUsbMassStorageEnabled,
     29     TRANSACTION_isUsbMassStorageEnabled,
     30     TRANSACTION_mountVolume,
     31     TRANSACTION_unmountVolume,
     32     TRANSACTION_formatVolume,
     33     TRANSACTION_getStorageUsers,
     34     TRANSACTION_getVolumeState,
     35     TRANSACTION_createSecureContainer,
     36     TRANSACTION_finalizeSecureContainer,
     37     TRANSACTION_destroySecureContainer,
     38     TRANSACTION_mountSecureContainer,
     39     TRANSACTION_unmountSecureContainer,
     40     TRANSACTION_isSecureContainerMounted,
     41     TRANSACTION_renameSecureContainer,
     42     TRANSACTION_getSecureContainerPath,
     43     TRANSACTION_getSecureContainerList,
     44     TRANSACTION_shutdown,
     45     TRANSACTION_finishMediaUpdate,
     46     TRANSACTION_mountObb,
     47     TRANSACTION_unmountObb,
     48     TRANSACTION_isObbMounted,
     49     TRANSACTION_getMountedObbPath,
     50     TRANSACTION_isExternalStorageEmulated,
     51     TRANSACTION_decryptStorage,
     52     TRANSACTION_encryptStorage,
     53 };
     54 
     55 class BpMountService: public BpInterface<IMountService>
     56 {
     57 public:
     58     BpMountService(const sp<IBinder>& impl)
     59         : BpInterface<IMountService>(impl)
     60     {
     61     }
     62 
     63     virtual void registerListener(const sp<IMountServiceListener>& listener)
     64     {
     65         Parcel data, reply;
     66         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
     67         data.writeStrongBinder(listener->asBinder());
     68         if (remote()->transact(TRANSACTION_registerListener, data, &reply) != NO_ERROR) {
     69             ALOGD("registerListener could not contact remote\n");
     70             return;
     71         }
     72         int32_t err = reply.readExceptionCode();
     73         if (err < 0) {
     74             ALOGD("registerListener caught exception %d\n", err);
     75             return;
     76         }
     77     }
     78 
     79     virtual void unregisterListener(const sp<IMountServiceListener>& listener)
     80     {
     81         Parcel data, reply;
     82         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
     83         data.writeStrongBinder(listener->asBinder());
     84         if (remote()->transact(TRANSACTION_unregisterListener, data, &reply) != NO_ERROR) {
     85             ALOGD("unregisterListener could not contact remote\n");
     86             return;
     87         }
     88         int32_t err = reply.readExceptionCode();
     89         if (err < 0) {
     90             ALOGD("unregisterListener caught exception %d\n", err);
     91             return;
     92         }
     93     }
     94 
     95     virtual bool isUsbMassStorageConnected()
     96     {
     97         Parcel data, reply;
     98         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
     99         if (remote()->transact(TRANSACTION_isUsbMassStorageConnected, data, &reply) != NO_ERROR) {
    100             ALOGD("isUsbMassStorageConnected could not contact remote\n");
    101             return false;
    102         }
    103         int32_t err = reply.readExceptionCode();
    104         if (err < 0) {
    105             ALOGD("isUsbMassStorageConnected caught exception %d\n", err);
    106             return false;
    107         }
    108         return reply.readInt32() != 0;
    109     }
    110 
    111     virtual void setUsbMassStorageEnabled(const bool enable)
    112     {
    113         Parcel data, reply;
    114         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    115         data.writeInt32(enable != 0);
    116         if (remote()->transact(TRANSACTION_setUsbMassStorageEnabled, data, &reply) != NO_ERROR) {
    117             ALOGD("setUsbMassStorageEnabled could not contact remote\n");
    118             return;
    119         }
    120         int32_t err = reply.readExceptionCode();
    121         if (err < 0) {
    122             ALOGD("setUsbMassStorageEnabled caught exception %d\n", err);
    123             return;
    124         }
    125     }
    126 
    127     virtual bool isUsbMassStorageEnabled()
    128     {
    129         Parcel data, reply;
    130         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    131         if (remote()->transact(TRANSACTION_isUsbMassStorageEnabled, data, &reply) != NO_ERROR) {
    132             ALOGD("isUsbMassStorageEnabled could not contact remote\n");
    133             return false;
    134         }
    135         int32_t err = reply.readExceptionCode();
    136         if (err < 0) {
    137             ALOGD("isUsbMassStorageEnabled caught exception %d\n", err);
    138             return false;
    139         }
    140         return reply.readInt32() != 0;
    141     }
    142 
    143     int32_t mountVolume(const String16& mountPoint)
    144     {
    145         Parcel data, reply;
    146         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    147         data.writeString16(mountPoint);
    148         if (remote()->transact(TRANSACTION_mountVolume, data, &reply) != NO_ERROR) {
    149             ALOGD("mountVolume could not contact remote\n");
    150             return -1;
    151         }
    152         int32_t err = reply.readExceptionCode();
    153         if (err < 0) {
    154             ALOGD("mountVolume caught exception %d\n", err);
    155             return err;
    156         }
    157         return reply.readInt32();
    158     }
    159 
    160     int32_t unmountVolume(const String16& mountPoint, const bool force, const bool removeEncryption)
    161     {
    162         Parcel data, reply;
    163         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    164         data.writeString16(mountPoint);
    165         data.writeInt32(force ? 1 : 0);
    166         data.writeInt32(removeEncryption ? 1 : 0);
    167         if (remote()->transact(TRANSACTION_unmountVolume, data, &reply) != NO_ERROR) {
    168             ALOGD("unmountVolume could not contact remote\n");
    169             return -1;
    170         }
    171         int32_t err = reply.readExceptionCode();
    172         if (err < 0) {
    173             ALOGD("unmountVolume caught exception %d\n", err);
    174             return err;
    175         }
    176         return reply.readInt32();
    177     }
    178 
    179     int32_t formatVolume(const String16& mountPoint)
    180     {
    181         Parcel data, reply;
    182         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    183         data.writeString16(mountPoint);
    184         if (remote()->transact(TRANSACTION_formatVolume, data, &reply) != NO_ERROR) {
    185             ALOGD("formatVolume could not contact remote\n");
    186             return -1;
    187         }
    188         int32_t err = reply.readExceptionCode();
    189         if (err < 0) {
    190             ALOGD("formatVolume caught exception %d\n", err);
    191             return err;
    192         }
    193         return reply.readInt32();
    194     }
    195 
    196     int32_t getStorageUsers(const String16& mountPoint, int32_t** users)
    197     {
    198         Parcel data, reply;
    199         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    200         data.writeString16(mountPoint);
    201         if (remote()->transact(TRANSACTION_getStorageUsers, data, &reply) != NO_ERROR) {
    202             ALOGD("getStorageUsers could not contact remote\n");
    203             return -1;
    204         }
    205         int32_t err = reply.readExceptionCode();
    206         if (err < 0) {
    207             ALOGD("getStorageUsers caught exception %d\n", err);
    208             return err;
    209         }
    210         const int32_t numUsers = reply.readInt32();
    211         *users = (int32_t*)malloc(sizeof(int32_t)*numUsers);
    212         for (int i = 0; i < numUsers; i++) {
    213             **users++ = reply.readInt32();
    214         }
    215         return numUsers;
    216     }
    217 
    218     int32_t getVolumeState(const String16& mountPoint)
    219     {
    220         Parcel data, reply;
    221         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    222         data.writeString16(mountPoint);
    223         if (remote()->transact(TRANSACTION_getVolumeState, data, &reply) != NO_ERROR) {
    224             ALOGD("getVolumeState could not contact remote\n");
    225             return -1;
    226         }
    227         int32_t err = reply.readExceptionCode();
    228         if (err < 0) {
    229             ALOGD("getVolumeState caught exception %d\n", err);
    230             return err;
    231         }
    232         return reply.readInt32();
    233     }
    234 
    235     int32_t createSecureContainer(const String16& id, const int32_t sizeMb, const String16& fstype,
    236             const String16& key, const int32_t ownerUid)
    237     {
    238         Parcel data, reply;
    239         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    240         data.writeString16(id);
    241         data.writeInt32(sizeMb);
    242         data.writeString16(fstype);
    243         data.writeString16(key);
    244         data.writeInt32(ownerUid);
    245         if (remote()->transact(TRANSACTION_createSecureContainer, data, &reply) != NO_ERROR) {
    246             ALOGD("createSecureContainer could not contact remote\n");
    247             return -1;
    248         }
    249         int32_t err = reply.readExceptionCode();
    250         if (err < 0) {
    251             ALOGD("createSecureContainer caught exception %d\n", err);
    252             return err;
    253         }
    254         return reply.readInt32();
    255     }
    256 
    257     int32_t finalizeSecureContainer(const String16& id)
    258     {
    259         Parcel data, reply;
    260         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    261         data.writeString16(id);
    262         if (remote()->transact(TRANSACTION_finalizeSecureContainer, data, &reply) != NO_ERROR) {
    263             ALOGD("finalizeSecureContainer couldn't call remote\n");
    264             return -1;
    265         }
    266         int32_t err = reply.readExceptionCode();
    267         if (err < 0) {
    268             ALOGD("finalizeSecureContainer caught exception %d\n", err);
    269             return err;
    270         }
    271         return reply.readInt32();
    272     }
    273 
    274     int32_t destroySecureContainer(const String16& id)
    275     {
    276         Parcel data, reply;
    277         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    278         data.writeString16(id);
    279         if (remote()->transact(TRANSACTION_destroySecureContainer, data, &reply) != NO_ERROR) {
    280             ALOGD("destroySecureContainer couldn't call remote");
    281             return -1;
    282         }
    283         int32_t err = reply.readExceptionCode();
    284         if (err < 0) {
    285             ALOGD("destroySecureContainer caught exception %d\n", err);
    286             return err;
    287         }
    288         return reply.readInt32();
    289     }
    290 
    291     int32_t mountSecureContainer(const String16& id, const String16& key, const int32_t ownerUid)
    292     {
    293         Parcel data, reply;
    294         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    295         data.writeString16(id);
    296         data.writeString16(key);
    297         data.writeInt32(ownerUid);
    298         if (remote()->transact(TRANSACTION_mountSecureContainer, data, &reply) != NO_ERROR) {
    299             ALOGD("mountSecureContainer couldn't call remote");
    300             return -1;
    301         }
    302         int32_t err = reply.readExceptionCode(); // What to do...
    303         if (err < 0) {
    304             ALOGD("mountSecureContainer caught exception %d\n", err);
    305             return err;
    306         }
    307         return reply.readInt32();
    308     }
    309 
    310     int32_t unmountSecureContainer(const String16& id, const bool force)
    311     {
    312         Parcel data, reply;
    313         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    314         data.writeString16(id);
    315         data.writeInt32(force ? 1 : 0);
    316         if (remote()->transact(TRANSACTION_getSecureContainerPath, data, &reply) != NO_ERROR) {
    317             ALOGD("unmountSecureContainer couldn't call remote");
    318             return -1;
    319         }
    320         int32_t err = reply.readExceptionCode(); // What to do...
    321         if (err < 0) {
    322             ALOGD("unmountSecureContainer caught exception %d\n", err);
    323             return err;
    324         }
    325         return reply.readInt32();
    326     }
    327 
    328     bool isSecureContainerMounted(const String16& id)
    329     {
    330         Parcel data, reply;
    331         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    332         data.writeString16(id);
    333         if (remote()->transact(TRANSACTION_isSecureContainerMounted, data, &reply) != NO_ERROR) {
    334             ALOGD("isSecureContainerMounted couldn't call remote");
    335             return false;
    336         }
    337         int32_t err = reply.readExceptionCode(); // What to do...
    338         if (err < 0) {
    339             ALOGD("isSecureContainerMounted caught exception %d\n", err);
    340             return false;
    341         }
    342         return reply.readInt32() != 0;
    343     }
    344 
    345     int32_t renameSecureContainer(const String16& oldId, const String16& newId)
    346     {
    347         Parcel data, reply;
    348         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    349         data.writeString16(oldId);
    350         data.writeString16(newId);
    351         if (remote()->transact(TRANSACTION_renameSecureContainer, data, &reply) != NO_ERROR) {
    352             ALOGD("renameSecureContainer couldn't call remote");
    353             return -1;
    354         }
    355         int32_t err = reply.readExceptionCode(); // What to do...
    356         if (err < 0) {
    357             ALOGD("renameSecureContainer caught exception %d\n", err);
    358             return err;
    359         }
    360         return reply.readInt32();
    361     }
    362 
    363     bool getSecureContainerPath(const String16& id, String16& path)
    364     {
    365         Parcel data, reply;
    366         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    367         data.writeString16(id);
    368         if (remote()->transact(TRANSACTION_getSecureContainerPath, data, &reply) != NO_ERROR) {
    369             ALOGD("getSecureContainerPath couldn't call remote");
    370             return false;
    371         }
    372         int32_t err = reply.readExceptionCode(); // What to do...
    373         if (err < 0) {
    374             ALOGD("getSecureContainerPath caught exception %d\n", err);
    375             return false;
    376         }
    377         path = reply.readString16();
    378         return true;
    379     }
    380 
    381     int32_t getSecureContainerList(const String16& id, String16*& containers)
    382     {
    383         Parcel data, reply;
    384         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    385         data.writeString16(id);
    386         if (remote()->transact(TRANSACTION_getSecureContainerList, data, &reply) != NO_ERROR) {
    387             ALOGD("getSecureContainerList couldn't call remote");
    388             return -1;
    389         }
    390         int32_t err = reply.readExceptionCode();
    391         if (err < 0) {
    392             ALOGD("getSecureContainerList caught exception %d\n", err);
    393             return err;
    394         }
    395         const int32_t numStrings = reply.readInt32();
    396         containers = new String16[numStrings];
    397         for (int i = 0; i < numStrings; i++) {
    398             containers[i] = reply.readString16();
    399         }
    400         return numStrings;
    401     }
    402 
    403     void shutdown(const sp<IMountShutdownObserver>& observer)
    404     {
    405         Parcel data, reply;
    406         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    407         data.writeStrongBinder(observer->asBinder());
    408         if (remote()->transact(TRANSACTION_shutdown, data, &reply) != NO_ERROR) {
    409             ALOGD("shutdown could not contact remote\n");
    410             return;
    411         }
    412         int32_t err = reply.readExceptionCode();
    413         if (err < 0) {
    414             ALOGD("shutdown caught exception %d\n", err);
    415             return;
    416         }
    417         reply.readExceptionCode();
    418     }
    419 
    420     void finishMediaUpdate()
    421     {
    422         Parcel data, reply;
    423         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    424         if (remote()->transact(TRANSACTION_finishMediaUpdate, data, &reply) != NO_ERROR) {
    425             ALOGD("finishMediaUpdate could not contact remote\n");
    426             return;
    427         }
    428         int32_t err = reply.readExceptionCode();
    429         if (err < 0) {
    430             ALOGD("finishMediaUpdate caught exception %d\n", err);
    431             return;
    432         }
    433         reply.readExceptionCode();
    434     }
    435 
    436     void mountObb(const String16& rawPath, const String16& canonicalPath, const String16& key,
    437             const sp<IObbActionListener>& token, int32_t nonce)
    438     {
    439         Parcel data, reply;
    440         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    441         data.writeString16(rawPath);
    442         data.writeString16(canonicalPath);
    443         data.writeString16(key);
    444         data.writeStrongBinder(token->asBinder());
    445         data.writeInt32(nonce);
    446         if (remote()->transact(TRANSACTION_mountObb, data, &reply) != NO_ERROR) {
    447             ALOGD("mountObb could not contact remote\n");
    448             return;
    449         }
    450         int32_t err = reply.readExceptionCode();
    451         if (err < 0) {
    452             ALOGD("mountObb caught exception %d\n", err);
    453             return;
    454         }
    455     }
    456 
    457     void unmountObb(const String16& filename, const bool force,
    458             const sp<IObbActionListener>& token, const int32_t nonce)
    459     {
    460         Parcel data, reply;
    461         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    462         data.writeString16(filename);
    463         data.writeInt32(force ? 1 : 0);
    464         data.writeStrongBinder(token->asBinder());
    465         data.writeInt32(nonce);
    466         if (remote()->transact(TRANSACTION_unmountObb, data, &reply) != NO_ERROR) {
    467             ALOGD("unmountObb could not contact remote\n");
    468             return;
    469         }
    470         int32_t err = reply.readExceptionCode();
    471         if (err < 0) {
    472             ALOGD("unmountObb caught exception %d\n", err);
    473             return;
    474         }
    475     }
    476 
    477     bool isObbMounted(const String16& filename)
    478     {
    479         Parcel data, reply;
    480         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    481         data.writeString16(filename);
    482         if (remote()->transact(TRANSACTION_isObbMounted, data, &reply) != NO_ERROR) {
    483             ALOGD("isObbMounted could not contact remote\n");
    484             return false;
    485         }
    486         int32_t err = reply.readExceptionCode();
    487         if (err < 0) {
    488             ALOGD("isObbMounted caught exception %d\n", err);
    489             return false;
    490         }
    491         return reply.readInt32() != 0;
    492     }
    493 
    494     bool getMountedObbPath(const String16& filename, String16& path)
    495     {
    496         Parcel data, reply;
    497         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    498         data.writeString16(filename);
    499         if (remote()->transact(TRANSACTION_getMountedObbPath, data, &reply) != NO_ERROR) {
    500             ALOGD("getMountedObbPath could not contact remote\n");
    501             return false;
    502         }
    503         int32_t err = reply.readExceptionCode();
    504         if (err < 0) {
    505             ALOGD("getMountedObbPath caught exception %d\n", err);
    506             return false;
    507         }
    508         path = reply.readString16();
    509         return true;
    510     }
    511 
    512     int32_t decryptStorage(const String16& password)
    513     {
    514         Parcel data, reply;
    515         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    516         data.writeString16(password);
    517         if (remote()->transact(TRANSACTION_decryptStorage, data, &reply) != NO_ERROR) {
    518             ALOGD("decryptStorage could not contact remote\n");
    519             return -1;
    520         }
    521         int32_t err = reply.readExceptionCode();
    522         if (err < 0) {
    523             ALOGD("decryptStorage caught exception %d\n", err);
    524             return err;
    525         }
    526         return reply.readInt32();
    527     }
    528 
    529     int32_t encryptStorage(const String16& password)
    530     {
    531         Parcel data, reply;
    532         data.writeInterfaceToken(IMountService::getInterfaceDescriptor());
    533         data.writeString16(password);
    534         if (remote()->transact(TRANSACTION_encryptStorage, data, &reply) != NO_ERROR) {
    535             ALOGD("encryptStorage could not contact remote\n");
    536             return -1;
    537         }
    538         int32_t err = reply.readExceptionCode();
    539         if (err < 0) {
    540             ALOGD("encryptStorage caught exception %d\n", err);
    541             return err;
    542         }
    543         return reply.readInt32();
    544     }
    545 };
    546 
    547 IMPLEMENT_META_INTERFACE(MountService, "IMountService");
    548 
    549 // ----------------------------------------------------------------------
    550 
    551 };
    552