Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit cca6b426 authored by Mathias Agopian's avatar Mathias Agopian
Browse files

Merge commit 'goog/master' into merge_master

parents f9d93277 f84dda74
Loading
Loading
Loading
Loading
+128 −42
Original line number Diff line number Diff line
/*
** Copyright 2008, The Android Open Source Project
** Copyright 2009, The Android Open Source Project
**
** Licensed under the Apache License, Version 2.0 (the "License");
** you may not use this file except in compliance with the License.
@@ -30,7 +30,8 @@ static DIR *open_keystore(const char *dir)
    return d;
}

static int list_files(const char *dir, char reply[REPLY_MAX]) {
static int list_files(const char *dir, char reply[REPLY_MAX])
{
    struct dirent *de;
    DIR *d;

@@ -39,7 +40,9 @@ static int list_files(const char *dir, char reply[REPLY_MAX]) {
    }
    reply[0]=0;
    while ((de = readdir(d))) {
        if (de->d_type != DT_REG) continue;
        if (de->d_type != DT_DIR) continue;
        if ((strcmp(DOT, de->d_name) == 0) ||
                (strcmp(DOTDOT, de->d_name) == 0)) continue;
        if (reply[0] != 0) strlcat(reply, " ", REPLY_MAX);
        if (strlcat(reply, de->d_name, REPLY_MAX) >= REPLY_MAX) {
            LOGE("reply is too long(too many files under '%s'\n", dir);
@@ -50,92 +53,175 @@ static int list_files(const char *dir, char reply[REPLY_MAX]) {
    return 0;
}

static int copy_keyfile(const char *keystore, const char *srcfile) {
    int srcfd, dstfd;
    int length;
    char buf[2048];
    char dstfile[KEYNAME_LENGTH];
    const char *filename = strrchr(srcfile, '/');
static int copy_keyfile(const char *src, int src_type, const char *dstfile) {
    int srcfd = -1, dstfd;
    char buf[REPLY_MAX];

    strlcpy(dstfile, keystore, KEYNAME_LENGTH);
    strlcat(dstfile, "/", KEYNAME_LENGTH);
    if (strlcat(dstfile, filename ? filename + 1 : srcfile,
                KEYNAME_LENGTH) >= KEYNAME_LENGTH) {
        LOGE("keyname is too long '%s'\n", srcfile);
        return -1;
    }

    if ((srcfd = open(srcfile, O_RDONLY)) == -1) {
        LOGE("Cannot open the original file '%s'\n", srcfile);
    if ((src_type == IS_FILE) && (srcfd = open(src, O_RDONLY)) == -1) {
        LOGE("Cannot open the original file '%s'\n", src);
        return -1;
    }
    if ((dstfd = open(dstfile, O_CREAT|O_RDWR)) == -1) {
        LOGE("Cannot open the destination file '%s'\n", dstfile);
        return -1;
    }
    while((length = read(srcfd, buf, 2048)) > 0) {
    if (src_type == IS_FILE) {
        int length;
        while((length = read(srcfd, buf, REPLY_MAX)) > 0) {
            write(dstfd, buf, length);
        }
    } else {
        write(dstfd, src, strlen(src));
    }
    close(srcfd);
    close(dstfd);
    chmod(dstfile, 0440);
    return 0;
}

static int install_key(const char *dir, const char *keyfile)
static int install_key(const char *path, const char *certname, const char *src,
        int src_is_file, char *dstfile)
{
    struct dirent *de;
    char fullpath[KEYNAME_LENGTH];
    DIR *d;

    if ((d = open_keystore(dir)) == NULL) {
    if (snprintf(fullpath, sizeof(fullpath), "%s/%s/", path, certname)
            >= KEYNAME_LENGTH) {
        LOGE("cert name '%s' is too long.\n", certname);
        return -1;
    }
    return copy_keyfile(dir, keyfile);

    if ((d = open_keystore(fullpath)) == NULL) {
        LOGE("Can not open the keystore '%s'\n", fullpath);
        return -1;
    }
    closedir(d);
    if (strlcat(fullpath, dstfile, KEYNAME_LENGTH) >= KEYNAME_LENGTH) {
        LOGE("cert name '%s' is too long.\n", certname);
        return -1;
    }
    return copy_keyfile(src, src_is_file, fullpath);
}

static int remove_key(const char *dir, const char *keyfile)
static int get_key(const char *path, const char *keyname, const char *file,
        char reply[REPLY_MAX])
{
    struct dirent *de;
    char filename[KEYNAME_LENGTH];
    int fd;

    if (snprintf(filename, sizeof(filename), "%s/%s/%s", path, keyname, file)
            >= KEYNAME_LENGTH) {
        LOGE("cert name '%s' is too long.\n", keyname);
        return -1;
    }

    if ((fd = open(filename, O_RDONLY)) == -1) {
        return -1;
    }
    close(fd);
    strlcpy(reply, filename, REPLY_MAX);
    return 0;
}

static int remove_key(const char *dir, const char *key)
{
    char dstfile[KEYNAME_LENGTH];
    char *keyfile[4] = { USER_KEY, USER_P12_CERT, USER_CERTIFICATE,
            CA_CERTIFICATE };
    int i, count = 0;

    for ( i = 0 ; i < 4 ; i++) {
        if (snprintf(dstfile, KEYNAME_LENGTH, "%s/%s/%s", dir, key, keyfile[i])
                >= KEYNAME_LENGTH) {
            LOGE("keyname is too long '%s'\n", key);
            return -1;
        }
        if (unlink(dstfile) == 0) count++;
    }

    strlcpy(dstfile, dir, KEYNAME_LENGTH);
    strlcat(dstfile, "/", KEYNAME_LENGTH);
    if (strlcat(dstfile, keyfile, KEYNAME_LENGTH) >= KEYNAME_LENGTH) {
        LOGE("keyname is too long '%s'\n", keyfile);
    if (count == 0) {
        LOGE("can not clean up '%s' keys or not exist\n", key);
        return -1;
    }
    if (unlink(dstfile)) {
        LOGE("cannot delete '%s': %s\n", dstfile, strerror(errno));

    snprintf(dstfile, KEYNAME_LENGTH, "%s/%s", dir, key);
    if (rmdir(dstfile)) {
        LOGE("can not clean up '%s' directory\n", key);
        return -1;
    }
    return 0;
}

int list_certs(char reply[REPLY_MAX])
int list_user_certs(char reply[REPLY_MAX])
{
    return list_files(CERTS_DIR, reply);
}

int list_userkeys(char reply[REPLY_MAX])
int list_ca_certs(char reply[REPLY_MAX])
{
    return list_files(CACERTS_DIR, reply);
}

int install_user_cert(const char *keyname, const char *cert, const char *key)
{
    if (install_key(CERTS_DIR, keyname, cert, IS_FILE, USER_CERTIFICATE) == 0) {
        return install_key(CERTS_DIR, keyname, key, IS_FILE, USER_KEY);
    }
    return -1;
}

int install_ca_cert(const char *keyname, const char *certfile)
{
    return install_key(CACERTS_DIR, keyname, certfile, IS_FILE, CA_CERTIFICATE);
}

int install_p12_cert(const char *keyname, const char *certfile)
{
    return list_files(USERKEYS_DIR, reply);
    return install_key(CERTS_DIR, keyname, certfile, IS_FILE, USER_P12_CERT);
}

int install_cert(const char *certfile)
int add_ca_cert(const char *keyname, const char *certificate)
{
    return install_key(CERTS_DIR, certfile);
    return install_key(CACERTS_DIR, keyname, certificate, IS_CONTENT,
            CA_CERTIFICATE);
}

int install_userkey(const char *keyfile)
int add_user_cert(const char *keyname, const char *certificate)
{
    return install_key(USERKEYS_DIR, keyfile);
    return install_key(CERTS_DIR, keyname, certificate, IS_CONTENT,
            USER_CERTIFICATE);
}

int add_user_key(const char *keyname, const char *key)
{
    return install_key(CERTS_DIR, keyname, key, IS_CONTENT, USER_KEY);
}

int get_ca_cert(const char *keyname, char reply[REPLY_MAX])
{
    return get_key(CACERTS_DIR, keyname, CA_CERTIFICATE, reply);
}

int get_user_cert(const char *keyname, char reply[REPLY_MAX])
{
    return get_key(CERTS_DIR, keyname, USER_CERTIFICATE, reply);
}

int get_user_key(const char *keyname, char reply[REPLY_MAX])
{
    if(get_key(CERTS_DIR, keyname, USER_KEY, reply))
        return get_key(CERTS_DIR, keyname, USER_P12_CERT, reply);
    return 0;
}

int remove_cert(const char *certfile)
int remove_user_cert(const char *key)
{
    return remove_key(CERTS_DIR, certfile);
    return remove_key(CERTS_DIR, key);
}

int remove_userkey(const char *keyfile)
int remove_ca_cert(const char *key)
{
    return remove_key(USERKEYS_DIR, keyfile);
    return remove_key(CACERTS_DIR, key);
}
+80 −20
Original line number Diff line number Diff line
@@ -16,37 +16,89 @@

#include "keystore.h"

static inline int has_whitespace(char *name)
{
    if((strrchr(name, ' ') != NULL)) {
        LOGE("'%s' contains whitespace character\n", name);
        return 1;
    }
    return 0;
}

static int do_list_user_certs(char **arg, char reply[REPLY_MAX])
{
    return list_user_certs(reply);
}

static int do_list_ca_certs(char **arg, char reply[REPLY_MAX])
{
    return list_ca_certs(reply);
}

static int do_install_user_cert(char **arg, char reply[REPLY_MAX])
{
    if (has_whitespace(arg[0])) return -1;
    /* copy the certificate and key to keystore */
    return install_user_cert(arg[0], arg[1], arg[2]);
}

static int do_list_certs(char **arg, char reply[REPLY_MAX])
static int do_install_p12_cert(char **arg, char reply[REPLY_MAX])
{
    return list_certs(reply);
    if (has_whitespace(arg[0])) return -1;
    return install_p12_cert(arg[0], arg[1]);
}

static int do_list_userkeys(char **arg, char reply[REPLY_MAX])
static int do_install_ca_cert(char **arg, char reply[REPLY_MAX])
{
    return list_userkeys(reply);
    if (has_whitespace(arg[0])) return -1;
    /* copy the certificate and key to keystore */
    return install_ca_cert(arg[0], arg[1]);
}

static int do_install_cert(char **arg, char reply[REPLY_MAX])
static int do_add_ca_cert(char **arg, char reply[REPLY_MAX])
{
    return install_cert(arg[0]); /* move the certificate to keystore */
    if (has_whitespace(arg[0])) return -1;
    return add_ca_cert(arg[0], arg[1]);
}

static int do_remove_cert(char **arg, char reply[REPLY_MAX])
static int do_add_user_cert(char **arg, char reply[REPLY_MAX])
{
    return remove_cert(arg[0]); /* certificate */
    if (has_whitespace(arg[0])) return -1;
    return add_user_cert(arg[0], arg[1]);
}

static int do_install_userkey(char **arg, char reply[REPLY_MAX])
static int do_add_user_key(char **arg, char reply[REPLY_MAX])
{
    return install_userkey(arg[0]); /* move the certificate to keystore */
    if (has_whitespace(arg[0])) return -1;
    return add_user_key(arg[0], arg[1]);
}

static int do_remove_userkey(char **arg, char reply[REPLY_MAX])
static int do_get_ca_cert(char **arg, char reply[REPLY_MAX])
{
    return remove_userkey(arg[0]); /* userkey */
    return get_ca_cert(arg[0], reply);
}

static int do_get_user_cert(char **arg, char reply[REPLY_MAX])
{
    return get_user_cert(arg[0], reply);
}

static int do_get_user_key(char **arg, char reply[REPLY_MAX])
{
    return get_user_key(arg[0], reply);
}

static int do_remove_user_cert(char **arg, char reply[REPLY_MAX])
{
    return remove_user_cert(arg[0]);
}

static int do_remove_ca_cert(char **arg, char reply[REPLY_MAX])
{
    return remove_ca_cert(arg[0]);
}


struct cmdinfo {
    const char *name;
    unsigned numargs;
@@ -55,12 +107,19 @@ struct cmdinfo {


struct cmdinfo cmds[] = {
    { "listcerts",            0, do_list_certs },
    { "listuserkeys",         0, do_list_userkeys },
    { "installcert",          1, do_install_cert },
    { "removecert",           1, do_remove_cert },
    { "installuserkey",       1, do_install_userkey },
    { "removeuserkey",        1, do_remove_userkey },
    { "listcacerts",        0, do_list_ca_certs },
    { "listusercerts",      0, do_list_user_certs },
    { "installusercert",    3, do_install_user_cert },
    { "installcacert",      2, do_install_ca_cert },
    { "installp12cert",     2, do_install_p12_cert },
    { "addusercert",        2, do_add_user_cert },
    { "adduserkey",         2, do_add_user_key },
    { "addcacert",          2, do_add_ca_cert },
    { "getusercert",        1, do_get_user_cert },
    { "getuserkey",         1, do_get_user_key },
    { "getcacert",          1, do_get_ca_cert },
    { "removecacert",       1, do_remove_ca_cert },
    { "removeusercert",     1, do_remove_user_cert },
};

static int readx(int s, void *_buf, int count)
@@ -121,7 +180,7 @@ static int execute(int s, char cmd[BUFFER_MAX])
    /* n is number of args (not counting arg[0]) */
    arg[0] = cmd;
    while (*cmd) {
        if (isspace(*cmd)) {
        if (*cmd == CMD_DELIMITER) {
            *cmd++ = 0;
            n++;
            arg[n] = cmd;
@@ -167,6 +226,7 @@ int shell_command(const int argc, const char **argv)
    int fd, i;
    short ret;
    unsigned short count;
    char delimiter[2] = { CMD_DELIMITER, 0 };
    char buf[BUFFER_MAX]="";

    fd = socket_local_client(SOCKET_PATH,
@@ -177,7 +237,7 @@ int shell_command(const int argc, const char **argv)
        exit(1);
    }
    for(i = 0; i < argc; i++) {
        if (i > 0) strlcat(buf, " ", BUFFER_MAX);
        if (i > 0) strlcat(buf, delimiter, BUFFER_MAX);
        if(strlcat(buf, argv[i], BUFFER_MAX) >= BUFFER_MAX) {
            fprintf(stderr, "Arguments are too long\n");
            exit(1);
+27 −10
Original line number Diff line number Diff line
@@ -40,18 +40,35 @@
/* path of the keystore */

#define KEYSTORE_DIR_PREFIX "/data/misc/keystore"
#define CERTS_DIR           KEYSTORE_DIR_PREFIX "/certs"
#define USERKEYS_DIR         KEYSTORE_DIR_PREFIX "/userkeys"
#define CERTS_DIR           KEYSTORE_DIR_PREFIX "/keys"
#define CACERTS_DIR         KEYSTORE_DIR_PREFIX "/cacerts"
#define CA_CERTIFICATE      "ca.crt"
#define USER_CERTIFICATE    "user.crt"
#define USER_P12_CERT       "user.p12"
#define USER_KEY            "user.key"
#define DOT                 "."
#define DOTDOT              ".."

#define BUFFER_MAX      1024  /* input buffer for commands */
#define BUFFER_MAX      4096  /* input buffer for commands */
#define TOKEN_MAX       8     /* max number of arguments in buffer */
#define REPLY_MAX       1024  /* largest reply allowed */
#define REPLY_MAX       4096  /* largest reply allowed */
#define CMD_DELIMITER   '\t'
#define KEYNAME_LENGTH  128
#define IS_CONTENT      0
#define IS_FILE         1


/* commands.c */
int list_certs(char reply[REPLY_MAX]);
int list_userkeys(char reply[REPLY_MAX]);
int install_cert(const char *certfile);
int install_userkey(const char *keyfile);
int remove_cert(const char *certfile);
int remove_userkey(const char *keyfile);
int list_ca_certs(char reply[REPLY_MAX]);
int list_user_certs(char reply[REPLY_MAX]);
int install_user_cert(const char *certname, const char *cert, const char *key);
int install_ca_cert(const char *certname, const char *cert);
int install_p12_cert(const char *certname, const char *cert);
int add_ca_cert(const char *certname, const char *content);
int add_user_cert(const char *certname, const char *content);
int add_user_key(const char *keyname, const char *content);
int get_ca_cert(const char *keyname, char reply[REPLY_MAX]);
int get_user_cert(const char *keyname, char reply[REPLY_MAX]);
int get_user_key(const char *keyname, char reply[REPLY_MAX]);
int remove_user_cert(const char *certname);
int remove_ca_cert(const char *certname);
+11 −7
Original line number Diff line number Diff line
@@ -100,13 +100,17 @@ public:
    // @return TTS_SUCCESS, or TTS_FAILURE
    virtual tts_result loadLanguage(const char *value, const size_t size);
    
    // Signal the engine to use the specified language. This will force the
    // language to be loaded if it wasn't loaded previously with loadLanguage().
    // See loadLanguage for the specification of the language.
    // @param value pointer to the language value
    // @param size  length of the language value
    // Load the resources associated with the specified language, country and Locale variant.
    // The loaded language will only be used once a call to setLanguageFromLocale() with the same
    // language value is issued. Language and country values are coded according to the ISO three
    // letter codes for languages and countries, as can be retrieved from a java.util.Locale
    // instance. The variant value is encoded as the variant string retrieved from a
    // java.util.Locale instance built with that variant data.
    // @param lang pointer to the ISO three letter code for the language
    // @param country pointer to the ISO three letter code for the country
    // @param variant pointer to the variant code
    // @return TTS_SUCCESS, or TTS_FAILURE
    virtual tts_result setLanguage(const char *value, const size_t size);
    virtual tts_result setLanguage(const char *lang, const char *country, const char *variant);

    // Retrieve the currently set language, or an empty "value" if no language
    // has been set.
+39 −24
Original line number Diff line number Diff line
@@ -19,33 +19,40 @@

#include <utils/Errors.h>
#include <utils/String8.h>
#include <utils/KeyedVector.h>

namespace android {

enum {
    BACKUP_HEADER_APP_V1 = 0x31707041, // App1 (little endian)
    BACKUP_HEADER_ENTITY_V1 = 0x61746144, // Data (little endian)
    BACKUP_FOOTER_APP_V1 = 0x746f6f46, // Foot (little endian)
};

// the sizes of all of these match.
typedef struct {
    int type; // == BACKUP_HEADER_APP_V1
    int packageLen; // length of the name of the package that follows, not including the null.
    int cookie;
} app_header_v1;

typedef struct {
    int type; // BACKUP_HEADER_ENTITY_V1
    int keyLen; // length of the key name, not including the null terminator
    int dataSize; // size of the data, not including the padding, -1 means delete
} entity_header_v1;

typedef struct {
    int type; // BACKUP_FOOTER_APP_V1
    int entityCount; // the number of entities that were written
    int cookie;
} app_footer_v1;
struct SnapshotHeader {
    int magic0;
    int fileCount;
    int magic1;
    int totalSize;
};

struct FileState {
    int modTime_sec;
    int modTime_nsec;
    int size;
    int crc32;
    int nameLen;
};

struct FileRec {
    String8 file;
    bool deleted;
    FileState s;
};


/**
@@ -61,13 +68,9 @@ public:
    // does not close fd
    ~BackupDataWriter();

    status_t WriteAppHeader(const String8& packageName, int cookie);

    status_t WriteEntityHeader(const String8& key, size_t dataSize);
    status_t WriteEntityData(const void* data, size_t size);

    status_t WriteAppFooter(int cookie);

private:
    explicit BackupDataWriter();
    status_t write_padding_for(int n);
@@ -92,34 +95,46 @@ public:
    ~BackupDataReader();

    status_t Status();
    status_t ReadNextHeader(int* type = NULL);
    status_t ReadNextHeader(bool* done, int* type);

    status_t ReadAppHeader(String8* packageName, int* cookie);
    bool HasEntities();
    status_t ReadEntityHeader(String8* key, size_t* dataSize);
    status_t SkipEntityData(); // must be called with the pointer at the begining of the data.
    status_t ReadEntityData(void* data, size_t size);
    status_t ReadAppFooter(int* cookie);
    ssize_t ReadEntityData(void* data, size_t size);

private:
    explicit BackupDataReader();
    status_t skip_padding();
    
    int m_fd;
    bool m_done;
    status_t m_status;
    ssize_t m_pos;
    ssize_t m_dataEndPos;
    int m_entityCount;
    union {
        int type;
        app_header_v1 app;
        entity_header_v1 entity;
        app_footer_v1 footer;
    } m_header;
    String8 m_key;
};

int back_up_files(int oldSnapshotFD, BackupDataWriter* dataStream, int newSnapshotFD,
        char const* const* files, char const* const *keys, int fileCount);

class RestoreHelperBase
{
public:
    RestoreHelperBase();
    ~RestoreHelperBase();

    status_t WriteFile(const String8& filename, BackupDataReader* in);
    status_t WriteSnapshot(int fd);

private:
    void* m_buf;
    KeyedVector<String8,FileRec> m_files;
};

#define TEST_BACKUP_HELPERS 1

Loading