Exemplo n.º 1
0
/* write_radio_image <src-image>
 * write_hboot_image <src-image>
 * Doesn't actually take effect until the rest of installation finishes.
 */
static int
cmd_write_firmware_image(const char *name, void *cookie,
        int argc, const char *argv[])
{
    UNUSED(cookie);
    CHECK_WORDS();

    if (argc != 1) {
        LOGE("Command %s requires exactly one argument\n", name);
        return 1;
    }

    const char *type;
    if (!strcmp(name, "write_radio_image")) {
        type = "radio";
    } else if (!strcmp(name, "write_hboot_image")) {
        type = "hboot";
    } else {
        LOGE("Unknown firmware update command %s\n", name);
        return 1;
    }

    if (!is_package_root_path(argv[0])) {
        LOGE("Command %s: non-package image file \"%s\" not supported\n",
                name, argv[0]);
        return 1;
    }

    ui_print("Extracting %s image...\n", type);
    char path[PATH_MAX];
    const ZipArchive *package;
    if (!translate_package_root_path(argv[0], path, sizeof(path), &package)) {
        LOGE("Command %s: bad source path \"%s\"\n", name, argv[0]);
        return 1;
    }

    const ZipEntry *entry = mzFindZipEntry(package, path);
    if (entry == NULL) {
        LOGE("Can't find %s\n", path);
        return 1;
    }

    // Load the update image into RAM.
    struct FirmwareContext context;
    context.total_bytes = mzGetZipEntryUncompLen(entry);
    context.done_bytes = 0;
    context.data = malloc(context.total_bytes);
    if (context.data == NULL) {
        LOGE("Can't allocate %d bytes for %s\n", context.total_bytes, argv[0]);
        return 1;
    }

    if (!mzProcessZipEntryContents(package, entry, firmware_fn, &context) ||
        context.done_bytes != context.total_bytes) {
        LOGE("Can't read %s\n", argv[0]);
        free(context.data);
        return 1;
    }

    if (remember_firmware_update(type, context.data, context.total_bytes)) {
        LOGE("Can't store %s image\n", type);
        free(context.data);
        return 1;
    }

    return 0;
}
Exemplo n.º 2
0
/* write_raw_image <src-image> <dest-root>
 */
static int
cmd_write_raw_image(const char *name, void *cookie,
        int argc, const char *argv[])
{
    UNUSED(cookie);
    CHECK_WORDS();

    if (argc != 2) {
        LOGE("Command %s requires exactly two arguments\n", name);
        return 1;
    }

    // Use 10% of the progress bar (20% post-verification) by default
    const char *src_root_path = argv[0];
    const char *dst_root_path = argv[1];
    ui_print("Writing %s...\n", dst_root_path);
    if (!gDidShowProgress) ui_show_progress(DEFAULT_IMAGE_PROGRESS_FRACTION, 0);

    /* Find the source image, which is probably in a package.
     */
    if (!is_package_root_path(src_root_path)) {
        LOGE("Command %s: non-package source path \"%s\" not yet supported\n",
                name, src_root_path);
        return 255;
    }

    /* Get the package.
     */
    char srcpathbuf[PATH_MAX];
    const char *src_path;
    const ZipArchive *package;
    src_path = translate_package_root_path(src_root_path,
            srcpathbuf, sizeof(srcpathbuf), &package);
    if (src_path == NULL) {
        LOGE("Command %s: bad source path \"%s\"\n", name, src_root_path);
        return 1;
    }

    /* Get the entry.
     */
    const ZipEntry *entry = mzFindZipEntry(package, src_path);
    if (entry == NULL) {
        LOGE("Missing file %s\n", src_path);
        return 1;
    }

    /* Unmount the destination root if it isn't already.
     */
    int ret = ensure_root_path_unmounted(dst_root_path);
    if (ret < 0) {
        LOGE("Can't unmount %s\n", dst_root_path);
        return 1;
    }

    /* Open the partition for writing.
     */
    const MtdPartition *partition = get_root_mtd_partition(dst_root_path);
    if (partition == NULL) {
        LOGE("Can't find %s\n", dst_root_path);
        return 1;
    }
    MtdWriteContext *context = mtd_write_partition(partition);
    if (context == NULL) {
        LOGE("Can't open %s\n", dst_root_path);
        return 1;
    }

    /* Extract and write the image.
     */
    bool ok = mzProcessZipEntryContents(package, entry,
            write_raw_image_process_fn, context);
    if (!ok) {
        LOGE("Error writing %s\n", dst_root_path);
        mtd_write_close(context);
        return 1;
    }

    if (mtd_erase_blocks(context, -1) == (off_t) -1) {
        LOGE("Error finishing %s\n", dst_root_path);
        mtd_write_close(context);
        return -1;
    }

    if (mtd_write_close(context)) {
        LOGE("Error closing %s\n", dst_root_path);
        return -1;
    }
    return 0;
}
Exemplo n.º 3
0
static void* unzip_new_data(void* cookie) {
    NewThreadInfo* nti = (NewThreadInfo*) cookie;
    mzProcessZipEntryContents(nti->za, nti->entry, receive_new_data, nti);
    return NULL;
}